[cfe-commits] [libcxx] r126504 - in /libcxx/trunk: include/locale test/localization/locale.categories/category.numeric/locale.num.get/facet.num.get.members/test_min_max.pass.cpp

Howard Hinnant hhinnant at apple.com
Fri Feb 25 11:52:42 PST 2011


Author: hhinnant
Date: Fri Feb 25 13:52:41 2011
New Revision: 126504

URL: http://llvm.org/viewvc/llvm-project?rev=126504&view=rev
Log:
http://llvm.org/bugs/show_bug.cgi?id=9326

Added:
    libcxx/trunk/test/localization/locale.categories/category.numeric/locale.num.get/facet.num.get.members/test_min_max.pass.cpp
Modified:
    libcxx/trunk/include/locale

Modified: libcxx/trunk/include/locale
URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/include/locale?rev=126504&r1=126503&r2=126504&view=diff
==============================================================================
--- libcxx/trunk/include/locale (original)
+++ libcxx/trunk/include/locale Fri Feb 25 13:52:41 2011
@@ -733,22 +733,27 @@
 {
     if (__a != __a_end)
     {
+        int __save_errno = errno;
+        errno = 0;
         char *__p2;
         long long __ll = strtoll_l(__a, &__p2, __base, 0);
+        int __current_errno = errno;
+        if (__current_errno == 0)
+            errno = __save_errno;
         if (__p2 != __a_end)
         {
             __err = ios_base::failbit;
             return 0;
         }
-        else if (__ll > numeric_limits<_Tp>::max())
+        else if (__current_errno == ERANGE         ||
+                 __ll < numeric_limits<_Tp>::min() ||
+                 numeric_limits<_Tp>::max() < __ll)
         {
             __err = ios_base::failbit;
-            return numeric_limits<_Tp>::max();
-        }
-        else if (__ll < numeric_limits<_Tp>::min())
-        {
-            __err = ios_base::failbit;
-            return numeric_limits<_Tp>::min();
+            if (__ll > 0)
+                return numeric_limits<_Tp>::max();
+            else
+                return numeric_limits<_Tp>::min();
         }
         return static_cast<_Tp>(__ll);
     }
@@ -763,14 +768,25 @@
 {
     if (__a != __a_end)
     {
+        if (*__a == '-')
+        {
+            __err = ios_base::failbit;
+            return 0;
+        }
+        int __save_errno = errno;
+        errno = 0;
         char *__p2;
         unsigned long long __ll = strtoull_l(__a, &__p2, __base, 0);
+        int __current_errno = errno;
+        if (__current_errno == 0)
+            errno = __save_errno;
         if (__p2 != __a_end)
         {
             __err = ios_base::failbit;
             return 0;
         }
-        else if (__ll > numeric_limits<_Tp>::max())
+        else if (__current_errno == ERANGE ||
+                 numeric_limits<_Tp>::max() < __ll)
         {
             __err = ios_base::failbit;
             return numeric_limits<_Tp>::max();

Added: libcxx/trunk/test/localization/locale.categories/category.numeric/locale.num.get/facet.num.get.members/test_min_max.pass.cpp
URL: http://llvm.org/viewvc/llvm-project/libcxx/trunk/test/localization/locale.categories/category.numeric/locale.num.get/facet.num.get.members/test_min_max.pass.cpp?rev=126504&view=auto
==============================================================================
--- libcxx/trunk/test/localization/locale.categories/category.numeric/locale.num.get/facet.num.get.members/test_min_max.pass.cpp (added)
+++ libcxx/trunk/test/localization/locale.categories/category.numeric/locale.num.get/facet.num.get.members/test_min_max.pass.cpp Fri Feb 25 13:52:41 2011
@@ -0,0 +1,53 @@
+#include <limits>
+#include <sstream>
+#include <iostream>
+#include <cassert>
+#include <iostream>
+
+using namespace std;
+
+template<typename T>
+void check_limits()
+{
+    T minv = numeric_limits<T>::min();
+    T maxv = numeric_limits<T>::max();
+
+    ostringstream miniss, maxiss;
+    assert(miniss << minv);
+    assert(maxiss << maxv);
+    std::string mins = miniss.str();
+    std::string maxs = maxiss.str(); 
+
+    istringstream maxoss(maxs), minoss(mins);
+
+    T new_minv, new_maxv;
+    assert(maxoss >> new_maxv);
+    assert(minoss >> new_minv);
+ 
+    assert(new_minv == minv);
+    assert(new_maxv == maxv);
+
+    if(mins == "0")
+        mins = "-1";
+    else
+        mins[mins.size() - 1]++;
+    
+    maxs[maxs.size() - 1]++;
+
+    istringstream maxoss2(maxs), minoss2(mins);
+    
+    assert(! (maxoss2 >> new_maxv));
+    assert(! (minoss2 >> new_minv));
+}
+
+int main(void)
+{
+    check_limits<short>();
+    check_limits<unsigned short>();
+    check_limits<int>();
+    check_limits<unsigned int>();
+    check_limits<long>();
+    check_limits<unsigned long>();
+    check_limits<long long>();
+    check_limits<unsigned long long>();
+}





More information about the cfe-commits mailing list