Home | History | Annotate | Download | only in cintltst
      1 /********************************************************************
      2  * COPYRIGHT:
      3  * Copyright (c) 2001-2009, International Business Machines Corporation and
      4  * others. All Rights Reserved.
      5  ********************************************************************/
      6 /********************************************************************************
      7 *
      8 * File custrtrn.C
      9 *
     10 * Modification History:
     11 *        Name                     Description
     12 *        Ram                      String transformations test
     13 *********************************************************************************
     14 */
     15 /****************************************************************************/
     16 
     17 
     18 #include <stdlib.h>
     19 #include <stdio.h>
     20 #include "unicode/utypes.h"
     21 #include "unicode/ustring.h"
     22 #include "unicode/ures.h"
     23 #include "ustr_imp.h"
     24 #include "cintltst.h"
     25 #include "cmemory.h"
     26 #include "cstring.h"
     27 #include "cwchar.h"
     28 
     29 #define LENGTHOF(array) (int32_t)(sizeof(array)/sizeof((array)[0]))
     30 
     31 void addUCharTransformTest(TestNode** root);
     32 
     33 static void Test_strToUTF32(void);
     34 static void Test_strToUTF32_surrogates(void);
     35 static void Test_strFromUTF32(void);
     36 static void Test_strFromUTF32_surrogates(void);
     37 static void Test_UChar_UTF8_API(void);
     38 static void Test_FromUTF8(void);
     39 static void Test_FromUTF8Lenient(void);
     40 static void Test_UChar_WCHART_API(void);
     41 static void Test_widestrs(void);
     42 static void Test_WCHART_LongString(void);
     43 
     44 void
     45 addUCharTransformTest(TestNode** root)
     46 {
     47    addTest(root, &Test_strToUTF32, "custrtrn/Test_strToUTF32");
     48    addTest(root, &Test_strToUTF32_surrogates, "custrtrn/Test_strToUTF32_surrogates");
     49    addTest(root, &Test_strFromUTF32, "custrtrn/Test_strFromUTF32");
     50    addTest(root, &Test_strFromUTF32_surrogates, "custrtrn/Test_strFromUTF32_surrogates");
     51    addTest(root, &Test_UChar_UTF8_API, "custrtrn/Test_UChar_UTF8_API");
     52    addTest(root, &Test_FromUTF8, "custrtrn/Test_FromUTF8");
     53    addTest(root, &Test_FromUTF8Lenient, "custrtrn/Test_FromUTF8Lenient");
     54    addTest(root, &Test_UChar_WCHART_API,  "custrtrn/Test_UChar_WCHART_API");
     55    addTest(root, &Test_widestrs,  "custrtrn/Test_widestrs");
     56    addTest(root, &Test_WCHART_LongString, "custrtrn/Test_WCHART_LongString");
     57 }
     58 
     59 static const UChar32 src32[]={
     60     0x00A8, 0x3003, 0x3005, 0x2015, 0xFF5E, 0x2016, 0x2026, 0x2018, 0x000D, 0x000A,
     61     0x2019, 0x201C, 0x201D, 0x3014, 0x3015, 0x3008, 0x3009, 0x300A, 0x000D, 0x000A,
     62     0x300B, 0x300C, 0x300D, 0x300E, 0x300F, 0x3016, 0x3017, 0x3010, 0x000D, 0x000A,
     63     0x3011, 0x00B1, 0x00D7, 0x00F7, 0x2236, 0x2227, 0x7FC1, 0x8956, 0x000D, 0x000A,
     64     0x9D2C, 0x9D0E, 0x9EC4, 0x5CA1, 0x6C96, 0x837B, 0x5104, 0x5C4B, 0x000D, 0x000A,
     65     0x61B6, 0x81C6, 0x6876, 0x7261, 0x4E59, 0x4FFA, 0x5378, 0x57F7, 0x000D, 0x000A,
     66     0x57F4, 0x57F9, 0x57FA, 0x57FC, 0x5800, 0x5802, 0x5805, 0x5806, 0x000D, 0x000A,
     67     0x580A, 0x581E, 0x6BB5, 0x6BB7, 0x6BBA, 0x6BBC, 0x9CE2, 0x977C, 0x000D, 0x000A,
     68     0x6BBF, 0x6BC1, 0x6BC5, 0x6BC6, 0x6BCB, 0x6BCD, 0x6BCF, 0x6BD2, 0x000D, 0x000A,
     69     0x6BD3, 0x6BD4, 0x6BD6, 0x6BD7, 0x6BD8, 0x6BDB, 0x6BEB, 0x6BEC, 0x000D, 0x000A,
     70     0x6C05, 0x6C08, 0x6C0F, 0x6C11, 0x6C13, 0x6C23, 0x6C34, 0x0041, 0x000D, 0x000A,
     71     0x0043, 0x0044, 0x0045, 0x0046, 0x0047, 0x0048, 0x0049, 0x004A, 0x000D, 0x000A,
     72     0x004B, 0x004C, 0x004D, 0x004E, 0x004F, 0x0050, 0x0051, 0x0052, 0x000D, 0x000A,
     73     0x0053, 0x0054, 0x0055, 0x0056, 0x0057, 0x0058, 0x0059, 0x005A, 0x000D, 0x000A,
     74     0x005B, 0x9792, 0x9CCC, 0x9CCD, 0x9CCE, 0x9CCF, 0x9CD0, 0x9CD3, 0x000D, 0x000A,
     75     0x9CD4, 0x9CD5, 0x9CD7, 0x9CD8, 0x9CD9, 0x9CDC, 0x9CDD, 0x9CDF, 0x000D, 0x000A,
     76     0x9785, 0x9791, 0x00BD, 0x0390, 0x0385, 0x0386, 0x0388, 0x0389, 0x000D, 0x000A,
     77     0x038E, 0x038F, 0x0390, 0x0391, 0x0392, 0x0393, 0x0394, 0x0395, 0x000D, 0x000A,
     78     0x0396, 0x0397, 0x0398, 0x0399, 0x039A, 0x038A, 0x038C, 0x039C, 0x000D, 0x000A,
     79     /* test non-BMP code points */
     80     0x0002A699,
     81     0x0002A69C, 0x0002A69D, 0x0002A69E, 0x0002A69F, 0x0002A6A0, 0x0002A6A5, 0x0002A6A6, 0x0002A6A7, 0x0002A6A8, 0x0002A6AB,
     82     0x0002A6AC, 0x0002A6AD, 0x0002A6AE, 0x0002A6AF, 0x0002A6B0, 0x0002A6B1, 0x0002A6B3, 0x0002A6B5, 0x0002A6B6, 0x0002A6B7,
     83     0x0002A6B8, 0x0002A6B9, 0x0002A6BA, 0x0002A6BB, 0x0002A6BC, 0x0002A6BD, 0x0002A6BE, 0x0002A6BF, 0x0002A6C0, 0x0002A6C1,
     84     0x0002A6C2, 0x0002A6C3, 0x0002A6C4, 0x0002A6C8, 0x0002A6CA, 0x0002A6CB, 0x0002A6CD, 0x0002A6CE, 0x0002A6CF, 0x0002A6D0,
     85     0x0002A6D1, 0x0002A6D2, 0x0002A6D3, 0x0002A6D4, 0x0002A6D5,
     86 
     87     0x4DB3, 0x4DB4, 0x4DB5, 0x4E00, 0x4E00, 0x4E01, 0x4E02, 0x4E03, 0x000D, 0x000A,
     88     0x0392, 0x0393, 0x0394, 0x0395, 0x0396, 0x0397, 0x33E0, 0x33E6, 0x000D, 0x000A,
     89     0x4E05, 0x4E07, 0x4E04, 0x4E08, 0x4E08, 0x4E09, 0x4E0A, 0x4E0B, 0x000D, 0x000A,
     90     0x4E0C, 0x0021, 0x0022, 0x0023, 0x0024, 0xFF40, 0xFF41, 0xFF42, 0x000D, 0x000A,
     91     0xFF43, 0xFF44, 0xFF45, 0xFF46, 0xFF47, 0xFF48, 0xFF49, 0xFF4A, 0x000D, 0x000A,0x0000
     92 };
     93 
     94 static const UChar src16[] = {
     95     0x00A8, 0x3003, 0x3005, 0x2015, 0xFF5E, 0x2016, 0x2026, 0x2018, 0x000D, 0x000A,
     96     0x2019, 0x201C, 0x201D, 0x3014, 0x3015, 0x3008, 0x3009, 0x300A, 0x000D, 0x000A,
     97     0x300B, 0x300C, 0x300D, 0x300E, 0x300F, 0x3016, 0x3017, 0x3010, 0x000D, 0x000A,
     98     0x3011, 0x00B1, 0x00D7, 0x00F7, 0x2236, 0x2227, 0x7FC1, 0x8956, 0x000D, 0x000A,
     99     0x9D2C, 0x9D0E, 0x9EC4, 0x5CA1, 0x6C96, 0x837B, 0x5104, 0x5C4B, 0x000D, 0x000A,
    100     0x61B6, 0x81C6, 0x6876, 0x7261, 0x4E59, 0x4FFA, 0x5378, 0x57F7, 0x000D, 0x000A,
    101     0x57F4, 0x57F9, 0x57FA, 0x57FC, 0x5800, 0x5802, 0x5805, 0x5806, 0x000D, 0x000A,
    102     0x580A, 0x581E, 0x6BB5, 0x6BB7, 0x6BBA, 0x6BBC, 0x9CE2, 0x977C, 0x000D, 0x000A,
    103     0x6BBF, 0x6BC1, 0x6BC5, 0x6BC6, 0x6BCB, 0x6BCD, 0x6BCF, 0x6BD2, 0x000D, 0x000A,
    104     0x6BD3, 0x6BD4, 0x6BD6, 0x6BD7, 0x6BD8, 0x6BDB, 0x6BEB, 0x6BEC, 0x000D, 0x000A,
    105     0x6C05, 0x6C08, 0x6C0F, 0x6C11, 0x6C13, 0x6C23, 0x6C34, 0x0041, 0x000D, 0x000A,
    106     0x0043, 0x0044, 0x0045, 0x0046, 0x0047, 0x0048, 0x0049, 0x004A, 0x000D, 0x000A,
    107     0x004B, 0x004C, 0x004D, 0x004E, 0x004F, 0x0050, 0x0051, 0x0052, 0x000D, 0x000A,
    108     0x0053, 0x0054, 0x0055, 0x0056, 0x0057, 0x0058, 0x0059, 0x005A, 0x000D, 0x000A,
    109     0x005B, 0x9792, 0x9CCC, 0x9CCD, 0x9CCE, 0x9CCF, 0x9CD0, 0x9CD3, 0x000D, 0x000A,
    110     0x9CD4, 0x9CD5, 0x9CD7, 0x9CD8, 0x9CD9, 0x9CDC, 0x9CDD, 0x9CDF, 0x000D, 0x000A,
    111     0x9785, 0x9791, 0x00BD, 0x0390, 0x0385, 0x0386, 0x0388, 0x0389, 0x000D, 0x000A,
    112     0x038E, 0x038F, 0x0390, 0x0391, 0x0392, 0x0393, 0x0394, 0x0395, 0x000D, 0x000A,
    113     0x0396, 0x0397, 0x0398, 0x0399, 0x039A, 0x038A, 0x038C, 0x039C, 0x000D, 0x000A,
    114 
    115     /* test non-BMP code points */
    116     0xD869, 0xDE99, 0xD869, 0xDE9C, 0xD869, 0xDE9D, 0xD869, 0xDE9E, 0xD869, 0xDE9F,
    117     0xD869, 0xDEA0, 0xD869, 0xDEA5, 0xD869, 0xDEA6, 0xD869, 0xDEA7, 0xD869, 0xDEA8,
    118     0xD869, 0xDEAB, 0xD869, 0xDEAC, 0xD869, 0xDEAD, 0xD869, 0xDEAE, 0xD869, 0xDEAF,
    119     0xD869, 0xDEB0, 0xD869, 0xDEB1, 0xD869, 0xDEB3, 0xD869, 0xDEB5, 0xD869, 0xDEB6,
    120     0xD869, 0xDEB7, 0xD869, 0xDEB8, 0xD869, 0xDEB9, 0xD869, 0xDEBA, 0xD869, 0xDEBB,
    121     0xD869, 0xDEBC, 0xD869, 0xDEBD, 0xD869, 0xDEBE, 0xD869, 0xDEBF, 0xD869, 0xDEC0,
    122     0xD869, 0xDEC1, 0xD869, 0xDEC2, 0xD869, 0xDEC3, 0xD869, 0xDEC4, 0xD869, 0xDEC8,
    123     0xD869, 0xDECA, 0xD869, 0xDECB, 0xD869, 0xDECD, 0xD869, 0xDECE, 0xD869, 0xDECF,
    124     0xD869, 0xDED0, 0xD869, 0xDED1, 0xD869, 0xDED2, 0xD869, 0xDED3, 0xD869, 0xDED4,
    125     0xD869, 0xDED5,
    126 
    127     0x4DB3, 0x4DB4, 0x4DB5, 0x4E00, 0x4E00, 0x4E01, 0x4E02, 0x4E03, 0x000D, 0x000A,
    128     0x0392, 0x0393, 0x0394, 0x0395, 0x0396, 0x0397, 0x33E0, 0x33E6, 0x000D, 0x000A,
    129     0x4E05, 0x4E07, 0x4E04, 0x4E08, 0x4E08, 0x4E09, 0x4E0A, 0x4E0B, 0x000D, 0x000A,
    130     0x4E0C, 0x0021, 0x0022, 0x0023, 0x0024, 0xFF40, 0xFF41, 0xFF42, 0x000D, 0x000A,
    131     0xFF43, 0xFF44, 0xFF45, 0xFF46, 0xFF47, 0xFF48, 0xFF49, 0xFF4A, 0x000D, 0x000A,0x0000
    132 };
    133 
    134 
    135 static void Test_strToUTF32(void){
    136     UErrorCode err = U_ZERO_ERROR;
    137     UChar32 u32Target[400];
    138     int32_t u32DestLen;
    139     int i= 0;
    140 
    141     /* first with length */
    142     u32DestLen = -2;
    143     u_strToUTF32(u32Target, 0, &u32DestLen, src16, LENGTHOF(src16),&err);
    144     if(err != U_BUFFER_OVERFLOW_ERROR || u32DestLen != LENGTHOF(src32)) {
    145         log_err("u_strToUTF32(preflight with length): "
    146                 "length %ld != %ld and %s != U_BUFFER_OVERFLOW_ERROR\n",
    147                 (long)u32DestLen, (long)LENGTHOF(src32), u_errorName(err));
    148         return;
    149     }
    150     err = U_ZERO_ERROR;
    151     u32DestLen = -2;
    152     u_strToUTF32(u32Target, LENGTHOF(src32)+1, &u32DestLen, src16, LENGTHOF(src16),&err);
    153     if(err != U_ZERO_ERROR || u32DestLen != LENGTHOF(src32)) {
    154         log_err("u_strToUTF32(with length): "
    155                 "length %ld != %ld and %s != U_ZERO_ERROR\n",
    156                 (long)u32DestLen, (long)LENGTHOF(src32), u_errorName(err));
    157         return;
    158     }
    159     /*for(i=0; i< u32DestLen; i++){
    160         printf("0x%08X, ",uTarget[i]);
    161         if(i%10==0){
    162             printf("\n");
    163         }
    164     }*/
    165     for(i=0; i< LENGTHOF(src32); i++){
    166         if(u32Target[i] != src32[i]){
    167             log_verbose("u_strToUTF32(with length) failed expected: %04X got: %04X at index: %i \n", src32[i], u32Target[i],i);
    168         }
    169     }
    170     if(u32Target[i] != 0){
    171         log_verbose("u_strToUTF32(with length) failed expected: %04X got: %04X at index: %i \n", 0, u32Target[i],i);
    172     }
    173 
    174     /* now NUL-terminated */
    175     u32DestLen = -2;
    176     u_strToUTF32(NULL,0, &u32DestLen, src16, -1,&err);
    177     if(err != U_BUFFER_OVERFLOW_ERROR || u32DestLen != LENGTHOF(src32)-1) {
    178         log_err("u_strToUTF32(preflight with NUL-termination): "
    179                 "length %ld != %ld and %s != U_BUFFER_OVERFLOW_ERROR\n",
    180                 (long)u32DestLen, (long)LENGTHOF(src32)-1, u_errorName(err));
    181         return;
    182     }
    183     err = U_ZERO_ERROR;
    184     u32DestLen = -2;
    185     u_strToUTF32(u32Target, LENGTHOF(src32), &u32DestLen, src16, -1,&err);
    186     if(err != U_ZERO_ERROR || u32DestLen != LENGTHOF(src32)-1) {
    187         log_err("u_strToUTF32(with NUL-termination): "
    188                 "length %ld != %ld and %s != U_ZERO_ERROR\n",
    189                 (long)u32DestLen, (long)LENGTHOF(src32)-1, u_errorName(err));
    190         return;
    191     }
    192 
    193     for(i=0; i< LENGTHOF(src32); i++){
    194         if(u32Target[i] != src32[i]){
    195             log_verbose("u_strToUTF32(NUL-termination) failed expected: %04X got: %04X \n", src32[i], u32Target[i]);
    196         }
    197     }
    198 }
    199 
    200 /* test unpaired surrogates */
    201 static void Test_strToUTF32_surrogates() {
    202     UErrorCode err = U_ZERO_ERROR;
    203     UChar32 u32Target[400];
    204     int32_t len16, u32DestLen;
    205     int32_t numSubstitutions;
    206     int i;
    207 
    208     static const UChar surr16[] = { 0x41, 0xd900, 0x61, 0xdc00, 0x5a, 0xd900, 0xdc00, 0x7a, 0 };
    209     static const UChar32 expected[] = { 0x5a, 0x50000, 0x7a, 0 };
    210     static const UChar32 expected_FFFD[] = { 0x41, 0xfffd, 0x61, 0xfffd, 0x5a, 0x50000, 0x7a, 0 };
    211     static const UChar32 expected_12345[] = { 0x41, 0x12345, 0x61, 0x12345, 0x5a, 0x50000, 0x7a, 0 };
    212     len16 = LENGTHOF(surr16);
    213     for(i = 0; i < 4; ++i) {
    214         err = U_ZERO_ERROR;
    215         u_strToUTF32(u32Target, 0, &u32DestLen, surr16+i, len16-i, &err);
    216         if(err != U_INVALID_CHAR_FOUND) {
    217             log_err("u_strToUTF32(preflight surr16+%ld) sets %s != U_INVALID_CHAR_FOUND\n",
    218                     (long)i, u_errorName(err));
    219             return;
    220         }
    221 
    222         err = U_ZERO_ERROR;
    223         u_strToUTF32(u32Target, LENGTHOF(u32Target), &u32DestLen, surr16+i, len16-i, &err);
    224         if(err != U_INVALID_CHAR_FOUND) {
    225             log_err("u_strToUTF32(surr16+%ld) sets %s != U_INVALID_CHAR_FOUND\n",
    226                     (long)i, u_errorName(err));
    227             return;
    228         }
    229 
    230         err = U_ZERO_ERROR;
    231         u_strToUTF32(NULL, 0, &u32DestLen, surr16+i, -1, &err);
    232         if(err != U_INVALID_CHAR_FOUND) {
    233             log_err("u_strToUTF32(preflight surr16+%ld/NUL) sets %s != U_INVALID_CHAR_FOUND\n",
    234                     (long)i, u_errorName(err));
    235             return;
    236         }
    237 
    238         err = U_ZERO_ERROR;
    239         u_strToUTF32(u32Target, LENGTHOF(u32Target), &u32DestLen, surr16+i, -1, &err);
    240         if(err != U_INVALID_CHAR_FOUND) {
    241             log_err("u_strToUTF32(surr16+%ld/NUL) sets %s != U_INVALID_CHAR_FOUND\n",
    242                     (long)i, u_errorName(err));
    243             return;
    244         }
    245     }
    246 
    247     err = U_ZERO_ERROR;
    248     u_strToUTF32(u32Target, 0, &u32DestLen, surr16+4, len16-4-1, &err);
    249     if(err != U_BUFFER_OVERFLOW_ERROR || u32DestLen != 3) {
    250         log_err("u_strToUTF32(preflight surr16+4) sets %s != U_BUFFER_OVERFLOW_ERROR or an unexpected length\n",
    251                 u_errorName(err));
    252         return;
    253     }
    254 
    255     err = U_ZERO_ERROR;
    256     u_strToUTF32(u32Target, LENGTHOF(u32Target), &u32DestLen, surr16+4, len16-4-1, &err);
    257     if(err != U_ZERO_ERROR || u32DestLen != 3 || uprv_memcmp(u32Target, expected, 4*4)) {
    258         log_err("u_strToUTF32(surr16+4) sets %s != U_ZERO_ERROR or does not produce the expected string\n",
    259                 u_errorName(err));
    260         return;
    261     }
    262 
    263     err = U_ZERO_ERROR;
    264     u_strToUTF32(NULL, 0, &u32DestLen, surr16+4, -1, &err);
    265     if(err != U_BUFFER_OVERFLOW_ERROR || u32DestLen != 3) {
    266         log_err("u_strToUTF32(preflight surr16+4/NUL) sets %s != U_BUFFER_OVERFLOW_ERROR or an unexpected length\n",
    267                 u_errorName(err));
    268         return;
    269     }
    270 
    271     err = U_ZERO_ERROR;
    272     u_strToUTF32(u32Target, LENGTHOF(u32Target), &u32DestLen, surr16+4, -1, &err);
    273     if(err != U_ZERO_ERROR || u32DestLen != 3 || uprv_memcmp(u32Target, expected, 4*4)) {
    274         log_err("u_strToUTF32(surr16+4/NUL) sets %s != U_ZERO_ERROR or does not produce the expected string\n",
    275                 u_errorName(err));
    276         return;
    277     }
    278 
    279     /* with substitution character */
    280     numSubstitutions = -1;
    281     err = U_ZERO_ERROR;
    282     u_strToUTF32WithSub(u32Target, 0, &u32DestLen, surr16, len16-1, 0xfffd, &numSubstitutions, &err);
    283     if(err != U_BUFFER_OVERFLOW_ERROR || u32DestLen != 7 || numSubstitutions != 2) {
    284         log_err("u_strToUTF32WithSub(preflight surr16) sets %s != U_BUFFER_OVERFLOW_ERROR or an unexpected length\n",
    285                 u_errorName(err));
    286         return;
    287     }
    288 
    289     err = U_ZERO_ERROR;
    290     u_strToUTF32WithSub(u32Target, LENGTHOF(u32Target), &u32DestLen, surr16, len16-1, 0xfffd, &numSubstitutions, &err);
    291     if(err != U_ZERO_ERROR || u32DestLen != 7 || numSubstitutions != 2 || uprv_memcmp(u32Target, expected_FFFD, 8*4)) {
    292         log_err("u_strToUTF32WithSub(surr16) sets %s != U_ZERO_ERROR or does not produce the expected string\n",
    293                 u_errorName(err));
    294         return;
    295     }
    296 
    297     err = U_ZERO_ERROR;
    298     u_strToUTF32WithSub(NULL, 0, &u32DestLen, surr16, -1, 0x12345, &numSubstitutions, &err);
    299     if(err != U_BUFFER_OVERFLOW_ERROR || u32DestLen != 7 || numSubstitutions != 2) {
    300         log_err("u_strToUTF32WithSub(preflight surr16/NUL) sets %s != U_BUFFER_OVERFLOW_ERROR or an unexpected length\n",
    301                 u_errorName(err));
    302         return;
    303     }
    304 
    305     err = U_ZERO_ERROR;
    306     u_strToUTF32WithSub(u32Target, LENGTHOF(u32Target), &u32DestLen, surr16, -1, 0x12345, &numSubstitutions, &err);
    307     if(err != U_ZERO_ERROR || u32DestLen != 7 || numSubstitutions != 2 || uprv_memcmp(u32Target, expected_12345, 8*4)) {
    308         log_err("u_strToUTF32WithSub(surr16/NUL) sets %s != U_ZERO_ERROR or does not produce the expected string\n",
    309                 u_errorName(err));
    310         return;
    311     }
    312 }
    313 
    314 static void Test_strFromUTF32(void){
    315     UErrorCode err = U_ZERO_ERROR;
    316     UChar uTarget[400];
    317     int32_t uDestLen;
    318     int i= 0;
    319 
    320     /* first with length */
    321     uDestLen = -2;
    322     u_strFromUTF32(uTarget,0,&uDestLen,src32,LENGTHOF(src32),&err);
    323     if(err != U_BUFFER_OVERFLOW_ERROR || uDestLen != LENGTHOF(src16)) {
    324         log_err("u_strFromUTF32(preflight with length): "
    325                 "length %ld != %ld and %s != U_BUFFER_OVERFLOW_ERROR\n",
    326                 (long)uDestLen, (long)LENGTHOF(src16), u_errorName(err));
    327         return;
    328     }
    329     err = U_ZERO_ERROR;
    330     uDestLen = -2;
    331     u_strFromUTF32(uTarget, LENGTHOF(src16)+1,&uDestLen,src32,LENGTHOF(src32),&err);
    332     if(err != U_ZERO_ERROR || uDestLen != LENGTHOF(src16)) {
    333         log_err("u_strFromUTF32(with length): "
    334                 "length %ld != %ld and %s != U_ZERO_ERROR\n",
    335                 (long)uDestLen, (long)LENGTHOF(src16), u_errorName(err));
    336         return;
    337     }
    338     /*for(i=0; i< uDestLen; i++){
    339         printf("0x%04X, ",uTarget[i]);
    340         if(i%10==0){
    341             printf("\n");
    342         }
    343     }*/
    344 
    345     for(i=0; i< uDestLen; i++){
    346         if(uTarget[i] != src16[i]){
    347             log_verbose("u_strFromUTF32(with length) failed expected: %04X got: %04X at index: %i \n", src16[i] ,uTarget[i],i);
    348         }
    349     }
    350     if(uTarget[i] != 0){
    351         log_verbose("u_strFromUTF32(with length) failed expected: %04X got: %04X at index: %i \n", 0,uTarget[i],i);
    352     }
    353 
    354     /* now NUL-terminated */
    355     uDestLen = -2;
    356     u_strFromUTF32(NULL,0,&uDestLen,src32,-1,&err);
    357     if(err != U_BUFFER_OVERFLOW_ERROR || uDestLen != LENGTHOF(src16)-1) {
    358         log_err("u_strFromUTF32(preflight with NUL-termination): "
    359                 "length %ld != %ld and %s != U_BUFFER_OVERFLOW_ERROR\n",
    360                 (long)uDestLen, (long)LENGTHOF(src16)-1, u_errorName(err));
    361         return;
    362     }
    363     err = U_ZERO_ERROR;
    364     uDestLen = -2;
    365     u_strFromUTF32(uTarget, LENGTHOF(src16),&uDestLen,src32,-1,&err);
    366     if(err != U_ZERO_ERROR || uDestLen != LENGTHOF(src16)-1) {
    367         log_err("u_strFromUTF32(with NUL-termination): "
    368                 "length %ld != %ld and %s != U_ZERO_ERROR\n",
    369                 (long)uDestLen, (long)LENGTHOF(src16)-1, u_errorName(err));
    370         return;
    371     }
    372 
    373     for(i=0; i< uDestLen; i++){
    374         if(uTarget[i] != src16[i]){
    375             log_verbose("u_strFromUTF32(with NUL-termination) failed expected: %04X got: %04X \n", src16[i] ,uTarget[i]);
    376         }
    377     }
    378 }
    379 
    380 /* test surrogate code points */
    381 static void Test_strFromUTF32_surrogates() {
    382     UErrorCode err = U_ZERO_ERROR;
    383     UChar uTarget[400];
    384     int32_t len32, uDestLen;
    385     int32_t numSubstitutions;
    386     int i;
    387 
    388     static const UChar32 surr32[] = { 0x41, 0xd900, 0x61, 0xdc00, -1, 0x110000, 0x5a, 0x50000, 0x7a, 0 };
    389     static const UChar expected[] = { 0x5a, 0xd900, 0xdc00, 0x7a, 0 };
    390     static const UChar expected_FFFD[] = { 0x41, 0xfffd, 0x61, 0xfffd, 0xfffd, 0xfffd, 0x5a, 0xd900, 0xdc00, 0x7a, 0 };
    391     static const UChar expected_12345[] = { 0x41, 0xd808, 0xdf45, 0x61, 0xd808, 0xdf45, 0xd808, 0xdf45, 0xd808, 0xdf45,
    392                                             0x5a, 0xd900, 0xdc00, 0x7a, 0 };
    393     len32 = LENGTHOF(surr32);
    394     for(i = 0; i < 6; ++i) {
    395         err = U_ZERO_ERROR;
    396         u_strFromUTF32(uTarget, 0, &uDestLen, surr32+i, len32-i, &err);
    397         if(err != U_INVALID_CHAR_FOUND) {
    398             log_err("u_strFromUTF32(preflight surr32+%ld) sets %s != U_INVALID_CHAR_FOUND\n",
    399                     (long)i, u_errorName(err));
    400             return;
    401         }
    402 
    403         err = U_ZERO_ERROR;
    404         u_strFromUTF32(uTarget, LENGTHOF(uTarget), &uDestLen, surr32+i, len32-i, &err);
    405         if(err != U_INVALID_CHAR_FOUND) {
    406             log_err("u_strFromUTF32(surr32+%ld) sets %s != U_INVALID_CHAR_FOUND\n",
    407                     (long)i, u_errorName(err));
    408             return;
    409         }
    410 
    411         err = U_ZERO_ERROR;
    412         u_strFromUTF32(NULL, 0, &uDestLen, surr32+i, -1, &err);
    413         if(err != U_INVALID_CHAR_FOUND) {
    414             log_err("u_strFromUTF32(preflight surr32+%ld/NUL) sets %s != U_INVALID_CHAR_FOUND\n",
    415                     (long)i, u_errorName(err));
    416             return;
    417         }
    418 
    419         err = U_ZERO_ERROR;
    420         u_strFromUTF32(uTarget, LENGTHOF(uTarget), &uDestLen, surr32+i, -1, &err);
    421         if(err != U_INVALID_CHAR_FOUND) {
    422             log_err("u_strFromUTF32(surr32+%ld/NUL) sets %s != U_INVALID_CHAR_FOUND\n",
    423                     (long)i, u_errorName(err));
    424             return;
    425         }
    426     }
    427 
    428     err = U_ZERO_ERROR;
    429     u_strFromUTF32(uTarget, 0, &uDestLen, surr32+6, len32-6-1, &err);
    430     if(err != U_BUFFER_OVERFLOW_ERROR || uDestLen != 4) {
    431         log_err("u_strFromUTF32(preflight surr32+6) sets %s != U_BUFFER_OVERFLOW_ERROR or an unexpected length\n",
    432                 u_errorName(err));
    433         return;
    434     }
    435 
    436     err = U_ZERO_ERROR;
    437     u_strFromUTF32(uTarget, LENGTHOF(uTarget), &uDestLen, surr32+6, len32-6-1, &err);
    438     if(err != U_ZERO_ERROR || uDestLen != 4 || u_memcmp(uTarget, expected, 5)) {
    439         log_err("u_strFromUTF32(surr32+6) sets %s != U_ZERO_ERROR or does not produce the expected string\n",
    440                 u_errorName(err));
    441         return;
    442     }
    443 
    444     err = U_ZERO_ERROR;
    445     u_strFromUTF32(NULL, 0, &uDestLen, surr32+6, -1, &err);
    446     if(err != U_BUFFER_OVERFLOW_ERROR || uDestLen != 4) {
    447         log_err("u_strFromUTF32(preflight surr32+6/NUL) sets %s != U_BUFFER_OVERFLOW_ERROR or an unexpected length\n",
    448                 u_errorName(err));
    449         return;
    450     }
    451 
    452     err = U_ZERO_ERROR;
    453     u_strFromUTF32(uTarget, LENGTHOF(uTarget), &uDestLen, surr32+6, -1, &err);
    454     if(err != U_ZERO_ERROR || uDestLen != 4 || u_memcmp(uTarget, expected, 5)) {
    455         log_err("u_strFromUTF32(surr32+6/NUL) sets %s != U_ZERO_ERROR or does not produce the expected string\n",
    456                 u_errorName(err));
    457         return;
    458     }
    459 
    460     /* with substitution character */
    461     numSubstitutions = -1;
    462     err = U_ZERO_ERROR;
    463     u_strFromUTF32WithSub(uTarget, 0, &uDestLen, surr32, len32-1, 0xfffd, &numSubstitutions, &err);
    464     if(err != U_BUFFER_OVERFLOW_ERROR || uDestLen != 10 || numSubstitutions != 4) {
    465         log_err("u_strFromUTF32WithSub(preflight surr32) sets %s != U_BUFFER_OVERFLOW_ERROR or an unexpected length\n",
    466                 u_errorName(err));
    467         return;
    468     }
    469 
    470     err = U_ZERO_ERROR;
    471     u_strFromUTF32WithSub(uTarget, LENGTHOF(uTarget), &uDestLen, surr32, len32-1, 0xfffd, &numSubstitutions, &err);
    472     if(err != U_ZERO_ERROR || uDestLen != 10 || numSubstitutions != 4 || u_memcmp(uTarget, expected_FFFD, 11)) {
    473         log_err("u_strFromUTF32WithSub(surr32) sets %s != U_ZERO_ERROR or does not produce the expected string\n",
    474                 u_errorName(err));
    475         return;
    476     }
    477 
    478     err = U_ZERO_ERROR;
    479     u_strFromUTF32WithSub(NULL, 0, &uDestLen, surr32, -1, 0x12345, &numSubstitutions, &err);
    480     if(err != U_BUFFER_OVERFLOW_ERROR || uDestLen != 14 || numSubstitutions != 4) {
    481         log_err("u_strFromUTF32WithSub(preflight surr32/NUL) sets %s != U_BUFFER_OVERFLOW_ERROR or an unexpected length\n",
    482                 u_errorName(err));
    483         return;
    484     }
    485 
    486     err = U_ZERO_ERROR;
    487     u_strFromUTF32WithSub(uTarget, LENGTHOF(uTarget), &uDestLen, surr32, -1, 0x12345, &numSubstitutions, &err);
    488     if(err != U_ZERO_ERROR || uDestLen != 14 || numSubstitutions != 4 || u_memcmp(uTarget, expected_12345, 15)) {
    489         log_err("u_strFromUTF32WithSub(surr32/NUL) sets %s != U_ZERO_ERROR or does not produce the expected string\n",
    490                 u_errorName(err));
    491         return;
    492     }
    493 }
    494 
    495 static void Test_UChar_UTF8_API(void){
    496 
    497     UErrorCode err = U_ZERO_ERROR;
    498     UChar uTemp[1];
    499     char u8Temp[1];
    500     UChar* uTarget=uTemp;
    501     const char* u8Src;
    502     int32_t u8SrcLen = 0;
    503     int32_t uTargetLength = 0;
    504     int32_t uDestLen=0;
    505     const UChar* uSrc = src16;
    506     int32_t uSrcLen   = sizeof(src16)/2;
    507     char* u8Target = u8Temp;
    508     int32_t u8TargetLength =0;
    509     int32_t u8DestLen =0;
    510     UBool failed = FALSE;
    511     int i= 0;
    512     int32_t numSubstitutions;
    513 
    514     {
    515         /* preflight */
    516         u8Temp[0] = 0x12;
    517         u_strToUTF8(u8Target,u8TargetLength, &u8DestLen, uSrc, uSrcLen,&err);
    518         if(err == U_BUFFER_OVERFLOW_ERROR && u8Temp[0] == 0x12){
    519             err = U_ZERO_ERROR;
    520             u8Target = (char*) malloc (sizeof(uint8_t) * (u8DestLen+1));
    521             u8TargetLength = u8DestLen;
    522 
    523             u8Target[u8TargetLength] = (char)0xfe;
    524             u8DestLen = -1;
    525             u_strToUTF8(u8Target,u8TargetLength, &u8DestLen, uSrc, uSrcLen,&err);
    526             if(U_FAILURE(err) || u8DestLen != u8TargetLength || u8Target[u8TargetLength] != (char)0xfe){
    527                 log_err("u_strToUTF8 failed after preflight. Error: %s\n", u_errorName(err));
    528                 return;
    529             }
    530 
    531         }
    532         else {
    533             log_err("Should have gotten U_BUFFER_OVERFLOW_ERROR");
    534         }
    535         failed = FALSE;
    536         /*for(i=0; i< u8DestLen; i++){
    537             printf("0x%04X, ",u8Target[i]);
    538             if(i%10==0){
    539                 printf("\n");
    540             }
    541         }*/
    542         /*for(i=0; i< u8DestLen; i++){
    543             if(u8Target[i] != src8[i]){
    544                 log_verbose("u_strToUTF8() failed expected: %04X got: %04X \n", src8[i], u8Target[i]);
    545                 failed =TRUE;
    546             }
    547         }
    548         if(failed){
    549             log_err("u_strToUTF8() failed \n");
    550         }*/
    551         u8Src = u8Target;
    552         u8SrcLen = u8DestLen;
    553 
    554         /* preflight */
    555         uTemp[0] = 0x1234;
    556         u_strFromUTF8(uTarget,uTargetLength,&uDestLen,u8Src,u8SrcLen,&err);
    557         if(err == U_BUFFER_OVERFLOW_ERROR && uTemp[0] == 0x1234){
    558             err = U_ZERO_ERROR;
    559             uTarget = (UChar*) malloc( sizeof(UChar) * (uDestLen+1));
    560             uTargetLength =  uDestLen;
    561 
    562             uTarget[uTargetLength] = 0xfff0;
    563             uDestLen = -1;
    564             u_strFromUTF8(uTarget,uTargetLength,&uDestLen,u8Src,u8SrcLen,&err);
    565         }
    566         else {
    567             log_err("error: u_strFromUTF8(preflight) should have gotten U_BUFFER_OVERFLOW_ERROR\n");
    568         }
    569         /*for(i=0; i< uDestLen; i++){
    570             printf("0x%04X, ",uTarget[i]);
    571             if(i%10==0){
    572                 printf("\n");
    573             }
    574         }*/
    575 
    576         if(U_FAILURE(err) || uDestLen != uTargetLength || uTarget[uTargetLength] != 0xfff0) {
    577             failed = TRUE;
    578         }
    579         for(i=0; i< uSrcLen; i++){
    580             if(uTarget[i] != src16[i]){
    581                 log_verbose("u_strFromUTF8() failed expected: \\u%04X got: \\u%04X at index: %i \n", src16[i] ,uTarget[i],i);
    582                 failed =TRUE;
    583             }
    584         }
    585         if(failed){
    586             log_err("error: u_strFromUTF8(after preflighting) failed\n");
    587         }
    588 
    589         free(u8Target);
    590         free(uTarget);
    591     }
    592     {
    593         u8SrcLen = -1;
    594         uTargetLength = 0;
    595         uSrcLen =-1;
    596         u8TargetLength=0;
    597         failed = FALSE;
    598         /* preflight */
    599         u_strToUTF8(NULL,u8TargetLength, &u8DestLen, uSrc, uSrcLen,&err);
    600         if(err == U_BUFFER_OVERFLOW_ERROR){
    601             err = U_ZERO_ERROR;
    602             u8Target = (char*) malloc (sizeof(uint8_t) * (u8DestLen+1));
    603             u8TargetLength = u8DestLen;
    604 
    605             u_strToUTF8(u8Target,u8TargetLength, &u8DestLen, uSrc, uSrcLen,&err);
    606 
    607         }
    608         else {
    609             log_err("Should have gotten U_BUFFER_OVERFLOW_ERROR");
    610         }
    611         failed = FALSE;
    612         /*for(i=0; i< u8DestLen; i++){
    613             printf("0x%04X, ",u8Target[i]);
    614             if(i%10==0){
    615                 printf("\n");
    616             }
    617         }*/
    618         /*for(i=0; i< u8DestLen; i++){
    619             if(u8Target[i] != src8[i]){
    620                 log_verbose("u_strToUTF8() failed expected: %04X got: %04X \n", src8[i], u8Target[i]);
    621                 failed =TRUE;
    622             }
    623         }
    624         if(failed){
    625             log_err("u_strToUTF8() failed \n");
    626         }*/
    627         u8Src = u8Target;
    628         u8SrcLen = u8DestLen;
    629 
    630         /* preflight */
    631         u_strFromUTF8(NULL,uTargetLength,&uDestLen,u8Src,u8SrcLen,&err);
    632         if(err == U_BUFFER_OVERFLOW_ERROR){
    633             err = U_ZERO_ERROR;
    634             uTarget = (UChar*) malloc( sizeof(UChar) * (uDestLen+1));
    635             uTargetLength =  uDestLen;
    636 
    637             u_strFromUTF8(uTarget,uTargetLength,&uDestLen,u8Src,u8SrcLen,&err);
    638         }
    639         else {
    640             log_err("Should have gotten U_BUFFER_OVERFLOW_ERROR");
    641         }
    642         /*for(i=0; i< uDestLen; i++){
    643             printf("0x%04X, ",uTarget[i]);
    644             if(i%10==0){
    645                 printf("\n");
    646             }
    647         }*/
    648 
    649         for(i=0; i< uSrcLen; i++){
    650             if(uTarget[i] != src16[i]){
    651                 log_verbose("u_strFromUTF8() failed expected: \\u%04X got: \\u%04X at index: %i \n", src16[i] ,uTarget[i],i);
    652                 failed =TRUE;
    653             }
    654         }
    655         if(failed){
    656             log_err("u_strToUTF8() failed \n");
    657         }
    658 
    659         free(u8Target);
    660         free(uTarget);
    661     }
    662 
    663     /* test UTF-8 with single surrogates - illegal in Unicode 3.2 */
    664     {
    665         static const UChar
    666             withLead16[]={ 0x1800, 0xd89a, 0x0061 },
    667             withTrail16[]={ 0x1800, 0xdcba, 0x0061, 0 },
    668             withTrail16SubFFFD[]={ 0x1800, 0xfffd, 0x0061, 0 }, /* sub==U+FFFD */
    669             withTrail16Sub50005[]={ 0x1800, 0xd900, 0xdc05, 0x0061, 0 }; /* sub==U+50005 */
    670         static const uint8_t
    671             withLead8[]={ 0xe1, 0xa0, 0x80, 0xed, 0xa2, 0x9a, 0x61 },
    672             withTrail8[]={ 0xe1, 0xa0, 0x80, 0xed, 0xb2, 0xba, 0x61, 0 },
    673             withTrail8Sub1A[]={ 0xe1, 0xa0, 0x80, 0x1a, 0x61, 0 }, /* sub==U+001A */
    674             withTrail8SubFFFD[]={ 0xe1, 0xa0, 0x80, 0xef, 0xbf, 0xbd, 0x61, 0 }; /* sub==U+FFFD */
    675         UChar out16[10];
    676         char out8[10];
    677 
    678         if(
    679             (err=U_ZERO_ERROR, u_strToUTF8(out8, LENGTHOF(out8), NULL, withLead16, LENGTHOF(withLead16), &err), err!=U_INVALID_CHAR_FOUND) ||
    680             (err=U_ZERO_ERROR, u_strToUTF8(out8, LENGTHOF(out8), NULL, withTrail16, -1, &err), err!=U_INVALID_CHAR_FOUND) ||
    681             (err=U_ZERO_ERROR, u_strFromUTF8(out16, LENGTHOF(out16), NULL, (const char *)withLead8, LENGTHOF(withLead8), &err), err!=U_INVALID_CHAR_FOUND) ||
    682             (err=U_ZERO_ERROR, u_strFromUTF8(out16, LENGTHOF(out16), NULL, (const char *)withTrail8, -1, &err), err!=U_INVALID_CHAR_FOUND)
    683         ) {
    684             log_err("error: u_strTo/FromUTF8(string with single surrogate) fails to report error\n");
    685         }
    686 
    687         /* test error handling with substitution characters */
    688 
    689         /* from UTF-8 with length */
    690         err=U_ZERO_ERROR;
    691         numSubstitutions=-1;
    692         out16[0]=0x55aa;
    693         uDestLen=0;
    694         u_strFromUTF8WithSub(out16, LENGTHOF(out16), &uDestLen,
    695                              (const char *)withTrail8, uprv_strlen((const char *)withTrail8),
    696                              0x50005, &numSubstitutions,
    697                              &err);
    698         if(U_FAILURE(err) || uDestLen!=u_strlen(withTrail16Sub50005) ||
    699                              0!=u_memcmp(withTrail16Sub50005, out16, uDestLen+1) ||
    700                              numSubstitutions!=1) {
    701             log_err("error: u_strFromUTF8WithSub(length) failed\n");
    702         }
    703 
    704         /* from UTF-8 with NUL termination */
    705         err=U_ZERO_ERROR;
    706         numSubstitutions=-1;
    707         out16[0]=0x55aa;
    708         uDestLen=0;
    709         u_strFromUTF8WithSub(out16, LENGTHOF(out16), &uDestLen,
    710                              (const char *)withTrail8, -1,
    711                              0xfffd, &numSubstitutions,
    712                              &err);
    713         if(U_FAILURE(err) || uDestLen!=u_strlen(withTrail16SubFFFD) ||
    714                              0!=u_memcmp(withTrail16SubFFFD, out16, uDestLen+1) ||
    715                              numSubstitutions!=1) {
    716             log_err("error: u_strFromUTF8WithSub(NUL termination) failed\n");
    717         }
    718 
    719         /* preflight from UTF-8 with NUL termination */
    720         err=U_ZERO_ERROR;
    721         numSubstitutions=-1;
    722         out16[0]=0x55aa;
    723         uDestLen=0;
    724         u_strFromUTF8WithSub(out16, 1, &uDestLen,
    725                              (const char *)withTrail8, -1,
    726                              0x50005, &numSubstitutions,
    727                              &err);
    728         if(err!=U_BUFFER_OVERFLOW_ERROR || uDestLen!=u_strlen(withTrail16Sub50005) || numSubstitutions!=1) {
    729             log_err("error: u_strFromUTF8WithSub(preflight/NUL termination) failed\n");
    730         }
    731 
    732         /* to UTF-8 with length */
    733         err=U_ZERO_ERROR;
    734         numSubstitutions=-1;
    735         out8[0]=(char)0xf5;
    736         u8DestLen=0;
    737         u_strToUTF8WithSub(out8, LENGTHOF(out8), &u8DestLen,
    738                            withTrail16, u_strlen(withTrail16),
    739                            0xfffd, &numSubstitutions,
    740                            &err);
    741         if(U_FAILURE(err) || u8DestLen!=uprv_strlen((const char *)withTrail8SubFFFD) ||
    742                              0!=uprv_memcmp((const char *)withTrail8SubFFFD, out8, u8DestLen+1) ||
    743                              numSubstitutions!=1) {
    744             log_err("error: u_strToUTF8WithSub(length) failed\n");
    745         }
    746 
    747         /* to UTF-8 with NUL termination */
    748         err=U_ZERO_ERROR;
    749         numSubstitutions=-1;
    750         out8[0]=(char)0xf5;
    751         u8DestLen=0;
    752         u_strToUTF8WithSub(out8, LENGTHOF(out8), &u8DestLen,
    753                            withTrail16, -1,
    754                            0x1a, &numSubstitutions,
    755                            &err);
    756         if(U_FAILURE(err) || u8DestLen!=uprv_strlen((const char *)withTrail8Sub1A) ||
    757                              0!=uprv_memcmp((const char *)withTrail8Sub1A, out8, u8DestLen+1) ||
    758                              numSubstitutions!=1) {
    759             log_err("error: u_strToUTF8WithSub(NUL termination) failed\n");
    760         }
    761 
    762         /* preflight to UTF-8 with NUL termination */
    763         err=U_ZERO_ERROR;
    764         numSubstitutions=-1;
    765         out8[0]=(char)0xf5;
    766         u8DestLen=0;
    767         u_strToUTF8WithSub(out8, 1, &u8DestLen,
    768                            withTrail16, -1,
    769                            0xfffd, &numSubstitutions,
    770                            &err);
    771         if(err!=U_BUFFER_OVERFLOW_ERROR || u8DestLen!=uprv_strlen((const char *)withTrail8SubFFFD) ||
    772                                            numSubstitutions!=1) {
    773             log_err("error: u_strToUTF8WithSub(preflight/NUL termination) failed\n");
    774         }
    775 
    776         /* test that numSubstitutions==0 if there are no substitutions */
    777 
    778         /* from UTF-8 with length (just first 3 bytes which are valid) */
    779         err=U_ZERO_ERROR;
    780         numSubstitutions=-1;
    781         out16[0]=0x55aa;
    782         uDestLen=0;
    783         u_strFromUTF8WithSub(out16, LENGTHOF(out16), &uDestLen,
    784                              (const char *)withTrail8, 3,
    785                              0x50005, &numSubstitutions,
    786                              &err);
    787         if(U_FAILURE(err) || uDestLen!=1 ||
    788                              0!=u_memcmp(withTrail16Sub50005, out16, uDestLen) ||
    789                              numSubstitutions!=0) {
    790             log_err("error: u_strFromUTF8WithSub(no subs) failed\n");
    791         }
    792 
    793         /* to UTF-8 with length (just first UChar which is valid) */
    794         err=U_ZERO_ERROR;
    795         numSubstitutions=-1;
    796         out8[0]=(char)0xf5;
    797         u8DestLen=0;
    798         u_strToUTF8WithSub(out8, LENGTHOF(out8), &u8DestLen,
    799                            withTrail16, 1,
    800                            0xfffd, &numSubstitutions,
    801                            &err);
    802         if(U_FAILURE(err) || u8DestLen!=3 ||
    803                              0!=uprv_memcmp((const char *)withTrail8SubFFFD, out8, u8DestLen) ||
    804                              numSubstitutions!=0) {
    805             log_err("error: u_strToUTF8WithSub(no subs) failed\n");
    806         }
    807 
    808         /* test that numSubstitutions==0 if subchar==U_SENTINEL (no subchar) */
    809 
    810         /* from UTF-8 with length (just first 3 bytes which are valid) */
    811         err=U_ZERO_ERROR;
    812         numSubstitutions=-1;
    813         out16[0]=0x55aa;
    814         uDestLen=0;
    815         u_strFromUTF8WithSub(out16, LENGTHOF(out16), &uDestLen,
    816                              (const char *)withTrail8, 3,
    817                              U_SENTINEL, &numSubstitutions,
    818                              &err);
    819         if(U_FAILURE(err) || uDestLen!=1 ||
    820                              0!=u_memcmp(withTrail16Sub50005, out16, uDestLen) ||
    821                              numSubstitutions!=0) {
    822             log_err("error: u_strFromUTF8WithSub(no subchar) failed\n");
    823         }
    824 
    825         /* to UTF-8 with length (just first UChar which is valid) */
    826         err=U_ZERO_ERROR;
    827         numSubstitutions=-1;
    828         out8[0]=(char)0xf5;
    829         u8DestLen=0;
    830         u_strToUTF8WithSub(out8, LENGTHOF(out8), &u8DestLen,
    831                            withTrail16, 1,
    832                            U_SENTINEL, &numSubstitutions,
    833                            &err);
    834         if(U_FAILURE(err) || u8DestLen!=3 ||
    835                              0!=uprv_memcmp((const char *)withTrail8SubFFFD, out8, u8DestLen) ||
    836                              numSubstitutions!=0) {
    837             log_err("error: u_strToUTF8WithSub(no subchar) failed\n");
    838         }
    839     }
    840 }
    841 
    842 /* compare if two strings are equal, but match 0xfffd in the second string with anything in the first */
    843 static UBool
    844 equalAnyFFFD(const UChar *s, const UChar *t, int32_t length) {
    845     UChar c1, c2;
    846 
    847     while(length>0) {
    848         c1=*s++;
    849         c2=*t++;
    850         if(c1!=c2 && c2!=0xfffd) {
    851             return FALSE;
    852         }
    853         --length;
    854     }
    855     return TRUE;
    856 }
    857 
    858 /* test u_strFromUTF8Lenient() */
    859 static void
    860 Test_FromUTF8(void) {
    861     /*
    862      * Test case from icu-support list 20071130 "u_strFromUTF8() returns U_INVALID_CHAR_FOUND(10)"
    863      */
    864     static const uint8_t bytes[]={ 0xe0, 0xa5, 0x9c, 0 };
    865     UChar dest[64];
    866     UChar *destPointer;
    867     int32_t destLength;
    868     UErrorCode errorCode;
    869 
    870     /* 3 bytes input, one UChar output (U+095C) */
    871     errorCode=U_ZERO_ERROR;
    872     destLength=-99;
    873     destPointer=u_strFromUTF8(NULL, 0, &destLength, (const char *)bytes, 3, &errorCode);
    874     if(errorCode!=U_BUFFER_OVERFLOW_ERROR || destPointer!=NULL || destLength!=1) {
    875         log_err("error: u_strFromUTF8(preflight srcLength=3) fails: destLength=%ld - %s\n",
    876                 (long)destLength, u_errorName(errorCode));
    877     }
    878 
    879     /* 4 bytes input, two UChars output (U+095C U+0000) */
    880     errorCode=U_ZERO_ERROR;
    881     destLength=-99;
    882     destPointer=u_strFromUTF8(NULL, 0, &destLength, (const char *)bytes, 4, &errorCode);
    883     if(errorCode!=U_BUFFER_OVERFLOW_ERROR || destPointer!=NULL || destLength!=2) {
    884         log_err("error: u_strFromUTF8(preflight srcLength=4) fails: destLength=%ld - %s\n",
    885                 (long)destLength, u_errorName(errorCode));
    886     }
    887 
    888     /* NUL-terminated 3 bytes input, one UChar output (U+095C) */
    889     errorCode=U_ZERO_ERROR;
    890     destLength=-99;
    891     destPointer=u_strFromUTF8(NULL, 0, &destLength, (const char *)bytes, -1, &errorCode);
    892     if(errorCode!=U_BUFFER_OVERFLOW_ERROR || destPointer!=NULL || destLength!=1) {
    893         log_err("error: u_strFromUTF8(preflight srcLength=-1) fails: destLength=%ld - %s\n",
    894                 (long)destLength, u_errorName(errorCode));
    895     }
    896 
    897     /* 3 bytes input, one UChar output (U+095C), transform not just preflight */
    898     errorCode=U_ZERO_ERROR;
    899     dest[0]=dest[1]=99;
    900     destLength=-99;
    901     destPointer=u_strFromUTF8(dest, LENGTHOF(dest), &destLength, (const char *)bytes, 3, &errorCode);
    902     if(U_FAILURE(errorCode) || destPointer!=dest || destLength!=1 || dest[0]!=0x95c || dest[1]!=0) {
    903         log_err("error: u_strFromUTF8(transform srcLength=3) fails: destLength=%ld - %s\n",
    904                 (long)destLength, u_errorName(errorCode));
    905     }
    906 }
    907 
    908 /* test u_strFromUTF8Lenient() */
    909 static void
    910 Test_FromUTF8Lenient(void) {
    911     /*
    912      * Multiple input strings, each NUL-terminated.
    913      * Terminate with a string starting with 0xff.
    914      */
    915     static const uint8_t bytes[]={
    916         /* well-formed UTF-8 */
    917         0x61,  0xc3, 0x9f,  0xe0, 0xa0, 0x80,  0xf0, 0xa0, 0x80, 0x80,
    918         0x62,  0xc3, 0xa0,  0xe0, 0xa0, 0x81,  0xf0, 0xa0, 0x80, 0x81, 0,
    919 
    920         /* various malformed sequences */
    921         0xc3, 0xc3, 0x9f,  0xc3, 0xa0,  0xe0, 0x80, 0x8a,  0xf0, 0x41, 0x42, 0x43, 0,
    922 
    923         /* truncated input */
    924         0xc3, 0,
    925         0xe0, 0,
    926         0xe0, 0xa0, 0,
    927         0xf0, 0,
    928         0xf0, 0x90, 0,
    929         0xf0, 0x90, 0x80, 0,
    930 
    931         /* non-ASCII characters in the last few bytes */
    932         0x61,  0xc3, 0x9f,  0xe0, 0xa0, 0x80, 0,
    933         0x61,  0xe0, 0xa0, 0x80,  0xc3, 0x9f, 0,
    934 
    935         /* empty string */
    936         0,
    937 
    938         /* finish */
    939         0xff, 0
    940     };
    941 
    942     /* Multiple output strings, each NUL-terminated. 0xfffd matches anything. */
    943     static const UChar uchars[]={
    944         0x61, 0xdf, 0x800,  0xd840, 0xdc00,
    945         0x62, 0xe0, 0x801,  0xd840, 0xdc01,  0,
    946 
    947         0xfffd, 0x9f, 0xe0, 0xa,  0xfffd, 0xfffd,  0,
    948 
    949         0xfffd, 0,
    950         0xfffd, 0,
    951         0xfffd, 0,
    952         0xfffd, 0,
    953         0xfffd, 0,
    954         0xfffd, 0,
    955 
    956         0x61, 0xdf, 0x800,  0,
    957         0x61, 0x800, 0xdf,  0,
    958 
    959         0,
    960 
    961         0
    962     };
    963 
    964     UChar dest[64];
    965     const char *pb;
    966     const UChar *pu, *pDest;
    967     int32_t srcLength, destLength0, destLength;
    968     int number;
    969     UErrorCode errorCode;
    970 
    971     /* verify checking for some illegal arguments */
    972     dest[0]=0x1234;
    973     destLength=-1;
    974     errorCode=U_ZERO_ERROR;
    975     pDest=u_strFromUTF8Lenient(dest, 1, &destLength, NULL, -1, &errorCode);
    976     if(errorCode!=U_ILLEGAL_ARGUMENT_ERROR || dest[0]!=0x1234) {
    977         log_err("u_strFromUTF8Lenient(src=NULL) failed\n");
    978     }
    979 
    980     dest[0]=0x1234;
    981     destLength=-1;
    982     errorCode=U_ZERO_ERROR;
    983     pDest=u_strFromUTF8Lenient(NULL, 1, &destLength, (const char *)bytes, -1, &errorCode);
    984     if(errorCode!=U_ILLEGAL_ARGUMENT_ERROR) {
    985         log_err("u_strFromUTF8Lenient(dest=NULL[1]) failed\n");
    986     }
    987 
    988     dest[0]=0x1234;
    989     destLength=-1;
    990     errorCode=U_MEMORY_ALLOCATION_ERROR;
    991     pDest=u_strFromUTF8Lenient(dest, 1, &destLength, (const char *)bytes, -1, &errorCode);
    992     if(errorCode!=U_MEMORY_ALLOCATION_ERROR || dest[0]!=0x1234) {
    993         log_err("u_strFromUTF8Lenient(U_MEMORY_ALLOCATION_ERROR) failed\n");
    994     }
    995 
    996     dest[0]=0x1234;
    997     destLength=-1;
    998     errorCode=U_MEMORY_ALLOCATION_ERROR;
    999     pDest=u_strFromUTF8Lenient(dest, 1, &destLength, (const char *)bytes, -1, NULL);
   1000     if(dest[0]!=0x1234) {
   1001         log_err("u_strFromUTF8Lenient(pErrorCode=NULL) failed\n");
   1002     }
   1003 
   1004     /* test normal behavior */
   1005     number=0; /* string number for log_err() */
   1006 
   1007     for(pb=(const char *)bytes, pu=uchars;
   1008         *pb!=(char)0xff;
   1009         pb+=srcLength+1, pu+=destLength0+1, ++number
   1010     ) {
   1011         srcLength=uprv_strlen(pb);
   1012         destLength0=u_strlen(pu);
   1013 
   1014         /* preflighting with NUL-termination */
   1015         dest[0]=0x1234;
   1016         destLength=-1;
   1017         errorCode=U_ZERO_ERROR;
   1018         pDest=u_strFromUTF8Lenient(NULL, 0, &destLength, pb, -1, &errorCode);
   1019         if (errorCode!= (destLength0==0 ? U_STRING_NOT_TERMINATED_WARNING : U_BUFFER_OVERFLOW_ERROR) ||
   1020             pDest!=NULL || dest[0]!=0x1234 || destLength!=destLength0
   1021         ) {
   1022             log_err("u_strFromUTF8Lenient(%d preflighting with NUL-termination) failed\n", number);
   1023         }
   1024 
   1025         /* preflighting/some capacity with NUL-termination */
   1026         if(srcLength>0) {
   1027             dest[destLength0-1]=0x1234;
   1028             destLength=-1;
   1029             errorCode=U_ZERO_ERROR;
   1030             pDest=u_strFromUTF8Lenient(dest, destLength0-1, &destLength, pb, -1, &errorCode);
   1031             if (errorCode!=U_BUFFER_OVERFLOW_ERROR ||
   1032                 dest[destLength0-1]!=0x1234 || destLength!=destLength0
   1033             ) {
   1034                 log_err("u_strFromUTF8Lenient(%d preflighting/some capacity with NUL-termination) failed\n", number);
   1035             }
   1036         }
   1037 
   1038         /* conversion with NUL-termination, much capacity */
   1039         dest[0]=dest[destLength0]=0x1234;
   1040         destLength=-1;
   1041         errorCode=U_ZERO_ERROR;
   1042         pDest=u_strFromUTF8Lenient(dest, LENGTHOF(dest), &destLength, pb, -1, &errorCode);
   1043         if (errorCode!=U_ZERO_ERROR ||
   1044             pDest!=dest || dest[destLength0]!=0 ||
   1045             destLength!=destLength0 || !equalAnyFFFD(dest, pu, destLength)
   1046         ) {
   1047             log_err("u_strFromUTF8Lenient(%d conversion with NUL-termination, much capacity) failed\n", number);
   1048         }
   1049 
   1050         /* conversion with NUL-termination, exact capacity */
   1051         dest[0]=dest[destLength0]=0x1234;
   1052         destLength=-1;
   1053         errorCode=U_ZERO_ERROR;
   1054         pDest=u_strFromUTF8Lenient(dest, destLength0, &destLength, pb, -1, &errorCode);
   1055         if (errorCode!=U_STRING_NOT_TERMINATED_WARNING ||
   1056             pDest!=dest || dest[destLength0]!=0x1234 ||
   1057             destLength!=destLength0 || !equalAnyFFFD(dest, pu, destLength)
   1058         ) {
   1059             log_err("u_strFromUTF8Lenient(%d conversion with NUL-termination, exact capacity) failed\n", number);
   1060         }
   1061 
   1062         /* preflighting with length */
   1063         dest[0]=0x1234;
   1064         destLength=-1;
   1065         errorCode=U_ZERO_ERROR;
   1066         pDest=u_strFromUTF8Lenient(NULL, 0, &destLength, pb, srcLength, &errorCode);
   1067         if (errorCode!= (destLength0==0 ? U_STRING_NOT_TERMINATED_WARNING : U_BUFFER_OVERFLOW_ERROR) ||
   1068             pDest!=NULL || dest[0]!=0x1234 || destLength!=srcLength
   1069         ) {
   1070             log_err("u_strFromUTF8Lenient(%d preflighting with length) failed\n", number);
   1071         }
   1072 
   1073         /* preflighting/some capacity with length */
   1074         if(srcLength>0) {
   1075             dest[srcLength-1]=0x1234;
   1076             destLength=-1;
   1077             errorCode=U_ZERO_ERROR;
   1078             pDest=u_strFromUTF8Lenient(dest, srcLength-1, &destLength, pb, srcLength, &errorCode);
   1079             if (errorCode!=U_BUFFER_OVERFLOW_ERROR ||
   1080                 dest[srcLength-1]!=0x1234 || destLength!=srcLength
   1081             ) {
   1082                 log_err("u_strFromUTF8Lenient(%d preflighting/some capacity with length) failed\n", number);
   1083             }
   1084         }
   1085 
   1086         /* conversion with length, much capacity */
   1087         dest[0]=dest[destLength0]=0x1234;
   1088         destLength=-1;
   1089         errorCode=U_ZERO_ERROR;
   1090         pDest=u_strFromUTF8Lenient(dest, LENGTHOF(dest), &destLength, pb, srcLength, &errorCode);
   1091         if (errorCode!=U_ZERO_ERROR ||
   1092             pDest!=dest || dest[destLength0]!=0 ||
   1093             destLength!=destLength0 || !equalAnyFFFD(dest, pu, destLength)
   1094         ) {
   1095             log_err("u_strFromUTF8Lenient(%d conversion with length, much capacity) failed\n", number);
   1096         }
   1097 
   1098         /* conversion with length, srcLength capacity */
   1099         dest[0]=dest[srcLength]=dest[destLength0]=0x1234;
   1100         destLength=-1;
   1101         errorCode=U_ZERO_ERROR;
   1102         pDest=u_strFromUTF8Lenient(dest, srcLength, &destLength, pb, srcLength, &errorCode);
   1103         if(srcLength==destLength0) {
   1104             if (errorCode!=U_STRING_NOT_TERMINATED_WARNING ||
   1105                 pDest!=dest || dest[destLength0]!=0x1234 ||
   1106                 destLength!=destLength0 || !equalAnyFFFD(dest, pu, destLength)
   1107             ) {
   1108                 log_err("u_strFromUTF8Lenient(%d conversion with length, srcLength capacity/not terminated) failed\n", number);
   1109             }
   1110         } else {
   1111             if (errorCode!=U_ZERO_ERROR ||
   1112                 pDest!=dest || dest[destLength0]!=0 ||
   1113                 destLength!=destLength0 || !equalAnyFFFD(dest, pu, destLength)
   1114             ) {
   1115                 log_err("u_strFromUTF8Lenient(%d conversion with length, srcLength capacity/terminated) failed\n", number);
   1116             }
   1117         }
   1118     }
   1119 }
   1120 
   1121 static const uint16_t src16j[] = {
   1122     0x0043, 0x0044, 0x0045, 0x0046, 0x0047, 0x0048, 0x0049, 0x004A, 0x000D, 0x000A,
   1123     0x004B, 0x004C, 0x004D, 0x004E, 0x004F, 0x0050, 0x0051, 0x0052, 0x000D, 0x000A,
   1124     0x0053, 0x0054, 0x0055, 0x0056, 0x0057, 0x0058, 0x0059, 0x005A, 0x000D, 0x000A,
   1125     0x0053, 0x0054, 0x0055, 0x0056, 0x0057, 0x0058, 0x0059, 0x005A, 0x000D, 0x000A,
   1126     0x0000,
   1127     /* Test only ASCII */
   1128 
   1129 };
   1130 static const uint16_t src16WithNulls[] = {
   1131     0x0043, 0x0044, 0x0045, 0x0046, 0x0047, 0x0000,
   1132     0x0048, 0x0049, 0x004A, 0x000D, 0x000A, 0x0000,
   1133     0x004B, 0x004C, 0x004D, 0x004E, 0x004F, 0x0000,
   1134     0x0050, 0x0051, 0x0052, 0x000D, 0x000A, 0x0000,
   1135     0x0053, 0x0054, 0x0055, 0x0056, 0x0057, 0x0000,
   1136     0x0058, 0x0059, 0x005A, 0x000D, 0x000A, 0x0000,
   1137     0x0053, 0x0054, 0x0055, 0x0056, 0x0057, 0x0000,
   1138     0x0058, 0x0059, 0x005A, 0x000D, 0x000A, 0x0000,
   1139     /* test only ASCII */
   1140     /*
   1141     0x00A8, 0x00A9, 0x00AA, 0x00AB, 0x00AC, 0x00AD,
   1142     0x00AE, 0x00AF, 0x00B0, 0x00B1, 0x00B2, 0x00B3, 0x00B4, 0x00B5, 0x00B6, 0x00B7,
   1143     0x00B8, 0x00B9, 0x00BA, 0x00BB, 0x00BC, 0x00BD, 0x00BE, 0x00BF, 0x00C0, 0x00C1,
   1144     0x00C2, 0x00C3, 0x00C4, 0x00C5, 0x00C6, 0x00C7, 0x00C8, 0x00C9, 0x00CA, 0x00CB,
   1145     0x00CC, 0x00CD, 0x00CE, 0x00CF, 0x00D0, 0x00D1, 0x00D2, 0x00D3, 0x00D4, 0x00D5,
   1146     0x00D6, 0x00D7, 0x00D8, 0x00D9, 0x00DA, 0x00DB, 0x00DC, 0x00DD, 0x00DE, 0x00DF,
   1147     0x00E0, 0x00E1, 0x00E2, 0x00E3, 0x00E4, 0x00E5, 0x00E6, 0x00E7, 0x00E8, 0x00E9,
   1148     0x0054, 0x0000 */
   1149 
   1150 };
   1151 static void Test_UChar_WCHART_API(void){
   1152 #if (defined(U_WCHAR_IS_UTF16) || defined(U_WCHAR_IS_UTF32)) || (!UCONFIG_NO_CONVERSION && !UCONFIG_NO_LEGACY_CONVERSION)
   1153     UErrorCode err = U_ZERO_ERROR;
   1154     const UChar* uSrc = src16j;
   1155     int32_t uSrcLen = sizeof(src16j)/2;
   1156     wchar_t* wDest = NULL;
   1157     int32_t wDestLen = 0;
   1158     int32_t reqLen= 0 ;
   1159     UBool failed = FALSE;
   1160     UChar* uDest = NULL;
   1161     int32_t uDestLen = 0;
   1162     int i =0;
   1163     {
   1164         /* Bad UErrorCode arguments. Make sure that the API doesn't crash, and that Purify doesn't complain. */
   1165         if (u_strFromWCS(NULL,0,NULL,NULL,0,NULL) != NULL) {
   1166             log_err("u_strFromWCS() should return NULL with a bad argument\n");
   1167         }
   1168         if (u_strToWCS(NULL,0,NULL,NULL,0,NULL) != NULL) {
   1169             log_err("u_strToWCS() should return NULL with a bad argument\n");
   1170         }
   1171 
   1172         /* Bad UErrorCode arguments. */
   1173         err = U_ZERO_ERROR;
   1174         u_strFromWCS(NULL,0,NULL,NULL,0,&err);
   1175         if (err != U_ILLEGAL_ARGUMENT_ERROR) {
   1176             log_err("u_strFromWCS() didn't fail as expected with bad arguments. Error: %s \n", u_errorName(err));
   1177         }
   1178         err = U_ZERO_ERROR;
   1179         u_strToWCS(NULL,0,NULL,NULL,0,&err);
   1180         if (err != U_ILLEGAL_ARGUMENT_ERROR) {
   1181             log_err("u_strToWCS() didn't fail as expected with bad arguments. Error: %s \n", u_errorName(err));
   1182         }
   1183         err = U_ZERO_ERROR;
   1184 
   1185         /* pre-flight*/
   1186         u_strToWCS(wDest,wDestLen,&reqLen,uSrc,uSrcLen-1,&err);
   1187 
   1188         if(err == U_BUFFER_OVERFLOW_ERROR){
   1189             err=U_ZERO_ERROR;
   1190             wDest =(wchar_t*) malloc(sizeof(wchar_t) * (reqLen+1));
   1191             wDestLen = reqLen+1;
   1192             u_strToWCS(wDest,wDestLen,&reqLen,uSrc,uSrcLen-1,&err);
   1193         }
   1194 
   1195         /* pre-flight */
   1196         u_strFromWCS(uDest, uDestLen,&reqLen,wDest,reqLen,&err);
   1197 
   1198 
   1199         if(err == U_BUFFER_OVERFLOW_ERROR){
   1200             err =U_ZERO_ERROR;
   1201             uDest = (UChar*) malloc(sizeof(UChar) * (reqLen+1));
   1202             uDestLen = reqLen + 1;
   1203             u_strFromWCS(uDest, uDestLen,&reqLen,wDest,reqLen,&err);
   1204         }else if(U_FAILURE(err)){
   1205 
   1206             log_err("u_strFromWCS() failed. Error: %s \n", u_errorName(err));
   1207             return;
   1208         }
   1209 
   1210         for(i=0; i< uSrcLen; i++){
   1211             if(uDest[i] != src16j[i]){
   1212                 log_verbose("u_str*WCS() failed for unterminated string expected: \\u%04X got: \\u%04X at index: %i \n", src16j[i] ,uDest[i],i);
   1213                 failed =TRUE;
   1214             }
   1215         }
   1216 
   1217         if(U_FAILURE(err)){
   1218             failed = TRUE;
   1219         }
   1220         if(failed){
   1221             log_err("u_strToWCS() failed \n");
   1222         }
   1223         free(wDest);
   1224         free(uDest);
   1225 
   1226 
   1227         /* test with embeded nulls */
   1228         uSrc = src16WithNulls;
   1229         uSrcLen = sizeof(src16WithNulls)/2;
   1230         wDestLen =0;
   1231         uDestLen =0;
   1232         wDest = NULL;
   1233         uDest = NULL;
   1234         /* pre-flight*/
   1235         u_strToWCS(wDest,wDestLen,&reqLen,uSrc,uSrcLen-1,&err);
   1236 
   1237         if(err == U_BUFFER_OVERFLOW_ERROR){
   1238             err=U_ZERO_ERROR;
   1239             wDest =(wchar_t*) malloc(sizeof(wchar_t) * (reqLen+1));
   1240             wDestLen = reqLen+1;
   1241             u_strToWCS(wDest,wDestLen,&reqLen,uSrc,uSrcLen-1,&err);
   1242         }
   1243 
   1244         /* pre-flight */
   1245         u_strFromWCS(uDest, uDestLen,&reqLen,wDest,reqLen,&err);
   1246 
   1247         if(err == U_BUFFER_OVERFLOW_ERROR){
   1248             err =U_ZERO_ERROR;
   1249             uDest = (UChar*) malloc(sizeof(UChar) * (reqLen+1));
   1250             uDestLen = reqLen + 1;
   1251             u_strFromWCS(uDest, uDestLen,&reqLen,wDest,reqLen,&err);
   1252         }
   1253 
   1254         if(!U_FAILURE(err)) {
   1255          for(i=0; i< uSrcLen; i++){
   1256             if(uDest[i] != src16WithNulls[i]){
   1257                 log_verbose("u_str*WCS() failed for string with nulls expected: \\u%04X got: \\u%04X at index: %i \n", src16WithNulls[i] ,uDest[i],i);
   1258                 failed =TRUE;
   1259             }
   1260          }
   1261         }
   1262 
   1263         if(U_FAILURE(err)){
   1264             failed = TRUE;
   1265         }
   1266         if(failed){
   1267             log_err("u_strToWCS() failed \n");
   1268         }
   1269         free(wDest);
   1270         free(uDest);
   1271 
   1272     }
   1273 
   1274     {
   1275 
   1276         uSrc = src16j;
   1277         uSrcLen = sizeof(src16j)/2;
   1278         wDestLen =0;
   1279         uDestLen =0;
   1280         wDest = NULL;
   1281         uDest = NULL;
   1282         wDestLen = 0;
   1283         /* pre-flight*/
   1284         u_strToWCS(wDest,wDestLen,&reqLen,uSrc,-1,&err);
   1285 
   1286         if(err == U_BUFFER_OVERFLOW_ERROR){
   1287             err=U_ZERO_ERROR;
   1288             wDest =(wchar_t*) malloc(sizeof(wchar_t) * (reqLen+1));
   1289             wDestLen = reqLen+1;
   1290             u_strToWCS(wDest,wDestLen,&reqLen,uSrc,-1,&err);
   1291         }
   1292         uDestLen = 0;
   1293         /* pre-flight */
   1294         u_strFromWCS(uDest, uDestLen,&reqLen,wDest,-1,&err);
   1295 
   1296         if(err == U_BUFFER_OVERFLOW_ERROR){
   1297             err =U_ZERO_ERROR;
   1298             uDest = (UChar*) malloc(sizeof(UChar) * (reqLen+1));
   1299             uDestLen = reqLen + 1;
   1300             u_strFromWCS(uDest, uDestLen,&reqLen,wDest,-1,&err);
   1301         }
   1302 
   1303 
   1304         if(!U_FAILURE(err)) {
   1305          for(i=0; i< uSrcLen; i++){
   1306             if(uDest[i] != src16j[i]){
   1307                 log_verbose("u_str*WCS() failed for null terminated string expected: \\u%04X got: \\u%04X at index: %i \n", src16j[i] ,uDest[i],i);
   1308                 failed =TRUE;
   1309             }
   1310          }
   1311         }
   1312 
   1313         if(U_FAILURE(err)){
   1314             failed = TRUE;
   1315         }
   1316         if(failed){
   1317             log_err("u_strToWCS() failed \n");
   1318         }
   1319         free(wDest);
   1320         free(uDest);
   1321     }
   1322 
   1323     /*
   1324      * Test u_terminateWChars().
   1325      * All u_terminateXYZ() use the same implementation macro;
   1326      * we test this function to improve API coverage.
   1327      */
   1328     {
   1329         wchar_t buffer[10];
   1330 
   1331         err=U_ZERO_ERROR;
   1332         buffer[3]=0x20ac;
   1333         wDestLen=u_terminateWChars(buffer, LENGTHOF(buffer), 3, &err);
   1334         if(err!=U_ZERO_ERROR || wDestLen!=3 || buffer[3]!=0) {
   1335             log_err("u_terminateWChars(buffer, all, 3, zero) failed: %s length %d [3]==U+%04x\n",
   1336                     u_errorName(err), wDestLen, buffer[3]);
   1337         }
   1338 
   1339         err=U_ZERO_ERROR;
   1340         buffer[3]=0x20ac;
   1341         wDestLen=u_terminateWChars(buffer, 3, 3, &err);
   1342         if(err!=U_STRING_NOT_TERMINATED_WARNING || wDestLen!=3 || buffer[3]!=0x20ac) {
   1343             log_err("u_terminateWChars(buffer, 3, 3, zero) failed: %s length %d [3]==U+%04x\n",
   1344                     u_errorName(err), wDestLen, buffer[3]);
   1345         }
   1346 
   1347         err=U_STRING_NOT_TERMINATED_WARNING;
   1348         buffer[3]=0x20ac;
   1349         wDestLen=u_terminateWChars(buffer, LENGTHOF(buffer), 3, &err);
   1350         if(err!=U_ZERO_ERROR || wDestLen!=3 || buffer[3]!=0) {
   1351             log_err("u_terminateWChars(buffer, all, 3, not-terminated) failed: %s length %d [3]==U+%04x\n",
   1352                     u_errorName(err), wDestLen, buffer[3]);
   1353         }
   1354 
   1355         err=U_ZERO_ERROR;
   1356         buffer[3]=0x20ac;
   1357         wDestLen=u_terminateWChars(buffer, 2, 3, &err);
   1358         if(err!=U_BUFFER_OVERFLOW_ERROR || wDestLen!=3 || buffer[3]!=0x20ac) {
   1359             log_err("u_terminateWChars(buffer, 2, 3, zero) failed: %s length %d [3]==U+%04x\n",
   1360                     u_errorName(err), wDestLen, buffer[3]);
   1361         }
   1362     }
   1363 #else
   1364     log_info("Not testing u_str*WCS because (!UCONFIG_NO_CONVERSION && !UCONFIG_NO_LEGACY_CONVERSION) and wchar is neither utf16 nor utf32");
   1365 #endif
   1366 }
   1367 
   1368 static void Test_widestrs()
   1369 {
   1370 #if (defined(U_WCHAR_IS_UTF16) || defined(U_WCHAR_IS_UTF32)) || (!UCONFIG_NO_CONVERSION && !UCONFIG_NO_LEGACY_CONVERSION)
   1371         wchar_t ws[100];
   1372         UChar rts[100];
   1373         int32_t wcap = sizeof(ws) / sizeof(*ws);
   1374         int32_t wl;
   1375         int32_t rtcap = sizeof(rts) / sizeof(*rts);
   1376         int32_t rtl;
   1377         wchar_t *wcs;
   1378         UChar *cp;
   1379         const char *errname;
   1380         UChar ustr[] = {'h', 'e', 'l', 'l', 'o', 0};
   1381         int32_t ul = sizeof(ustr)/sizeof(*ustr) -1;
   1382         char astr[100];
   1383 
   1384         UErrorCode err;
   1385 
   1386         err = U_ZERO_ERROR;
   1387         wcs = u_strToWCS(ws, wcap, &wl, ustr, ul, &err);
   1388         if (U_FAILURE(err)) {
   1389                 errname = u_errorName(err);
   1390                 log_err("test_widestrs: u_strToWCS error: %s!\n",errname);
   1391         }
   1392         if(ul!=wl){
   1393             log_err("u_strToWCS: ustr = %s, ul = %d, ws = %S, wl = %d!\n", u_austrcpy(astr, ustr), ul, ws, wl);
   1394         }
   1395         err = U_ZERO_ERROR;
   1396         wl = (int32_t)uprv_wcslen(wcs);
   1397         cp = u_strFromWCS(rts, rtcap, &rtl, wcs, wl, &err);
   1398         if (U_FAILURE(err)) {
   1399                 errname = u_errorName(err);
   1400                 fprintf(stderr, "test_widestrs: ucnv_wcstombs error: %s!\n",errname);
   1401         }
   1402         if(wl != rtl){
   1403             log_err("u_strFromWCS: wcs = %S, wl = %d,rts = %s, rtl = %d!\n", wcs, wl, u_austrcpy(astr, rts), rtl);
   1404         }
   1405 #else
   1406     log_info("Not testing u_str*WCS because (!UCONFIG_NO_CONVERSION && !UCONFIG_NO_LEGACY_CONVERSION) and wchar is neither utf16 nor utf32");
   1407 #endif
   1408 }
   1409 
   1410 static void
   1411 Test_WCHART_LongString(){
   1412 #if (defined(U_WCHAR_IS_UTF16) || defined(U_WCHAR_IS_UTF32)) || (!UCONFIG_NO_CONVERSION && !UCONFIG_NO_LEGACY_CONVERSION)
   1413     UErrorCode status = U_ZERO_ERROR;
   1414     const char* testdatapath=loadTestData(&status);
   1415     UResourceBundle *theBundle = ures_open(testdatapath, "testtypes", &status);
   1416     int32_t strLen =0;
   1417     const UChar* str = ures_getStringByKey(theBundle, "testinclude",&strLen,&status);
   1418     const UChar* uSrc = str;
   1419     int32_t uSrcLen = strLen;
   1420     int32_t wDestLen =0, reqLen=0, i=0;
   1421     int32_t uDestLen =0;
   1422     wchar_t* wDest = NULL;
   1423     UChar* uDest = NULL;
   1424     UBool failed = FALSE;
   1425 
   1426     if(U_FAILURE(status)){
   1427         log_data_err("Could not get testinclude resource from testtypes bundle. Error: %s\n",u_errorName(status));
   1428         return;
   1429     }
   1430 
   1431     /* pre-flight*/
   1432     u_strToWCS(wDest,wDestLen,&reqLen,uSrc,-1,&status);
   1433 
   1434     if(status == U_BUFFER_OVERFLOW_ERROR){
   1435         status=U_ZERO_ERROR;
   1436         wDest =(wchar_t*) malloc(sizeof(wchar_t) * (reqLen+1));
   1437         wDestLen = reqLen+1;
   1438         u_strToWCS(wDest,wDestLen,&reqLen,uSrc,-1,&status);
   1439     }
   1440     uDestLen = 0;
   1441     /* pre-flight */
   1442     u_strFromWCS(uDest, uDestLen,&reqLen,wDest,-1,&status);
   1443 
   1444     if(status == U_BUFFER_OVERFLOW_ERROR){
   1445         status =U_ZERO_ERROR;
   1446         uDest = (UChar*) malloc(sizeof(UChar) * (reqLen+1));
   1447         uDestLen = reqLen + 1;
   1448         u_strFromWCS(uDest, uDestLen,&reqLen,wDest,-1,&status);
   1449     }
   1450 
   1451 
   1452     for(i=0; i< uSrcLen; i++){
   1453         if(uDest[i] != str[i]){
   1454             log_verbose("u_str*WCS() failed for null terminated string expected: \\u%04X got: \\u%04X at index: %i \n", src16j[i] ,uDest[i],i);
   1455             failed =TRUE;
   1456         }
   1457     }
   1458 
   1459     if(U_FAILURE(status)){
   1460         failed = TRUE;
   1461     }
   1462     if(failed){
   1463         log_err("u_strToWCS() failed \n");
   1464     }
   1465     free(wDest);
   1466     free(uDest);
   1467     /* close the bundle */
   1468     ures_close(theBundle);
   1469 #else
   1470     log_info("Not testing u_str*WCS because (!UCONFIG_NO_CONVERSION && !UCONFIG_NO_LEGACY_CONVERSION) and wchar is neither utf16 nor utf32");
   1471 #endif
   1472 }
   1473 
   1474