volatile int typecast return value. Could this make problem?

Hello experts, I'm a beginner of embedded system development.

I have question.about difference of two code.

at first, suppose there is function like

   int SomeFunction(void) {

      ......

       return (some integer);

}

And using this function return value like these

  • int retval;

       retval = SomeFunction();

       if (retval == {some Variable})  {

         . . .

       }

  • if ( {some Variable} == (volatile int) SomeFunction()) {

          ....

        }

    

former one doesn't make any problem, but when i used like latter one.. some times, retval is not correct and some strange value remains on r0 register...;

I don't know what is problem on latter one exactly...;

Could explain what is the problem of these?

Thank you very much for reading this..... though it is written by pool english...

Parents
  • Hello  levi,

    if the retval of the volatile function was incorrect, it would might be a bug of the compiler.
    The difference between
    retval = SomeFunction();
    and
    retval = (volatile int)SomeFunction();
    is whether the function must be executed for every call.
    In the case of several function calls of SomeFunction, if there would not be the volatile cast, the call might be executed once and the return value might be re-use for the other return values of the same functions.
    If there is the volatile cast, the function must be executed for every its function call.
    Therefore, if the return value is defined in one way according to the input arguments, the volatile cast has no means.
    The volatile cast would be used when the return value would vary at every call even if the input arguments are the same.

    For example, please refer to the following source code and assembled result.

    o Source Code

    int main()
    {
      int retval;
      retval = SomeFunction();
      if (retval == 0x11223344) {
        foo();
      }
      if (retval == 0x11223344) {
        bar();
      }
      if ( 0x11223344 == (volatile int) SomeFunction()) {
        foo();
      }
      if ( 0x11223344 == (volatile int) SomeFunction()) {
        bar();
      }
      return 0;
    }     
    
    

    o Assembled Result

    main:
            stmfd   sp!, {fp, lr}
            add     fp, sp, #4
            sub     sp, sp, #8
            bl      SomeFunction
            str     r0, [fp, #-8]
            ldr     r2, [fp, #-8]
            movw    r3, #13124
            movt    r3, 4386
            cmp     r2, r3
            bne     .L4
            bl      foo
    .L4:
            ldr     r2, [fp, #-8]  @ return value is re-used
            movw    r3, #13124
            movt    r3, 4386
            cmp     r2, r3
            bne     .L5
            bl      bar
    .L5:
            bl      SomeFunction
            mov     r2, r0
            movw    r3, #13124
            movt    r3, 4386
            cmp     r2, r3
            bne     .L6
            bl      foo
    .L6:
            bl      SomeFunction
            mov     r2, r0
            movw    r3, #13124
            movt    r3, 4386
            cmp     r2, r3
            bne     .L7
            bl      bar
    .L7:
            mov     r3, #0
            mov     r0, r3
            sub     sp, fp, #4
            ldmfd   sp!, {fp, pc}
     
    

    Best regards,
    Yasuhiko Koumoto.

  • Thanks a lot yasuhikokoumoto.

    Your answer is so helpful.

    But i stiil  have a question.

    Strangely, when I used the return value by saving volatile variable, there is no problem.

    In other word.. if I used like..

    1

    2

    3

    4

    5

    6

    7

    8

    9

    10

    11

    12

    13

    14

    15

    16

    17

    18

    19

    20

    21

    22

    23

    24

    25

    26

    27

    int SomeFunction(void)

    {

        ...

       

        return {Some integer but changeable like Tick..}

    }

    int main (void)

    {

        (volatile int) retval;

        int comparedVariable = {Some value} ;

        ...

       

        retval = SomeFunction(void);

       

        // There is no Bugs.

        if (retval  == compareVriable) {

            foo();

        } else {

            exit(1);

        }

    }

    Colored by Color Scripter

    cs

    above way doesn't make any problem....

    but if I compare using typecasting like..

    1

    2

    3

    4

    5

    6

    7

    8

    9

    10

    11

    12

    13

    14

    15

    16

    17

    18

    19

    20

    21

    22

    23

    24

    25

    int SomeFunction(void)

    {

        ...

       

        return {Some integer but changeable like Tick..}

    }

    int main (void)

    {

        int comparedVariable = {Some value} ;

        ...

       

        retval = SomeFunction(void);

       

        // Some times retrun value saved in r0 is wrong.

        if (compareVriable == (volatile int) SomeFunction()) {

            foo();

        } else {

            exit(1);

        }

    }

    Colored by Color Scripter

    cs

    makes the problem.

    when i compared the assembly code..... also, there is no big difference.. Just r0 value is wrong, when comparing.

    Could I think it is compiler bug as you said?

    Thx a lot.

Reply Children
More questions in this forum