PRB: Compiler Generates C4056, C4756 Warnings Incorrectly

Last reviewed: July 17, 1997
Article ID: Q97839
6.00 6.00a 6.00ax 7.00 | 1.00 1.50 1.51 1.52
MS-DOS                 | WINDOWS
kbtool kbprb

The information in this article applies to:

  • The Microsoft C/C++ Compiler (CL.EXE), included with:

        - Microsoft C for MS-DOS, versions 6.0, 6.0a, and 6.0ax
        - Microsoft C/C++ for MS-DOS, versions 7.0
        - Microsoft Visual C++ for Windows, versions 1.0, 1.5, 1.51, and
          1.52
    

SYMPTOMS

When it compiles the code sample below, Microsoft C generates one of the following warning messages. In Microsoft C/C++ versions 7.0 and later:

   warning C4756: overflow in constant arithmetic

In Microsoft C versions 6.0, 6.0a, and 6.0ax:

   warning C4056: overflow in constant arithmetic

The compiler generates the correct code; the warning is erroneous.

CAUSE

The optimizing compiler performs strength reduction for equations by removing parentheses from the equation when the resulting equation is mathematically equivalent.

The warning occurs when strength reduction creates a constant that is too large for its data type. The compiler can create such a constant because the ANSI standard does not mandate that the compiler honor parentheses as long as the resulting equation is mathematically equivalent. After the compiler performs strength reduction, the compiler cannot determine where the parentheses were and does not provide any method to suppress the warning message.

RESOLUTION

There are two methods to work around this warning message:

  • Compile the module with the fast compiler (specify /f on the compiler command line). The fast compiler does not perform any strength reduction.
  • Create a temporary variable to hold partial results of the calculation.

MORE INFORMATION

The following sample code demonstrates this warning message.

When the compiler performs strength reduction on the code below, it creates the following equation:

   result += number * 31536000L - 63072000000L;

The warning does not occur if you replace the equation with the following:

   long temp = 0L;

   temp = number - 2000L;
   result += temp * 31536000L;

Sample Code

/*
 * Compile options needed: /f- /W2
 */

long result = 0L; long number = 2010L;

void main (void)
{
   result += (number - 2000L) * 31536000L;
}


Additional reference words: 6.00 6.00a 6.00ax 7.00 8.00 8.00c
1.00 1.50 1.51 1.52
KBCategory: kbtool
KBSubcategory: kbprb
Keywords : kb16bitonly


THE INFORMATION PROVIDED IN THE MICROSOFT KNOWLEDGE BASE IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND. MICROSOFT DISCLAIMS ALL WARRANTIES, EITHER EXPRESS OR IMPLIED, INCLUDING THE WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL MICROSOFT CORPORATION OR ITS SUPPLIERS BE LIABLE FOR ANY DAMAGES WHATSOEVER INCLUDING DIRECT, INDIRECT, INCIDENTAL, CONSEQUENTIAL, LOSS OF BUSINESS PROFITS OR SPECIAL DAMAGES, EVEN IF MICROSOFT CORPORATION OR ITS SUPPLIERS HAVE BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. SOME STATES DO NOT ALLOW THE EXCLUSION OR LIMITATION OF LIABILITY FOR CONSEQUENTIAL OR INCIDENTAL DAMAGES SO THE FOREGOING LIMITATION MAY NOT APPLY.

Last reviewed: July 17, 1997
© 1998 Microsoft Corporation. All rights reserved. Terms of Use.