This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

Question for "<<"

Hi all

I write a sample code like

a = 1 << b;

when b = 0 , The result for a will get 2

If I uncheck "Enable ANSI integer promotion rules " ,It will get correct answer 1

can anyone tell me why ??

Thanks a lot

  • Sorry, I try this again

    It seems like even I uncheck

    "Enable ANSI integer promotion rules "

    The result also fail.

    Here is the code ,Please help to this

    void start_dmpg(void)
    {
    uchar b = ptr_reg[PCIC_PC2MPU_CMD7];

    uchar a = (ENABLE << b);
    }

    ; FUNCTION start_dmpg (BEGIN)
    ; SOURCE LINE # 169
    ; SOURCE LINE # 170
    ; SOURCE LINE # 175
    0000 900000 E MOV DPTR,#ptr_reg
    0003 E0 MOVX A,@DPTR
    0004 FE MOV R6,A
    0005 A3 INC DPTR
    0006 E0 MOVX A,@DPTR
    0007 FF MOV R7,A
    0008 8F82 MOV DPL,R7
    000A 8E83 MOV DPH,R6
    000C E582 MOV A,DPL
    000E 2447 ADD A,#047H
    0010 F582 MOV DPL,A
    0012 E583 MOV A,DPH
    0014 3404 ADDC A,#04H
    0016 F583 MOV DPH,A
    0018 E0 MOVX A,@DPTR
    0019 FF MOV R7,A
    001A 900000 R MOV DPTR,#b
    001D EF MOV A,R7
    001E F0 MOVX @DPTR,A
    ; SOURCE LINE # 177
    001F 900000 R MOV DPTR,#b
    0022 E0 MOVX A,@DPTR
    0023 FF MOV R7,A
    0024 7401 MOV A,#01H
    0026 A807 MOV R0,AR7
    0028 08 INC R0
    0029 8002 SJMP ?C0181
    002B ?C0180:
    002B C3 CLR C
    002C 33 RLC A
    002D ?C0181:
    002D D8FC DJNZ R0,?C0180
    002F FF MOV R7,A
    0030 900000 R MOV DPTR,#a
    0033 EF MOV A,R7
    0034 F0 MOVX @DPTR,A
    C51 COMPILER V7.08 CMD51 05/10/2005 14:34:41 PAGE 106

    ; SOURCE LINE # 199
    0035 ?C0012:
    0035 22 RET
    ; FUNCTION start_dmpg (END)

  • "b" is a variable, extracted from a table. Are you sure it is zero when you execute the shift?

  • Yes,I Sure

    The ptr_reg[PCIC_PC2MPU_CMD7] Value

    is set by me,I have print out the value

    is zero like I set,but the answer is 2.

    Thanks for yuor replay.

  • Hi

    Noone know this ??

    why a = 1 << b

    when b = 0 , a is not always equal 1

    why??

  • "Noone know this ??"

    I don't think anyone is convinced that b=0.

    Try compiling a simple test case in isolation, if it gives the correct result take another look at 'b' to see whether it is actually 1.

  • The section of your code that does the shifting is this bit:

    0024 7401   MOV A,#01H
    0026 A807   MOV R0,AR7
    0028 08     INC R0
    0029 8002   SJMP ?C0181
    002B ?C0180:
    002B C3     CLR C
    002C 33     RLC A
    002D ?C0181:
    002D D8FC   DJNZ R0,?C0180
    002F FF     MOV R7,A
    
    That looks OK to me. This is an 8-bit shift so presumably this is the code without ANSI promotion rules.

    Is the code you posted the version that works?

    In the past, I have spent some time looking at the shift operators in C51 and they always looked OK to me.

    You might find the following code to be of interest, although it only relates to 16 and 32-bit shift and roll operations.

    http://www.programmersheaven.com/zone5/cat27/31937.htm

  • Thanks for replay

    I have a ready to this ,Please see it

    #define ENABLE 1
    uchar volatile xdata *ptr_reg=0x8000;
    bug0 =0;
    bug1 =0;

    uchar b = pre_reg[0];

    a = (ENABLE << b);

    if ( b != 0 ) bug0++;
    if ( a != 1 ) bug1++;

    after I run this ,bug0 is zero ,but bug1
    is nonzero.

    I also have run this code in VC60,and it work fine.

    Thanks for your kind help

  • Thank to Graham

    I also think the asm code is fine,
    but I realy got a wrong answer ><

    maybe I have setting something wrong&#12290;

    For now,I just use switch-case to do
    this sample work.

  • uchar volatile xdata *ptr_reg=0x8000;
    bug0 =0;
    bug1 =0;
    
    uchar b = pre_reg[0];
    You have shown a definition for ptr_reg, but you are using pre_reg.

    What is pre_reg?

    When posting code for others to review, be sure to use cut-and-paste - do not manually retype!

  • Thanks for correct my type error^^"""

    Sorry,I have already delete the code
    so i just type it again.

    It is ptr_reg not pre_reg&#12290;

    Thanks a lot

  • Do you call the function from an interrupt service routine. The code that you have posted works correct for registerbank 0, but will fail if you call it from an interrupt service routine that uses a different register bank.

    See also: http://www.keil.com/support/docs/2201.htm


    Reinhard