]> git.saurik.com Git - apple/icu.git/blobdiff - icuSources/test/cintltst/cnmdptst.c
ICU-551.51.4.tar.gz
[apple/icu.git] / icuSources / test / cintltst / cnmdptst.c
index 5847aefc1eea4c8c4809cee3cb18f2944696b9bb..8b3cbd61d245c5f14d2662cd81df209a1f0c95b9 100644 (file)
@@ -1,6 +1,6 @@
 /********************************************************************
- * COPYRIGHT: 
- * Copyright (c) 1997-2004, International Business Machines Corporation
+ * COPYRIGHT:
+ * Copyright (c) 1997-2014, International Business Machines Corporation
  * and others. All Rights Reserved.
  ********************************************************************/
 /*******************************************************************************
@@ -29,6 +29,7 @@
 #include "cnmdptst.h"
 #include "cmemory.h"
 #include "cstring.h"
+#include "ulist.h"
 
 #define CHECK(status,str) if (U_FAILURE(status)) { log_err("FAIL: %s\n", str); return; }
 
@@ -49,6 +50,8 @@ void addNumFrDepTest(TestNode** root)
   addTest(root, &TestDoubleAttribute, "tsformat/cnmdptst/TestDoubleAttribute");
   addTest(root, &TestSecondaryGrouping, "tsformat/cnmdptst/TestSecondaryGrouping");
   addTest(root, &TestCurrencyKeywords, "tsformat/cnmdptst/TestCurrencyKeywords");
+  addTest(root, &TestRounding5350, "tsformat/cnmdptst/TestRounding5350");
+  addTest(root, &TestGetKeywordValuesForLocale, "tsformat/cnmdptst/TestGetKeywordValuesForLocale");
 }
 
 /*Test Various format patterns*/
@@ -65,7 +68,7 @@ static void TestPatterns(void)
     const char* pat[]    = { "#.#", "#.", ".#", "#" };
     const char* newpat[] = { "#0.#", "#0.", "#.0", "#" };
     const char* num[]    = { "0",   "0.", ".0", "0" };
-    
+
     log_verbose("\nTesting different format patterns\n");
     pat_length = sizeof(pat) / sizeof(pat[0]);
     for (i=0; i < pat_length; ++i)
@@ -74,8 +77,8 @@ static void TestPatterns(void)
         u_uastrcpy(upat, pat[i]);
         fmt= unum_open(UNUM_IGNORE,upat, u_strlen(upat), "en_US",NULL, &status);
         if (U_FAILURE(status)) {
-            log_err("FAIL: Number format constructor failed for pattern %s\n", pat[i]);
-            continue; 
+            log_err_status(status, "FAIL: Number format constructor failed for pattern %s -> %s\n", pat[i], u_errorName(status));
+            continue;
         }
         lneed=0;
         lneed=unum_toPattern(fmt, FALSE, NULL, lneed, &status);
@@ -90,7 +93,7 @@ static void TestPatterns(void)
         u_uastrcpy(unewpat, newpat[i]);
         if(u_strcmp(unewp, unewpat) != 0)
             log_err("FAIL: Pattern  %s should be transmute to %s; %s seen instead\n", pat[i], newpat[i],  austrdup(unewp) );
-        
+
         lneed=0;
         lneed=unum_format(fmt, 0, NULL, lneed, NULL, &status);
         if(status==U_BUFFER_OVERFLOW_ERROR){
@@ -105,7 +108,7 @@ static void TestPatterns(void)
         if (u_strcmp(str, unum) != 0)
         {
             log_err("FAIL: Pattern %s should format zero as %s; %s Seen instead\n", pat[i], num[i], austrdup(str) );
-            
+
         }
         free(unewp);
         free(str);
@@ -127,7 +130,7 @@ static void TestQuotes(void)
     u_uastrcpy(pat, "a'fo''o'b#");
     fmt =unum_open(UNUM_IGNORE,pat, u_strlen(pat), "en_US",NULL, &status);
     if(U_FAILURE(status)){
-        log_err("Error in number format costruction using pattern \"a'fo''o'b#\"\n");
+        log_err_status(status, "Error in number format costruction using pattern \"a'fo''o'b#\" -> %s\n", u_errorName(status));
     }
     lneed=0;
     lneed=unum_format(fmt, 123, NULL, lneed, NULL, &status);
@@ -137,7 +140,7 @@ static void TestQuotes(void)
         unum_format(fmt, 123, str, lneed+1,  NULL, &status);
     }
     if(U_FAILURE(status) || !str) {
-        log_err("Error in formatting using unum_format(.....): %s\n", myErrorName(status) );
+        log_err_status(status, "Error in formatting using unum_format(.....): %s\n", myErrorName(status) );
         return;
     }
     log_verbose("Pattern \"%s\" \n", u_austrcpy(tempBuf, pat) );
@@ -145,15 +148,15 @@ static void TestQuotes(void)
     u_uastrcpy(res, "afo'ob123");
     if(u_strcmp(str, res) != 0)
         log_err("FAIL: Expected afo'ob123");
-    
+
     free(str);
     unum_close(fmt);
-    
-    
+
+
     u_uastrcpy(pat, "");
     u_uastrcpy(pat, "a''b#");
-    
-    
+
+
     fmt =unum_open(UNUM_IGNORE,pat, u_strlen(pat), "en_US",NULL, &status);
     if(U_FAILURE(status)){
         log_err("Error in number format costruction using pattern \"a''b#\"\n");
@@ -174,7 +177,7 @@ static void TestQuotes(void)
     u_uastrcpy(res, "a'b123");
     if(u_strcmp(str, res) != 0)
         log_err("FAIL: Expected a'b123\n");
-    
+
     free(str);
     unum_close(fmt);
 }
@@ -193,51 +196,53 @@ static void TestExponential(void)
     char tempMsgBug[256];
     double a;
     UErrorCode status = U_ZERO_ERROR;
-#ifdef OS390
-    double val[] = { 0.01234, 123456789, 1.23e75, -3.141592653e-78 };
+#if U_PLATFORM == U_PF_OS390
+    static const double val[] = { 0.01234, 123456789, 1.23e75, -3.141592653e-78 };
 #else
-    double val[] = { 0.01234, 123456789, 1.23e300, -3.141592653e-271 };
+    static const double val[] = { 0.01234, 123456789, 1.23e300, -3.141592653e-271 };
 #endif
-    const char* pat[] = { "0.####E0", "00.000E00", "##0.######E000", "0.###E0;[0.###E0]" };
-    int32_t lval[] = { 0, -1, 1, 123456789 };
-    
-    const char* valFormat[] =
+    static const char* pat[] = { "0.####E0", "00.000E00", "##0.######E000", "0.###E0;[0.###E0]" };
+    static const int32_t lval[] = { 0, -1, 1, 123456789 };
+
+    static const char* valFormat[] =
     {
         "1.234E-2", "1.2346E8", "1.23E300", "-3.1416E-271",
-            "12.340E-03", "12.346E07", "12.300E299", "-31.416E-272",
-            "12.34E-003", "123.4568E006", "1.23E300", "-314.1593E-273",
-            "1.234E-2", "1.235E8", "1.23E300", "[3.142E-271]"
+        "12.340E-03", "12.346E07", "12.300E299", "-31.416E-272",
+        "12.34E-003", "123.4568E006", "1.23E300", "-314.1593E-273",
+        "1.234E-2", "1.235E8", "1.23E300", "[3.142E-271]"
     };
-    const char* lvalFormat[] =
+    static const char* lvalFormat[] =
     {
         "0E0", "-1E0", "1E0", "1.2346E8",
-            "00.000E00", "-10.000E-01", "10.000E-01", "12.346E07",
-            "0E000", "-1E000", "1E000", "123.4568E006",
-            "0E0", "[1E0]", "1E0", "1.235E8"
+        "00.000E00", "-10.000E-01", "10.000E-01", "12.346E07",
+        "0E000", "-1E000", "1E000", "123.4568E006",
+        "0E0", "[1E0]", "1E0", "1.235E8"
     };
-    double valParse[] =
+    static const double valParse[] =
     {
-#ifdef OS390
+#if U_PLATFORM == U_PF_OS390
         0.01234, 123460000, 1.23E75, -3.1416E-78,
-            0.01234, 123460000, 1.23E75, -3.1416E-78,
-            0.01234, 123456800, 1.23E75, -3.141593E-78,
-            0.01234, 123500000, 1.23E75, -3.142E-78
+        0.01234, 123460000, 1.23E75, -3.1416E-78,
+        0.01234, 123456800, 1.23E75, -3.141593E-78,
+        0.01234, 123500000, 1.23E75, -3.142E-78
 #else
-            0.01234, 123460000, 1.23E300, -3.1416E-271,
-            0.01234, 123460000, 1.23E300, -3.1416E-271,
-            0.01234, 123456800, 1.23E300, -3.141593E-271,
-            0.01234, 123500000, 1.23E300, -3.142E-271
+        /* We define the whole IEEE 754 number in the 4th column because
+        Visual Age 7 has a bug in rounding numbers. */
+        0.01234, 123460000, 1.23E300, -3.1415999999999999E-271,
+        0.01234, 123460000, 1.23E300, -3.1415999999999999E-271,
+        0.01234, 123456800, 1.23E300, -3.1415929999999999E-271,
+        0.01234, 123500000, 1.23E300, -3.1420000000000001E-271
 #endif
     };
-    int32_t lvalParse[] =
+    static const int32_t lvalParse[] =
     {
         0, -1, 1, 123460000,
             0, -1, 1, 123460000,
             0, -1, 1, 123456800,
             0, -1, 1, 123500000
     };
-    
-    
+
+
     pat_length = sizeof(pat) / sizeof(pat[0]);
     val_length = sizeof(val) / sizeof(val[0]);
     lval_length = sizeof(lval) / sizeof(lval[0]);
@@ -248,9 +253,9 @@ static void TestExponential(void)
         upat=(UChar*)malloc(sizeof(UChar) * (strlen(pat[p])+1) );
         u_uastrcpy(upat, pat[p]);
         fmt=unum_open(UNUM_IGNORE,upat, u_strlen(upat), "en_US",NULL, &status);
-        if (U_FAILURE(status)) { 
-            log_err("FAIL: Bad status returned by Number format construction with pattern %s\n, pat[i]"); 
-            continue; 
+        if (U_FAILURE(status)) {
+            log_err_status(status, "FAIL: Bad status returned by Number format construction with pattern %s -> %s\n", pat[p], u_errorName(status));
+            continue;
         }
         lneed= u_strlen(upat) + 1;
         unum_toPattern(fmt, FALSE, pattern, lneed, &status);
@@ -258,7 +263,7 @@ static void TestExponential(void)
         for (v=0; v<val_length; ++v)
         {
             /*format*/
-            lneed=0; 
+            lneed=0;
             lneed=unum_formatDouble(fmt, val[v], NULL, lneed, NULL, &status);
             if(status==U_BUFFER_OVERFLOW_ERROR){
                 status=U_ZERO_ERROR;
@@ -268,13 +273,13 @@ static void TestExponential(void)
             if(U_FAILURE(status)) {
                 log_err("Error in formatting using unum_format(.....): %s\n", myErrorName(status) );
             }
-            
-            
-            
+
+
+
             u_uastrcpy(uvalfor, valFormat[v+ival]);
             if(u_strcmp(str, uvalfor) != 0)
                 log_verbose("FAIL: Expected %s ( %s )\n", valFormat[v+ival], u_austrcpy(tempMsgBug, uvalfor) );
-            
+
             /*parsing*/
             ppos=0;
             a=unum_parseDouble(fmt, str, u_strlen(str), &ppos, &status);
@@ -284,13 +289,13 @@ static void TestExponential(void)
             }
             else
                 log_err(" FAIL: Partial parse (  %d  chars ) ->  %e\n",  ppos, a);
-            
+
             free(str);
         }
         for (v=0; v<lval_length; ++v)
         {
             /*format*/
-            lneed=0; 
+            lneed=0;
             lneed=unum_formatDouble(fmt, lval[v], NULL, lneed, NULL, &status);
             if(status==U_BUFFER_OVERFLOW_ERROR){
                 status=U_ZERO_ERROR;
@@ -304,7 +309,7 @@ static void TestExponential(void)
             u_uastrcpy(ulvalfor, lvalFormat[v+ilval]);
             if(u_strcmp(str, ulvalfor) != 0)
                 log_err("FAIL: Expected %s ( %s )\n", valFormat[v+ilval], austrdup(ulvalfor) );
-            
+
             /*parsing*/
             ppos=0;
             a=unum_parseDouble(fmt, str, u_strlen(str), &ppos, &status);
@@ -315,9 +320,9 @@ static void TestExponential(void)
             }
             else
                 log_err(" FAIL: Partial parse (  %d  chars ) ->  %e\n",  ppos, a);
-            
+
             free(str);
-            
+
         }
         ival += val_length;
         ilval += lval_length;
@@ -339,15 +344,15 @@ static void TestCurrencySign(void)
     UChar *res=NULL;
     UErrorCode status = U_ZERO_ERROR;
     char tempBuf[256];
-    
+
     pattern=(UChar*)malloc(sizeof(UChar) * (strlen("*#,##0.00;-*#,##0.00") + 1) );
     u_uastrcpy(pattern, "*#,##0.00;-*#,##0.00");
     pattern[0]=pattern[11]=0xa4; /* insert latin-1 currency symbol */
     fmt = unum_open(UNUM_IGNORE,pattern, u_strlen(pattern), "en_US",NULL, &status);
     if(U_FAILURE(status)){
-        log_err("Error in number format construction with pattern  \"\\xA4#,##0.00;-\\xA4#,##0.00\\\" \n");
+        log_err_status(status, "Error in number format construction with pattern  \"\\xA4#,##0.00;-\\xA4#,##0.00\\\" -> %s\n", u_errorName(status));
     }
-    lneed=0; 
+    lneed=0;
     lneed=unum_formatDouble(fmt, 1234.56, NULL, lneed, NULL, &status);
     if(status==U_BUFFER_OVERFLOW_ERROR){
         status=U_ZERO_ERROR;
@@ -355,7 +360,7 @@ static void TestCurrencySign(void)
         unum_formatDouble(fmt, 1234.56, str, lneed+1, NULL, &status);
     }
     if(U_FAILURE(status)) {
-        log_err("Error in formatting using unum_format(.....): %s\n", myErrorName(status) );
+        log_err_status(status, "Error in formatting using unum_format(.....): %s\n", myErrorName(status) );
     }
     lneed=0;
     lneed=unum_toPattern(fmt, FALSE, NULL, lneed, &status);
@@ -369,15 +374,15 @@ static void TestCurrencySign(void)
     if(U_SUCCESS(status) && str) {
         res=(UChar*)malloc(sizeof(UChar) * (strlen("$1,234.56")+1) );
         u_uastrcpy(res, "$1,234.56");
-        if (u_strcmp(str, res) !=0) log_err("FAIL: Expected $1,234.56\n");
+        if (u_strcmp(str, res) !=0) log_data_err("FAIL: Expected $1,234.56\n");
     } else {
-        log_err("Error formatting\n");
+        log_err_status(status, "Error formatting -> %s\n", u_errorName(status));
     }
     free(str);
     free(res);
     free(pat);
-    
-    lneed=0; 
+
+    lneed=0;
     lneed=unum_formatDouble(fmt, -1234.56, NULL, lneed, NULL, &status);
     if(status==U_BUFFER_OVERFLOW_ERROR){
         status=U_ZERO_ERROR;
@@ -385,17 +390,17 @@ static void TestCurrencySign(void)
         unum_formatDouble(fmt, -1234.56, str, lneed+1, NULL, &status);
     }
     if(U_FAILURE(status)) {
-        log_err("Error in formatting using unum_format(.....): %s\n", myErrorName(status) );
+        log_err_status(status, "Error in formatting using unum_format(.....): %s\n", myErrorName(status) );
     }
     if(str) {
         res=(UChar*)malloc(sizeof(UChar) * (strlen("-$1,234.56")+1) );
         u_uastrcpy(res, "-$1,234.56");
-        if (u_strcmp(str, res) != 0) log_err("FAIL: Expected -$1,234.56\n");
+        if (u_strcmp(str, res) != 0) log_data_err("FAIL: Expected -$1,234.56\n");
         free(str);
         free(res);
     }
-    
-    unum_close(fmt);  
+
+    unum_close(fmt);
     free(pattern);
 }
 
@@ -411,31 +416,37 @@ static void TestCurrency(void)
     UChar res[100];
     UErrorCode status = U_ZERO_ERROR;
     const char* locale[]={"fr_CA", "de_DE_PREEURO", "fr_FR_PREEURO"};
-    const char* result[]={"1,50 $", "1,50 DM", "1,50 F"};
+    const char* result[]={"1,50\\u00a0$", "1,50\\u00a0DM", "1,50\\u00a0F"};
     log_verbose("\nTesting the number format with different currency patterns\n");
     for(i=0; i < 3; i++)
     {
         str=NULL;
         currencyFmt = unum_open(UNUM_CURRENCY, NULL,0,locale[i],NULL, &status);
+
         if(U_FAILURE(status)){
-            log_err("Error in the construction of number format with style currency:\n%s\n",
+            log_data_err("Error in the construction of number format with style currency: %s (Are you missing data?)\n",
                 myErrorName(status));
+        } else {
+            lneed=0;
+            lneed= unum_formatDouble(currencyFmt, 1.50, NULL, lneed, NULL, &status);
+            if(status==U_BUFFER_OVERFLOW_ERROR){
+                status=U_ZERO_ERROR;
+                str=(UChar*)malloc(sizeof(UChar) * (lneed+1) );
+                pos.field = 0;
+                unum_formatDouble(currencyFmt, 1.50, str, lneed+1, &pos, &status);
+            }
+
+            if(U_FAILURE(status)) {
+                log_err("Error in formatting using unum_formatDouble(.....): %s\n", myErrorName(status) );
+            } else {
+                u_unescape(result[i], res, (int32_t)strlen(result[i])+1);
+
+                if (u_strcmp(str, res) != 0){
+                    log_err("FAIL: Expected %s Got: %s for locale: %s\n", result[i], aescstrdup(str, -1), locale[i]);
+                }
+            }
         }
-        lneed=0;
-        lneed= unum_formatDouble(currencyFmt, 1.50, NULL, lneed, NULL, &status);
-        if(status==U_BUFFER_OVERFLOW_ERROR){
-            status=U_ZERO_ERROR;
-            str=(UChar*)malloc(sizeof(UChar) * (lneed+1) );
-            pos.field = 0;
-            unum_formatDouble(currencyFmt, 1.50, str, lneed+1, &pos, &status);
-        }
-        if(U_FAILURE(status)) {
-            log_err("Error in formatting using unum_formatDouble(.....): %s\n", myErrorName(status) );
-        }
-        u_charsToUChars(result[i], res, (int32_t)strlen(result[i])+1);
-        if (u_strcmp(str, res) != 0){
-            log_err("FAIL: Expected %s Got: %s for locale: %s\n", result[i], aescstrdup(str, -1), locale[i]);
-        }
+
         unum_close(currencyFmt);
         free(str);
     }
@@ -450,52 +461,58 @@ static void TestCurrencyPreEuro(void)
     int32_t lneed, i;
     UFieldPosition pos;
     UErrorCode status = U_ZERO_ERROR;
-    
+
     const char* locale[]={
-        "ca_ES_PREEURO",  "de_LU_PREEURO",  "en_IE_PREEURO",              "fi_FI_PREEURO",  "fr_LU_PREEURO",  "it_IT_PREEURO",  
-        "pt_PT_PREEURO",  "de_AT_PREEURO",  "el_GR_PREEURO",              "es_ES_PREEURO",  "fr_BE_PREEURO",  "ga_IE_PREEURO",  
-        "nl_BE_PREEURO",  "de_DE_PREEURO",  "en_BE_PREEURO",              "eu_ES_PREEURO",  "fr_FR_PREEURO",  "gl_ES_PREEURO",  
+        "ca_ES_PREEURO",  "de_LU_PREEURO",  "en_IE_PREEURO",              "fi_FI_PREEURO",  "fr_LU_PREEURO",  "it_IT_PREEURO",
+        "pt_PT_PREEURO",  "de_AT_PREEURO",  "el_GR_PREEURO",              "es_ES_PREEURO",  "fr_BE_PREEURO",  "ga_IE_PREEURO",
+        "nl_BE_PREEURO",  "de_DE_PREEURO",  "en_BE_PREEURO",              "eu_ES_PREEURO",  "fr_FR_PREEURO",  "gl_ES_PREEURO",
         "nl_NL_PREEURO",
     };
-    
+
     const char* result[]={
-        "\\u20A7 2",      "2 F",            "\\u00A31.50",                "1,50 mk",        "1,50 F",         "\\u20A4 2", 
-        "1$50 Esc.",      "\\u00F6S 1,50",  "1,50 \\u0394\\u03C1\\u03C7", "2 \\u20A7",      "1,50 FB",        "\\u00a31.50", 
-        "1,50 BF",        "1,50 DM",        "1,50 BF",                    "\\u20A7 2",      "1,50 F",         "\\u20A7 2", 
-        "fl 1,50"
+        "\\u20A7\\u00A02", "2\\u00A0F",            "IEP1.50",                      "1,50\\u00A0mk",   "2\\u00A0F",         "ITL\\u00A02",
+        "1$50\\u00A0\\u200B", "\\u00F6S\\u00A01,50",  "1,50\\u00A0\\u0394\\u03C1\\u03C7", "2\\u00A0\\u20A7", "1,50\\u00A0FB",     "IEP1.50",
+        "1,50\\u00A0BEF",   "1,50\\u00A0DM",        "1,50\\u00A0BEF",                    "\\u20A7\\u00A02", "1,50\\u00A0F",      "2\\u00A0\\u20A7",
+        "NLG\\u00A01,50"
     };
-    
+
     log_verbose("\nTesting the number format with different currency patterns\n");
     for(i=0; i < 19; i++)
     {
         char curID[256] = {0};
         uloc_canonicalize(locale[i], curID, 256, &status);
         if(U_FAILURE(status)){
-            log_err("Could not canonicalize %s. Error: %s \n", locale[i], u_errorName(status));
+            log_data_err("Could not canonicalize %s. Error: %s (Are you missing data?)\n", locale[i], u_errorName(status));
             continue;
         }
         currencyFmt = unum_open(UNUM_CURRENCY, NULL,0,curID,NULL, &status);
+
         if(U_FAILURE(status)){
-            log_err("Error in the construction of number format with style currency:\n%s\n",
+            log_data_err("Error in the construction of number format with style currency: %s (Are you missing data?)\n",
                 myErrorName(status));
+        } else {
+            lneed=0;
+            lneed= unum_formatDouble(currencyFmt, 1.50, NULL, lneed, NULL, &status);
+
+            if(status==U_BUFFER_OVERFLOW_ERROR){
+                status=U_ZERO_ERROR;
+                str=(UChar*)malloc(sizeof(UChar) * (lneed+1) );
+                pos.field = 0;
+                unum_formatDouble(currencyFmt, 1.50, str, lneed+1, &pos, &status);
+            }
+
+            if(U_FAILURE(status)) {
+                log_err("Error in formatting using unum_formatDouble(.....): %s\n", myErrorName(status) );
+            } else {
+                res=(UChar*)malloc(sizeof(UChar) * (strlen(result[i])+1) );
+                u_unescape(result[i],res,(int32_t)(strlen(result[i])+1));
+
+                if (u_strcmp(str, res) != 0){
+                    log_err("FAIL: Expected %s Got: %s for locale: %s\n", result[i],aescstrdup(str, -1),locale[i]);
+                }
+            }
         }
-        lneed=0;
-        lneed= unum_formatDouble(currencyFmt, 1.50, NULL, lneed, NULL, &status);
-        if(status==U_BUFFER_OVERFLOW_ERROR){
-            status=U_ZERO_ERROR;
-            str=(UChar*)malloc(sizeof(UChar) * (lneed+1) );
-            pos.field = 0;
-            unum_formatDouble(currencyFmt, 1.50, str, lneed+1, &pos, &status);
-        }
-        if(U_FAILURE(status)) {
-            log_err("Error in formatting using unum_formatDouble(.....): %s\n", myErrorName(status) );
-        }
-        res=(UChar*)malloc(sizeof(UChar) * (strlen(result[i])+1) );
-        u_unescape(result[i],res,(int32_t)(strlen(result[i])+1));
-        if (u_strcmp(str, res) != 0){
-            log_err("FAIL: Expected %s Got: %s for locale: %s\n", result[i],aescstrdup(str, -1),locale[i]);
-        }
-        
+
         unum_close(currencyFmt);
         free(str);
         free(res);
@@ -514,22 +531,22 @@ static void TestCurrencyObject(void)
     int32_t lneed, i;
     UFieldPosition pos;
     UErrorCode status = U_ZERO_ERROR;
-    
+
     const char* locale[]={
         "fr_FR",
-            "fr_FR",
+        "fr_FR",
     };
-    
+
     const char* currency[]={
         "",
-            "JPY",
+        "JPY",
     };
-    
+
     const char* result[]={
-        "1\\u00A0234,56 \\u20AC",
-            "1\\u00A0235 \\u00A5",
+        "1\\u00A0234,56\\u00A0\\u20AC",
+        "1\\u00A0235\\u00A0JPY",
     };
-    
+
     log_verbose("\nTesting the number format with different currency codes\n");
     for(i=0; i < 2; i++)
     {
@@ -537,45 +554,51 @@ static void TestCurrencyObject(void)
         UChar isoCode[16]={0};
         currencyFmt = unum_open(UNUM_CURRENCY, NULL,0,locale[i],NULL, &status);
         if(U_FAILURE(status)){
-            log_err("Error in the construction of number format with style currency:\n%s\n",
+            log_data_err("Error in the construction of number format with style currency: %s (Are you missing data?)\n",
                 myErrorName(status));
-        }
-        if (*currency[i]) {
-            u_uastrcpy(isoCode, currency[i]);
-            unum_setTextAttribute(currencyFmt, UNUM_CURRENCY_CODE,
-                isoCode, u_strlen(isoCode), &status);
+        } else {
+            if (*currency[i]) {
+                u_uastrcpy(isoCode, currency[i]);
+                unum_setTextAttribute(currencyFmt, UNUM_CURRENCY_CODE,
+                    isoCode, u_strlen(isoCode), &status);
+
+                if(U_FAILURE(status)) {
+                    log_err("FAIL: can't set currency code %s\n", myErrorName(status) );
+                }
+            }
+
+            unum_getTextAttribute(currencyFmt, UNUM_CURRENCY_CODE,
+                isoCode, sizeof(isoCode), &status);
+
             if(U_FAILURE(status)) {
-                log_err("FAIL: can't set currency code %s\n", myErrorName(status) );
+                log_err("FAIL: can't get currency code %s\n", myErrorName(status) );
+            }
+
+            u_UCharsToChars(isoCode,cStr,u_strlen(isoCode));
+            log_verbose("ISO code %s\n", cStr);
+            if (*currency[i] && uprv_strcmp(cStr, currency[i])) {
+                log_err("FAIL: currency should be %s, but is %s\n", currency[i], cStr);
+            }
+
+            lneed=0;
+            lneed= unum_formatDouble(currencyFmt, 1234.56, NULL, lneed, NULL, &status);
+            if(status==U_BUFFER_OVERFLOW_ERROR){
+                status=U_ZERO_ERROR;
+                str=(UChar*)malloc(sizeof(UChar) * (lneed+1) );
+                pos.field = 0;
+                unum_formatDouble(currencyFmt, 1234.56, str, lneed+1, &pos, &status);
+            }
+            if(U_FAILURE(status)) {
+                log_err("Error in formatting using unum_formatDouble(.....): %s\n", myErrorName(status) );
+            } else {
+                res=(UChar*)malloc(sizeof(UChar) * (strlen(result[i])+1) );
+                u_unescape(result[i],res, (int32_t)(strlen(result[i])+1));
+                if (u_strcmp(str, res) != 0){
+                    log_err("FAIL: Expected %s Got: %s for locale: %s\n", result[i],aescstrdup(str, -1),locale[i]);
+                }
             }
         }
-        unum_getTextAttribute(currencyFmt, UNUM_CURRENCY_CODE,
-            isoCode, sizeof(isoCode), &status);
-        if(U_FAILURE(status)) {
-            log_err("FAIL: can't get currency code %s\n", myErrorName(status) );
-        }
-        u_UCharsToChars(isoCode,cStr,u_strlen(isoCode));
-        log_verbose("ISO code %s\n", cStr);
-        if (*currency[i] && uprv_strcmp(cStr, currency[i])) {
-            log_err("FAIL: currency should be %s, but is %s\n", currency[i], cStr);
-        }
-        
-        lneed=0;
-        lneed= unum_formatDouble(currencyFmt, 1234.56, NULL, lneed, NULL, &status);
-        if(status==U_BUFFER_OVERFLOW_ERROR){
-            status=U_ZERO_ERROR;
-            str=(UChar*)malloc(sizeof(UChar) * (lneed+1) );
-            pos.field = 0;
-            unum_formatDouble(currencyFmt, 1234.56, str, lneed+1, &pos, &status);
-        }
-        if(U_FAILURE(status)) {
-            log_err("Error in formatting using unum_formatDouble(.....): %s\n", myErrorName(status) );
-        }
-        res=(UChar*)malloc(sizeof(UChar) * (strlen(result[i])+1) );
-        u_unescape(result[i],res, (int32_t)(strlen(result[i])+1));
-        if (u_strcmp(str, res) != 0){
-            log_err("FAIL: Expected %s Got: %s for locale: %s\n", result[i],aescstrdup(str, -1),locale[i]);
-        }
-        
+
         unum_close(currencyFmt);
         free(str);
         free(res);
@@ -589,25 +612,28 @@ static void TestRounding487(void)
 {
     UNumberFormat *nnf;
     UErrorCode status = U_ZERO_ERROR;
-    /* this is supposed to open default date format, but later on it treats it like it is "en_US" 
+    /* this is supposed to open default date format, but later on it treats it like it is "en_US"
      - very bad if you try to run the tests on machine where default locale is NOT "en_US" */
     /* nnf = unum_open(UNUM_DEFAULT, NULL, &status); */
     nnf = unum_open(UNUM_DEFAULT, NULL,0,"en_US",NULL, &status);
+
     if(U_FAILURE(status)){
-        log_err("FAIL: failure in the construction of number format: %s\n", myErrorName(status));
+        log_data_err("FAIL: failure in the construction of number format: %s (Are you missing data?)\n", myErrorName(status));
+    } else {
+        roundingTest(nnf, 0.00159999, 4, "0.0016");
+        roundingTest(nnf, 0.00995, 4, "0.01");
+
+        roundingTest(nnf, 12.3995, 3, "12.4");
+
+        roundingTest(nnf, 12.4999, 0, "12");
+        roundingTest(nnf, - 19.5, 0, "-20");
     }
-    roundingTest(nnf, 0.00159999, 4, "0.0016");
-    roundingTest(nnf, 0.00995, 4, "0.01");
-    
-    roundingTest(nnf, 12.3995, 3, "12.4");
-    
-    roundingTest(nnf, 12.4999, 0, "12");
-    roundingTest(nnf, - 19.5, 0, "-20");
+
     unum_close(nnf);
 }
+
 /*-------------------------------------*/
+
 static void roundingTest(UNumberFormat* nf, double x, int32_t maxFractionDigits, const char* expected)
 {
     UChar *out = NULL;
@@ -641,7 +667,7 @@ static void roundingTest(UNumberFormat* nf, double x, int32_t maxFractionDigits,
 }
 
 /*
- * Testing unum_getDoubleAttribute and  unum_setDoubleAttribute() 
+ * Testing unum_getDoubleAttribute and  unum_setDoubleAttribute()
  */
 static void TestDoubleAttribute(void)
 {
@@ -652,19 +678,26 @@ static void TestDoubleAttribute(void)
     UNumberFormatAttribute attr;
     UNumberFormatStyle style= UNUM_DEFAULT;
     UNumberFormat *def;
-    def=unum_open(style, NULL,0,NULL,NULL, &status);
+
     log_verbose("\nTesting get and set DoubleAttributes\n");
-    attr=UNUM_ROUNDING_INCREMENT;
-    dvalue=unum_getDoubleAttribute(def, attr);
-    for (i = 0; i<9 ; i++)
-    {
-        dvalue = mydata[i]; 
-        unum_setDoubleAttribute(def, attr, dvalue);
-        if(unum_getDoubleAttribute(def,attr)!=mydata[i])
-            log_err("Fail: error in setting and getting double attributes for UNUM_ROUNDING_INCREMENT\n");
-        else
-            log_verbose("Pass: setting and getting double attributes for UNUM_ROUNDING_INCREMENT works fine\n");
+    def=unum_open(style, NULL,0,NULL,NULL, &status);
+
+    if (U_FAILURE(status)) {
+        log_data_err("Fail: error creating a default number formatter -> %s (Are you missing data?)\n", u_errorName(status));
+    } else {
+        attr=UNUM_ROUNDING_INCREMENT;
+        dvalue=unum_getDoubleAttribute(def, attr);
+        for (i = 0; i<9 ; i++)
+        {
+            dvalue = mydata[i];
+            unum_setDoubleAttribute(def, attr, dvalue);
+            if(unum_getDoubleAttribute(def,attr)!=mydata[i])
+                log_err("Fail: error in setting and getting double attributes for UNUM_ROUNDING_INCREMENT\n");
+            else
+                log_verbose("Pass: setting and getting double attributes for UNUM_ROUNDING_INCREMENT works fine\n");
+        }
     }
+
     unum_close(def);
 }
 
@@ -685,7 +718,10 @@ static void TestSecondaryGrouping(void) {
 
     u_uastrcpy(buffer, "#,##,###");
     f = unum_open(UNUM_IGNORE,buffer, -1, "en_US",NULL, &status);
-    CHECK(status, "DecimalFormat ct");
+    if (U_FAILURE(status)) {
+        log_data_err("Error DecimalFormat ct -> %s (Are you missing data?)\n", u_errorName(status));
+        return;
+    }
 
     pos.field = 0;
     unum_format(f, (int32_t)123456789L, resultBuffer, 512 , &pos, &status);
@@ -760,14 +796,14 @@ static void TestSecondaryGrouping(void) {
     }
     if (!ok) {
         log_err("FAIL  Expected %s x hi_IN -> \"1,87,65,43,210\" (with Hindi digits), got %s\n", "1876543210L", resultBuffer);
-    } 
+    }
     unum_close(f);
     unum_close(us);
 }
 
 static void TestCurrencyKeywords(void)
 {
-    static const char *currencies[] = { 
+    static const char * const currencies[] = {
         "ADD", "ADP", "AED", "AFA", "AFN", "AIF", "ALK", "ALL", "ALV", "ALX", "AMD",
         "ANG", "AOA", "AOK", "AON", "AOR", "AOS", "ARA", "ARM", "ARP", "ARS", "ATS",
         "AUD", "AUP", "AWG", "AZM", "BAD", "BAM", "BAN", "BBD", "BDT", "BEC", "BEF",
@@ -776,35 +812,35 @@ static void TestCurrencyKeywords(void)
         "BSD", "BSP", "BTN", "BTR", "BUK", "BUR", "BWP", "BYB", "BYL", "BYR", "BZD",
         "BZH", "CAD", "CDF", "CDG", "CDL", "CFF", "CHF", "CKD", "CLC", "CLE", "CLF",
         "CLP", "CMF", "CNP", "CNX", "CNY", "COB", "COF", "COP", "CRC", "CSC", "CSK",
-        "CUP", "CUX", "CVE", "CWG", "CYP", "CZK", "DDM", "DEM", "DES", "DJF", "DKK", 
-        "DOP", "DZD", "DZF", "DZG", "ECS", "ECV", "EEK", "EGP", "ERN", "ESP", "ETB", 
-        "ETD", "EUR", "FIM", "FIN", "FJD", "FJP", "FKP", "FOK", "FRF", "FRG", "GAF", 
-        "GBP", "GEK", "GEL", "GHC", "GHO", "GHP", "GHR", "GIP", "GLK", "GMD", "GMP", 
-        "GNF", "GNI", "GNS", "GPF", "GQE", "GQF", "GQP", "GRD", "GRN", "GTQ", "GUF", 
-        "GWE", "GWM", "GWP", "GYD", "HKD", "HNL", "HRD", "HRK", "HTG", "HUF", "IBP", 
-        "IDG", "IDJ", "IDN", "IDR", "IEP", "ILL", "ILP", "ILS", "IMP", "INR", "IQD", 
-        "IRR", "ISK", "ITL", "JEP", "JMD", "JMP", "JOD", "JPY", "KES", "KGS", "KHO", 
-        "KHR", "KID", "KMF", "KPP", "KPW", "KRH", "KRO", "KRW", "KWD", "KYD", "KZR", 
-        "KZT", "LAK", "LBP", "LIF", "LKR", "LNR", "LRD", "LSL", "LTL", "LTT", "LUF", 
-        "LVL", "LVR", "LYB", "LYD", "LYP", "MAD", "MAF", "MCF", "MCG", "MDC", "MDL", 
-        "MDR", "MGA", "MGF", "MHD", "MKD", "MKN", "MLF", "MMK", "MMX", "MNT", "MOP", 
-        "MQF", "MRO", "MTL", "MTP", "MUR", "MVP", "MVR", "MWK", "MWP", "MXN", "MXP", 
-        "MXV", "MYR", "MZE", "MZM", "NAD", "NCF", "NGN", "NGP", "NHF", "NIC", "NIG", 
-        "NIO", "NLG", "NOK", "NPR", "NZD", "NZP", "OMR", "OMS", "PAB", "PDK", "PDN", 
-        "PDR", "PEI", "PEN", "PES", "PGK", "PHP", "PKR", "PLN", "PLX", "PLZ", "PSP", 
-        "PTC", "PTE", "PYG", "QAR", "REF", "ROL", "RON", "RUB", "RUR", "RWF", "SAR", 
-        "SAS", "SBD", "SCR", "SDD", "SDP", "SEK", "SGD", "SHP", "SIB", "SIT", "SKK", 
-        "SLL", "SML", "SOS", "SQS", "SRG", "SSP", "STD", "STE", "SUN", "SUR", "SVC", 
-        "SYP", "SZL", "TCC", "TDF", "THB", "TJR", "TJS", "TMM", "TND", "TOP", "TOS", 
-        "TPE", "TPP", "TRL", "TTD", "TTO", "TVD", "TWD", "TZS", "UAH", "UAK", "UGS", 
-        "UGX", "USD", "USN", "USS", "UYF", "UYP", "UYU", "UZC", "UZS", "VAL", "VDD", 
-        "VDN", "VDP", "VEB", "VGD", "VND", "VNN", "VNR", "VNS", "VUV", "WSP", "WST", 
-        "XAD", "XAF", "XAM", "XAU", "XBA", "XBB", "XBC", "XBD", "XCD", "XCF", "XDR", 
-        "XEF", "XEU", "XFO", "XFU", "XID", "XMF", "XNF", "XOF", "XPF", "XPS", "XSS", 
-        "XTR", "YDD", "YEI", "YER", "YUD", "YUF", "YUG", "YUM", "YUN", "YUO", "YUR", 
+        "CUP", "CUX", "CVE", "CWG", "CYP", "CZK", "DDM", "DEM", "DES", "DJF", "DKK",
+        "DOP", "DZD", "DZF", "DZG", "ECS", "ECV", "EEK", "EGP", "ERN", "ESP", "ETB",
+        "ETD", "EUR", "FIM", "FIN", "FJD", "FJP", "FKP", "FOK", "FRF", "FRG", "GAF",
+        "GBP", "GEK", "GEL", "GHC", "GHO", "GHP", "GHR", "GIP", "GLK", "GMD", "GMP",
+        "GNF", "GNI", "GNS", "GPF", "GQE", "GQF", "GQP", "GRD", "GRN", "GTQ", "GUF",
+        "GWE", "GWM", "GWP", "GYD", "HKD", "HNL", "HRD", "HRK", "HTG", "HUF", "IBP",
+        "IDG", "IDJ", "IDN", "IDR", "IEP", "ILL", "ILP", "ILS", "IMP", "INR", "IQD",
+        "IRR", "ISK", "ITL", "JEP", "JMD", "JMP", "JOD", "JPY", "KES", "KGS", "KHO",
+        "KHR", "KID", "KMF", "KPP", "KPW", "KRH", "KRO", "KRW", "KWD", "KYD", "KZR",
+        "KZT", "LAK", "LBP", "LIF", "LKR", "LNR", "LRD", "LSL", "LTL", "LTT", "LUF",
+        "LVL", "LVR", "LYB", "LYD", "LYP", "MAD", "MAF", "MCF", "MCG", "MDC", "MDL",
+        "MDR", "MGA", "MGF", "MHD", "MKD", "MKN", "MLF", "MMK", "MMX", "MNT", "MOP",
+        "MQF", "MRO", "MTL", "MTP", "MUR", "MVP", "MVR", "MWK", "MWP", "MXN", "MXP",
+        "MXV", "MYR", "MZE", "MZM", "NAD", "NCF", "NGN", "NGP", "NHF", "NIC", "NIG",
+        "NIO", "NLG", "NOK", "NPR", "NZD", "NZP", "OMR", "OMS", "PAB", "PDK", "PDN",
+        "PDR", "PEI", "PEN", "PES", "PGK", "PHP", "PKR", "PLN", "PLX", "PLZ", "PSP",
+        "PTC", "PTE", "PYG", "QAR", "REF", "ROL", "RON", "RUB", "RUR", "RWF", "SAR",
+        "SAS", "SBD", "SCR", "SDD", "SDP", "SEK", "SGD", "SHP", "SIB", "SIT", "SKK",
+        "SLL", "SML", "SOS", "SQS", "SRG", "SSP", "STD", "STE", "SUN", "SUR", "SVC",
+        "SYP", "SZL", "TCC", "TDF", "THB", "TJR", "TJS", "TMM", "TND", "TOP", "TOS",
+        "TPE", "TPP", "TRL", "TTD", "TTO", "TVD", "TWD", "TZS", "UAH", "UAK", "UGS",
+        "UGX", "USD", "USN", "USS", "UYF", "UYP", "UYU", "UZC", "UZS", "VAL", "VDD",
+        "VDN", "VDP", "VEB", "VGD", "VND", "VNN", "VNR", "VNS", "VUV", "WSP", "WST",
+        "XAD", "XAF", "XAM", "XAU", "XBA", "XBB", "XBC", "XBD", "XCD", "XCF", "XDR",
+        "XEF", "XEU", "XFO", "XFU", "XID", "XMF", "XNF", "XOF", "XPF", "XPS", "XSS",
+        "XTR", "YDD", "YEI", "YER", "YUD", "YUF", "YUG", "YUM", "YUN", "YUO", "YUR",
         "ZAL", "ZAP", "ZAR", "ZMK", "ZMP", "ZRN", "ZRZ", "ZWD"
     };
-    
+
     UErrorCode status = U_ZERO_ERROR;
     int32_t i = 0, j = 0;
     int32_t noLocales = uloc_countAvailable();
@@ -812,8 +848,8 @@ static void TestCurrencyKeywords(void)
     char currLoc[256];
     UChar result[4];
     UChar currBuffer[256];
-    
-    
+
+
     for(i = 0; i < noLocales; i++) {
         strcpy(currLoc, uloc_getAvailable(i));
         for(j = 0; j < sizeof(currencies)/sizeof(currencies[0]); j++) {
@@ -827,7 +863,204 @@ static void TestCurrencyKeywords(void)
                 log_err("Didn't get the right currency for %s\n", locale);
             }
         }
+
+    }
+}
+
+static void TestGetKeywordValuesForLocale(void) {
+#define PREFERRED_SIZE 12
+#define MAX_NUMBER_OF_KEYWORDS 4
+    const char *PREFERRED[PREFERRED_SIZE][MAX_NUMBER_OF_KEYWORDS] = {
+            { "root",               "USD", "USN", NULL },
+            { "und",                "USD", "USN", NULL },
+ /*           { "und_ZZ",             "USD", NULL, NULL },  -- temporarily remove as this locale now has 15 entries */
+            { "en_US",              "USD", "USN", NULL },
+            { "en_029",             "USD", "USN", NULL },
+            { "en_TH",              "THB", NULL, NULL },
+            { "de",                 "EUR", NULL, NULL },
+            { "de_DE",              "EUR", NULL, NULL },
+            { "ar",                 "EGP", NULL, NULL },
+            { "ar_PS",              "ILS", "JOD", NULL },
+            { "en@currency=CAD",    "USD", "USN", NULL },
+            { "fr@currency=zzz",    "EUR", NULL, NULL },
+            { "de_DE@currency=DEM", "EUR", NULL, NULL },
+    };
+    const int32_t EXPECTED_SIZE[PREFERRED_SIZE] = {
+            2, 2, 2, 2, 1, 1, 1, 1, 2, 2, 1, 1
+    };
+    UErrorCode status = U_ZERO_ERROR;
+    int32_t i, j, size;
+    UEnumeration *pref, *all;
+    const char *loc = NULL;
+    UBool matchPref, matchAll;
+    const char *value = NULL;
+    int32_t valueLength = 0;
+    
+    UList *ALLList = NULL;
+    
+    UEnumeration *ALL = ucurr_getKeywordValuesForLocale("currency", uloc_getDefault(), FALSE, &status);
+    if (ALL == NULL) {
+        log_err_status(status, "ERROR getting keyword value for default locale. -> %s\n", u_errorName(status));
+        return;
+    }
+    
+    for (i = 0; i < PREFERRED_SIZE; i++) {
+        pref = NULL;
+        all = NULL;
+        loc = PREFERRED[i][0];
+        pref = ucurr_getKeywordValuesForLocale("currency", loc, TRUE, &status);
+        matchPref = FALSE;
+        matchAll = FALSE;
+        
+        size = uenum_count(pref, &status);
+        
+        if (size == EXPECTED_SIZE[i]) {
+            matchPref = TRUE;
+            for (j = 0; j < size; j++) {
+                if ((value = uenum_next(pref, &valueLength, &status)) != NULL && U_SUCCESS(status)) {
+                    if (uprv_strcmp(value, PREFERRED[i][j+1]) != 0) {
+                        log_err("ERROR: locale %s got keywords #%d %s expected %s\n", loc, j, value, PREFERRED[i][j+1]);
+
+                        matchPref = FALSE;
+                        break;
+                    }
+                } else {
+                    matchPref = FALSE;
+                    log_err("ERROR getting keyword value for locale \"%s\"\n", loc);
+                    break;
+                }
+            }
+        } else {
+            log_err("FAIL: size of locale \"%s\" %d does not match expected size %d\n", loc, size, EXPECTED_SIZE[i]);
+        }
+        
+        if (!matchPref) {
+            log_err("FAIL: Preferred values for locale \"%s\" does not match expected.\n", loc);
+            break;
+        }
+        uenum_close(pref);
+        
+        all = ucurr_getKeywordValuesForLocale("currency", loc, FALSE, &status);
         
+        size = uenum_count(all, &status);
+        
+        if (U_SUCCESS(status) && size == uenum_count(ALL, &status)) {
+            matchAll = TRUE;
+            ALLList = ulist_getListFromEnum(ALL);
+            for (j = 0; j < size; j++) {
+                if ((value = uenum_next(all, &valueLength, &status)) != NULL && U_SUCCESS(status)) {
+                    if (!ulist_containsString(ALLList, value, uprv_strlen(value))) {
+                        log_err("Locale %s have %s not in ALL\n", loc, value);
+                        matchAll = FALSE;
+                        break;
+                    }
+                } else {
+                    matchAll = FALSE;
+                    log_err("ERROR getting \"all\" keyword value for locale \"%s\"\n", loc);
+                    break;
+                }
+            }
+           if (!matchAll) {
+            log_err("FAIL: All values for locale \"%s\" does not match expected.\n", loc);
+           }
+        } else {
+            if(U_FAILURE(status)) {
+               log_err("ERROR: %s\n", u_errorName(status));
+            } else if(size!=uenum_count(ALL, &status)) {
+               log_err("ERROR: got size of %d, wanted %d\n", size, uenum_count(ALL, &status));
+            }
+        }
+        
+        uenum_close(all);
+    }
+    
+    uenum_close(ALL);
+    
+}
+
+/**
+ * Test proper handling of rounding modes.
+ */
+static void TestRounding5350(void)
+{
+    UNumberFormat *nnf;
+    UErrorCode status = U_ZERO_ERROR;
+    /* this is supposed to open default date format, but later on it treats it like it is "en_US"
+     - very bad if you try to run the tests on machine where default locale is NOT "en_US" */
+    /* nnf = unum_open(UNUM_DEFAULT, NULL, &status); */
+    nnf = unum_open(UNUM_DEFAULT, NULL,0,"en_US",NULL, &status);
+
+    if(U_FAILURE(status)){
+        log_data_err("FAIL: failure in the construction of number format: %s (Are you missing data?)\n", myErrorName(status));
+        return;
+    }
+
+    unum_setAttribute(nnf, UNUM_MAX_FRACTION_DIGITS, 2);
+    roundingTest2(nnf, -0.125, UNUM_ROUND_CEILING, "-0.12");
+    roundingTest2(nnf, -0.125, UNUM_ROUND_FLOOR, "-0.13");
+    roundingTest2(nnf, -0.125, UNUM_ROUND_DOWN, "-0.12");
+    roundingTest2(nnf, -0.125, UNUM_ROUND_UP, "-0.13");
+    roundingTest2(nnf, 0.125, UNUM_FOUND_HALFEVEN, "0.12");
+    roundingTest2(nnf, 0.135, UNUM_ROUND_HALFDOWN, "0.13");
+    roundingTest2(nnf, 0.125, UNUM_ROUND_HALFUP, "0.13");
+    roundingTest2(nnf, 0.135, UNUM_FOUND_HALFEVEN, "0.14");
+    /* The following are exactly represented, and shouldn't round */
+    roundingTest2(nnf, 1.00, UNUM_ROUND_UP, "1");
+    roundingTest2(nnf, 24.25, UNUM_ROUND_UP, "24.25");
+    roundingTest2(nnf, 24.25, UNUM_ROUND_CEILING, "24.25");
+    roundingTest2(nnf, -24.25, UNUM_ROUND_UP, "-24.25");
+
+    /* Differences pretty far out there */
+    roundingTest2(nnf, 1.0000001, UNUM_ROUND_CEILING, "1.01");
+    roundingTest2(nnf, 1.0000001, UNUM_ROUND_FLOOR, "1");
+    roundingTest2(nnf, 1.0000001, UNUM_ROUND_DOWN, "1");
+    roundingTest2(nnf, 1.0000001, UNUM_ROUND_UP, "1.01");
+    roundingTest2(nnf, 1.0000001, UNUM_FOUND_HALFEVEN, "1");
+    roundingTest2(nnf, 1.0000001, UNUM_ROUND_HALFDOWN, "1");
+    roundingTest2(nnf, 1.0000001, UNUM_ROUND_HALFUP, "1");
+
+    roundingTest2(nnf, -1.0000001, UNUM_ROUND_CEILING, "-1");
+    roundingTest2(nnf, -1.0000001, UNUM_ROUND_FLOOR, "-1.01");
+    roundingTest2(nnf, -1.0000001, UNUM_ROUND_DOWN, "-1");
+    roundingTest2(nnf, -1.0000001, UNUM_ROUND_UP, "-1.01");
+    roundingTest2(nnf, -1.0000001, UNUM_FOUND_HALFEVEN, "-1");
+    roundingTest2(nnf, -1.0000001, UNUM_ROUND_HALFDOWN, "-1");
+    roundingTest2(nnf, -1.0000001, UNUM_ROUND_HALFUP, "-1");
+
+    unum_close(nnf);
+}
+
+/*-------------------------------------*/
+
+static void roundingTest2(UNumberFormat* nf, double x, int32_t roundingMode, const char* expected)
+{
+    UChar *out = NULL;
+    UChar *res;
+    UFieldPosition pos;
+    UErrorCode status;
+    int32_t lneed;
+    status=U_ZERO_ERROR;
+    unum_setAttribute(nf, UNUM_ROUNDING_MODE, roundingMode);
+    lneed=0;
+    lneed=unum_formatDouble(nf, x, NULL, lneed, NULL, &status);
+    if(status==U_BUFFER_OVERFLOW_ERROR){
+        status=U_ZERO_ERROR;
+        out=(UChar*)malloc(sizeof(UChar) * (lneed+1) );
+        pos.field=0;
+        unum_formatDouble(nf, x, out, lneed+1, &pos, &status);
+    }
+    if(U_FAILURE(status)) {
+        log_err("Error in formatting using unum_formatDouble(.....): %s\n", myErrorName(status) );
+    }
+    /*Need to use log_verbose here. Problem with the float*/
+    /*printf("%f format with %d fraction digits to %s\n", x, maxFractionDigits, austrdup(out) );*/
+    res=(UChar*)malloc(sizeof(UChar) * (strlen(expected)+1) );
+    u_uastrcpy(res, expected);
+    if (u_strcmp(out, res) != 0)
+        log_err("FAIL: Expected: \"%s\"  Got: \"%s\"\n", expected, austrdup(out) );
+    free(res);
+    if(out != NULL) {
+        free(out);
     }
 }