VC12 pollutes the floating point stack when casting Infinity/NaN to unsigned long - by d.major

Status : 

  Duplicate<br /><br />
		This item appears to be a duplicate of another existing Connect or internal item.<br /><br />
		A more detailed explanation for the resolution of this particular item may have been provided in the comments section.


5
0
Sign in
to vote
ID 806362 Comments
Status Closed Workarounds
Type Bug Repros 3
Opened 10/23/2013 2:19:31 PM
Access Restriction Public

Description

When C++ code casts a double to unsigned long, VC12 generates a call to library function _dtoui3. If the double is infinite or NaN, the _dtoui3 function performs an unbalanced push onto the processor's floating point stack. If this happens eight times, the floating point stack becomes completely full, and subsequent floating point stack operations may fail. This is a regression from previous versions of Visual Studio.

The sample program performs some operations in a loop eight times. It is expected that all of these operations return the same result every time they are called. However, by the eighth iteration, the floating point stack is depleted, and DoSomeMath has unexpected behavior. This is a contrived sample, but it is based on code from a real application.

Expected result:

CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42

Actual result:

CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: 42
CastToULong: 0  DoSomeMath: -2147483648

------------------------------------------------------------------------------

#include <stdio.h>
#include <math.h>

__declspec(noinline) void CastToULong(double d)
{
    unsigned long ul = static_cast<unsigned long>(d);
    printf("CastToULong: %u\t", ul);
}

__declspec(noinline) void DoSomeMath(int x)
{
    double d = ceil(x * 0.0034);
    int n = static_cast<int>(d);
    printf("DoSomeMath: %d\n", n);
}

int main(int argc, char* argv[])
{
    for (int i = 0; i < 8; i++) {
        CastToULong(INFINITY);
        DoSomeMath(12345);
    }
    return 0;
}
Sign in to post a comment.
Posted by Bruce Dawson on 5/16/2014 at 3:06 PM
A better link to the duplicate bug is https://connect.microsoft.com/VisualStudio/feedback/details/808199 -- I was able to create this from the number supplied below. Thanks for that.

I have confirmed that this bug is fixed in VS 2013 Update 2.
Posted by Charles Fu on 1/13/2014 at 11:13 AM
This is a duplicate of https://connectadmin/Feedback/ConnectTab.aspx?FeedbackID=808199

We are aiming to ship the fix in next VS Update (Spring). In the meantime, I attached a private file ftol3.obj with the fix (The file might take several minutes or hours to appear).

Sorry for the bug.

Charles Fu
Visual Studio C++ Team.
Posted by Bruce Dawson on 1/11/2014 at 9:19 PM
This bug also exists in VS 2013. It looks like it will block us from switching from VS 2010.

I notice that the bug has been closed as a duplicate. Unfortunately there is no indication of what bug it is a duplicate and there is no apparent route to getting further feedback on this bug.
Posted by d.major on 10/28/2013 at 7:53 PM
It has been pointed out to me that casting infinity to uint is undefined in C++11. Perhaps the compiler's behavior here is technically not incorrect, but still, leaving an unbalanced stack is pretty destructive! Please consider this bug from the compatibility perspective at least.
Posted by Macy [MSFT] on 10/23/2013 at 9:29 PM
Thanks for your feedback.

We are rerouting this issue to the appropriate group within the Visual Studio Product Team for triage and resolution. These specialized experts will follow-up with your issue.
Posted by Macy [MSFT] on 10/23/2013 at 2:51 PM
Thank you for your feedback, we are currently reviewing the issue you have submitted. If this issue is urgent, please contact support directly(http://support.microsoft.com)