Uploaded image for project: 'Embedded Software & Tools'
  1. Embedded Software & Tools
  2. EXT_EP-7977

Double constant expression may be incorrectly truncated if assigned to a narrow integer type

    XMLWordPrintable

Details

    • Bug
    • Status: Accepted
    • Low
    • Resolution: Unresolved
    • Code Generation Tools
    • CODEGEN-662
    • SDSCM00047077
    • Hide
      ARM_15.12.0.LTS
      ARM_18.1.0.LTS
      ARM_16.9.0.LTS
      ARM_18.12.0.LTS
      ARM_5.2.0B1
      ARM_20.2.0.LTS
      Show
      ARM_15.12.0.LTS ARM_18.1.0.LTS ARM_16.9.0.LTS ARM_18.12.0.LTS ARM_5.2.0B1 ARM_20.2.0.LTS
    • Cast such expressions to long or unsigned long instead.
    • No plans to address at this time.

    Description

      The expression ushort = 0.04f * 1000.0 gets a different value than ulong = 0.04f * 1000.0, even in strict mode.

      The value 0.04 is not exactly representable in IEEE-754 binary floating-point format. The value used in the compiler is approximately 0.039999999105930328369140625 (exactly 0x1.47ae14p-5, in C99 hex format).
      1000.0 is a double-precision float constant because you didn't use the 'f' suffix. 1000.0f is a single-precision float constant.
      When you perform arithmetic on floating-point types, rounding occurs
      When you perform arithmetic on mixed types, the compiler must promote them to a common type, usually the larger of the two.

      Now, what's going on is that you are multiplying the single-precision variable fTest by a double-precision value 1000.0. This requires the compiler to promote the value in fTest to a double, which means adding a bunch of zeros on the end. The compiler then rounds the double-precision result, which has a lot of zeros at the end, so it doesn't round up. Then the value gets truncated to an integer type for assignment to an integer.

      The parser assumes that (because the ultimate destination has only 16 bits) that it is safe to convert 1000.0 to 1000.0f; the problem is that this changes the result. This is safe if the ultimate destination is float, because double->float conversion rounds, but double->integer truncates.

      Attachments

        Activity

          People

            syncuser TI User
            syncuser TI User
            Votes:
            1 Vote for this issue
            Watchers:
            1 Start watching this issue

            Dates

              Created:
              Updated: