Home | History | Annotate | Download | only in unit
      1 #include "locale_test.h"
      2 
      3 #if !defined (STLPORT) || !defined (_STLP_USE_NO_IOSTREAMS)
      4 #  include <locale>
      5 #  include <stdexcept>
      6 
      7 #  if !defined (STLPORT) || defined(_STLP_USE_NAMESPACES)
      8 using namespace std;
      9 #  endif
     10 
     11 static const char* tested_locales[] = {
     12 //name,
     13 #  if !defined (STLPORT) || defined (_STLP_USE_EXCEPTIONS)
     14   // We need exception support to check support of the following localizations.
     15   "fr_FR",
     16   "ru_RU.koi8r",
     17   "en_GB",
     18   "en_US",
     19 #  endif
     20   "",
     21   "C"
     22 };
     23 
     24 //
     25 // tests implementation
     26 //
     27 void LocaleTest::_ctype_facet( const locale& loc)
     28 {
     29   CPPUNIT_ASSERT( has_facet<ctype<char> >(loc) );
     30   ctype<char> const& ct = use_facet<ctype<char> >(loc);
     31   //is
     32   {
     33     CPPUNIT_ASSERT( ct.is(ctype_base::digit, '0') );
     34     CPPUNIT_ASSERT( ct.is(ctype_base::upper, 'A') );
     35     CPPUNIT_ASSERT( ct.is(ctype_base::lower, 'a') );
     36     CPPUNIT_ASSERT( ct.is(ctype_base::alpha, 'A') );
     37     CPPUNIT_ASSERT( ct.is(ctype_base::space, ' ') );
     38     CPPUNIT_ASSERT( !ct.is(ctype_base::space, '2') );
     39     CPPUNIT_ASSERT( ct.is(ctype_base::punct, '.') );
     40     CPPUNIT_ASSERT( ct.is(ctype_base::xdigit, 'a') );
     41   }
     42 
     43   //is range
     44   {
     45     char values[] = "0Aa .";
     46     ctype_base::mask res[sizeof(values)];
     47     ct.is(values, values + sizeof(values), res);
     48     // '0'
     49     CPPUNIT_ASSERT( (res[0] & ctype_base::print) != 0 );
     50     CPPUNIT_ASSERT( (res[0] & ctype_base::digit) != 0 );
     51     CPPUNIT_ASSERT( (res[0] & ctype_base::xdigit) != 0 );
     52     // 'A'
     53     CPPUNIT_ASSERT( (res[1] & ctype_base::print) != 0 );
     54     CPPUNIT_ASSERT( (res[1] & ctype_base::alpha) != 0 );
     55     CPPUNIT_ASSERT( (res[1] & ctype_base::xdigit) != 0 );
     56     CPPUNIT_ASSERT( (res[1] & ctype_base::upper) != 0 );
     57     // 'a'
     58     CPPUNIT_ASSERT( (res[2] & ctype_base::print) != 0 );
     59     CPPUNIT_ASSERT( (res[2] & ctype_base::alpha) != 0 );
     60     CPPUNIT_ASSERT( (res[2] & ctype_base::xdigit) != 0 );
     61     CPPUNIT_ASSERT( (res[2] & ctype_base::lower) != 0 );
     62     CPPUNIT_ASSERT( (res[2] & ctype_base::space) == 0 );
     63     // ' '
     64     CPPUNIT_ASSERT( (res[3] & ctype_base::print) != 0 );
     65     CPPUNIT_ASSERT( (res[3] & ctype_base::space) != 0 );
     66     CPPUNIT_ASSERT( (res[3] & ctype_base::digit) == 0 );
     67     // '.'
     68     CPPUNIT_ASSERT( (res[4] & ctype_base::print) != 0 );
     69     CPPUNIT_ASSERT( (res[4] & ctype_base::punct) != 0 );
     70     CPPUNIT_ASSERT( (res[4] & ctype_base::digit) == 0 );
     71   }
     72 
     73   //scan_is
     74   {
     75     char range[] = "abAc123 .";
     76     const char *rbeg = range;
     77     const char *rend = range + sizeof(range);
     78 
     79     const char *res;
     80     res = ct.scan_is((ctype_base::mask)(ctype_base::alpha | ctype_base::lower), rbeg, rend);
     81     CPPUNIT_ASSERT( res != rend );
     82     CPPUNIT_ASSERT( *res == 'a' );
     83 
     84     res = ct.scan_is(ctype_base::upper, rbeg, rend);
     85     CPPUNIT_ASSERT( res != rend );
     86     CPPUNIT_ASSERT( *res == 'A' );
     87 
     88     res = ct.scan_is(ctype_base::punct, rbeg, rend);
     89     CPPUNIT_ASSERT( res != rend );
     90     CPPUNIT_ASSERT( *res == '.' );
     91   }
     92 
     93   //scan_not
     94   {
     95     char range[] = "abAc123 .";
     96     const char *rbeg = range;
     97     const char *rend = range + sizeof(range);
     98 
     99     const char *res;
    100     res = ct.scan_not((ctype_base::mask)(ctype_base::alpha | ctype_base::lower), rbeg, rend);
    101     CPPUNIT_ASSERT( res != rend );
    102     CPPUNIT_ASSERT( *res == '1' );
    103 
    104     res = ct.scan_not(ctype_base::alpha, rbeg, rend);
    105     CPPUNIT_ASSERT( res != rend );
    106     CPPUNIT_ASSERT( *res == '1' );
    107 
    108     res = ct.scan_not(ctype_base::punct, rbeg, rend);
    109     CPPUNIT_ASSERT( res != rend );
    110     CPPUNIT_ASSERT( *res == 'a' );
    111   }
    112 
    113   //toupper
    114   {
    115     CPPUNIT_ASSERT( ct.toupper('a') == 'A' );
    116     CPPUNIT_ASSERT( ct.toupper('A') == 'A' );
    117     CPPUNIT_ASSERT( ct.toupper('1') == '1' );
    118   }
    119 
    120   //toupper range
    121   {
    122     char range[] = "abAc1";
    123     char expected_range[] = "ABAC1";
    124     ct.toupper(range, range + sizeof(range));
    125     CPPUNIT_ASSERT( equal(range, range + sizeof(range), expected_range) );
    126   }
    127 
    128   //tolower
    129   {
    130     CPPUNIT_ASSERT( ct.tolower('A') == 'a' );
    131     CPPUNIT_ASSERT( ct.tolower('a') == 'a' );
    132     CPPUNIT_ASSERT( ct.tolower('1') == '1' );
    133   }
    134 
    135   //tolower range
    136   {
    137     char range[] = "ABaC1";
    138     char expected_range[] = "abac1";
    139     ct.tolower(range, range + sizeof(range));
    140     CPPUNIT_ASSERT( equal(range, range + sizeof(range), expected_range) );
    141   }
    142 
    143   //widen
    144   {
    145     CPPUNIT_ASSERT( ct.widen('a') == 'a' );
    146   }
    147 
    148   //widen range
    149   {
    150     char range[] = "ABaC1";
    151     char res[sizeof(range)];
    152     ct.widen(range, range + sizeof(range), res);
    153     CPPUNIT_ASSERT( equal(range, range + sizeof(range), res) );
    154   }
    155 
    156   //narrow
    157   {
    158     CPPUNIT_ASSERT( ct.narrow('a', 'b') == 'a' );
    159   }
    160 
    161   //narrow range
    162   {
    163     char range[] = "ABaC1";
    164     char res[sizeof(range)];
    165     ct.narrow(range, range + sizeof(range), 'b', res);
    166     CPPUNIT_ASSERT( equal(range, range + sizeof(range), res) );
    167   }
    168 }
    169 
    170 void LocaleTest::_ctype_facet_w( const locale& loc )
    171 {
    172 # ifndef _STLP_NO_WCHAR_T
    173   CPPUNIT_ASSERT( has_facet<ctype<wchar_t> >(loc) );
    174   ctype<wchar_t> const& wct = use_facet<ctype<wchar_t> >(loc);
    175   //is
    176   {
    177     CPPUNIT_CHECK( wct.is(ctype_base::digit, L'0') );
    178     CPPUNIT_CHECK( wct.is(ctype_base::upper, L'A') );
    179     CPPUNIT_CHECK( wct.is(ctype_base::lower, L'a') );
    180     CPPUNIT_CHECK( wct.is(ctype_base::alpha, L'A') );
    181     CPPUNIT_CHECK( wct.is(ctype_base::space, L' ') );
    182     CPPUNIT_CHECK( !wct.is(ctype_base::space, L'2') );
    183     CPPUNIT_CHECK( wct.is(ctype_base::punct, L'.') );
    184     CPPUNIT_CHECK( wct.is(ctype_base::xdigit, L'a') );
    185   }
    186 
    187   //is range
    188   {
    189     wchar_t values[] = L"0Aa .";
    190     ctype_base::mask res[sizeof(values) / sizeof(wchar_t)];
    191     wct.is(values, values + (sizeof(values) / sizeof(wchar_t)), res);
    192     // '0'
    193     CPPUNIT_CHECK( (res[0] & ctype_base::print) != 0 );
    194     CPPUNIT_CHECK( (res[0] & ctype_base::digit) != 0 );
    195     CPPUNIT_CHECK( (res[0] & ctype_base::xdigit) != 0 );
    196     // 'A'
    197     CPPUNIT_CHECK( (res[1] & ctype_base::print) != 0 );
    198     CPPUNIT_CHECK( (res[1] & ctype_base::alpha) != 0 );
    199     CPPUNIT_CHECK( (res[1] & ctype_base::xdigit) != 0 );
    200     CPPUNIT_CHECK( (res[1] & ctype_base::upper) != 0 );
    201     // 'a'
    202     CPPUNIT_CHECK( (res[2] & ctype_base::print) != 0 );
    203     CPPUNIT_CHECK( (res[2] & ctype_base::alpha) != 0 );
    204     CPPUNIT_CHECK( (res[2] & ctype_base::xdigit) != 0 );
    205     CPPUNIT_CHECK( (res[2] & ctype_base::lower) != 0 );
    206     CPPUNIT_CHECK( (res[2] & ctype_base::space) == 0 );
    207     // ' '
    208     CPPUNIT_CHECK( (res[3] & ctype_base::print) != 0 );
    209     CPPUNIT_CHECK( (res[3] & ctype_base::space) != 0 );
    210     CPPUNIT_CHECK( (res[3] & ctype_base::digit) == 0 );
    211     // '.'
    212     CPPUNIT_CHECK( (res[4] & ctype_base::print) != 0 );
    213     CPPUNIT_CHECK( (res[4] & ctype_base::punct) != 0 );
    214     CPPUNIT_CHECK( (res[4] & ctype_base::digit) == 0 );
    215   }
    216 
    217   //scan_is
    218   {
    219     wchar_t range[] = L"abAc123 .";
    220     const wchar_t *rbeg = range;
    221     const wchar_t *rend = range + (sizeof(range) / sizeof(wchar_t));
    222 
    223     const wchar_t *res;
    224     res = wct.scan_is((ctype_base::mask)(ctype_base::alpha | ctype_base::lower), rbeg, rend);
    225     CPPUNIT_CHECK( res != rend );
    226     CPPUNIT_CHECK( *res == L'a' );
    227 
    228     res = wct.scan_is(ctype_base::upper, rbeg, rend);
    229     CPPUNIT_CHECK( res != rend );
    230     CPPUNIT_CHECK( *res == L'A' );
    231 
    232     res = wct.scan_is(ctype_base::punct, rbeg, rend);
    233     CPPUNIT_CHECK( res != rend );
    234     CPPUNIT_CHECK( *res == L'.' );
    235   }
    236 
    237   //scan_not
    238   {
    239     wchar_t range[] = L"abAc123 .";
    240     const wchar_t *rbeg = range;
    241     const wchar_t *rend = range + (sizeof(range) / sizeof(wchar_t));
    242 
    243     const wchar_t *res;
    244     res = wct.scan_not((ctype_base::mask)(ctype_base::alpha | ctype_base::lower), rbeg, rend);
    245     CPPUNIT_CHECK( res != rend );
    246     CPPUNIT_CHECK( *res == L'1' );
    247 
    248     res = wct.scan_not(ctype_base::alpha, rbeg, rend);
    249     CPPUNIT_CHECK( res != rend );
    250     CPPUNIT_CHECK( *res == L'1' );
    251 
    252     res = wct.scan_not(ctype_base::punct, rbeg, rend);
    253     CPPUNIT_CHECK( res != rend );
    254     CPPUNIT_CHECK( *res == L'a' );
    255   }
    256 
    257   //toupper
    258   {
    259     CPPUNIT_CHECK( wct.toupper(L'a') == L'A' );
    260     CPPUNIT_CHECK( wct.toupper(L'A') == L'A' );
    261     CPPUNIT_CHECK( wct.toupper(L'1') == L'1' );
    262   }
    263 
    264   //toupper range
    265   {
    266     wchar_t range[] = L"abAc1";
    267     wchar_t expected_range[] = L"ABAC1";
    268     wct.toupper(range, range + sizeof(range) / sizeof(wchar_t));
    269     CPPUNIT_CHECK( equal(range, range + sizeof(range) / sizeof(wchar_t), expected_range) );
    270   }
    271 
    272   //tolower
    273   {
    274     CPPUNIT_CHECK( wct.tolower(L'A') == L'a' );
    275     CPPUNIT_CHECK( wct.tolower(L'a') == L'a' );
    276     CPPUNIT_CHECK( wct.tolower(L'1') == L'1' );
    277   }
    278 
    279   //tolower range
    280   {
    281     wchar_t range[] = L"ABaC1";
    282     wchar_t expected_range[] = L"abac1";
    283     wct.tolower(range, range + sizeof(range) / sizeof(wchar_t));
    284     CPPUNIT_CHECK( equal(range, range + sizeof(range) / sizeof(wchar_t), expected_range) );
    285   }
    286 
    287   //widen
    288   {
    289     CPPUNIT_CHECK( wct.widen('a') == L'a' );
    290   }
    291 
    292   //widen range
    293   {
    294     char range[] = "ABaC1";
    295     wchar_t res[sizeof(range)];
    296     wchar_t expected_res[] = L"ABaC1";
    297     wct.widen(range, range + sizeof(range), res);
    298     CPPUNIT_CHECK( equal(expected_res, expected_res + sizeof(range), res) );
    299   }
    300 
    301   //narrow
    302   {
    303     CPPUNIT_CHECK( wct.narrow(L'a', 'b') == L'a' );
    304   }
    305 
    306   //narrow range
    307   {
    308     wchar_t range[] = L"ABaC1";
    309     char res[sizeof(range) / sizeof(wchar_t)];
    310     char expected_res[] = "ABaC1";
    311     wct.narrow(range, range + sizeof(range) / sizeof(wchar_t), 'b', res);
    312     CPPUNIT_CHECK( equal(expected_res, expected_res + sizeof(range) / sizeof(wchar_t), res) );
    313   }
    314 # endif
    315 }
    316 
    317 
    318 typedef void (LocaleTest::*_Test) (const locale&);
    319 static void test_supported_locale(LocaleTest& inst, _Test __test) {
    320   size_t n = sizeof(tested_locales) / sizeof(tested_locales[0]);
    321   for (size_t i = 0; i < n; ++i) {
    322     locale loc;
    323 #  if !defined (STLPORT) || defined (_STLP_USE_EXCEPTIONS)
    324     try
    325 #  endif
    326     {
    327       locale tmp(tested_locales[i]);
    328       loc = tmp;
    329     }
    330 #  if !defined (STLPORT) || defined (_STLP_USE_EXCEPTIONS)
    331     catch (runtime_error const&) {
    332       //This locale is not supported.
    333       continue;
    334     }
    335 #  endif
    336 
    337     CPPUNIT_MESSAGE( loc.name().c_str() );
    338     (inst.*__test)(loc);
    339 
    340     {
    341       locale tmp(locale::classic(), tested_locales[i], locale::ctype);
    342       loc = tmp;
    343     }
    344     (inst.*__test)(loc);
    345 
    346     {
    347       locale tmp(locale::classic(), new ctype_byname<char>(tested_locales[i]));
    348 #ifndef _STLP_NO_WCHAR_T
    349       locale tmp0(tmp, new ctype_byname<wchar_t>(tested_locales[i]));
    350       tmp = tmp0;
    351 #endif
    352       loc = tmp;
    353     }
    354     (inst.*__test)(loc);
    355   }
    356 }
    357 
    358 void LocaleTest::ctype_facet()
    359 {
    360   test_supported_locale(*this, &LocaleTest::_ctype_facet);
    361 #ifndef _STLP_NO_WCHAR_T
    362   test_supported_locale(*this, &LocaleTest::_ctype_facet_w);
    363 #endif
    364 }
    365 
    366 void LocaleTest::ctype_by_name()
    367 {
    368   /*
    369    * Check of the 22.1.1.2.7 standard point. Construction of a locale
    370    * instance from a null pointer or an unknown name should result in
    371    * a runtime_error exception.
    372    */
    373 #  if !defined (STLPORT) || defined (_STLP_USE_EXCEPTIONS)
    374 #    if  defined (STLPORT) || (!defined(__GNUC__) && (!defined (_MSC_VER) || (_MSC_VER > 1400)))
    375    // libstdc++ call freelocate on bad locale
    376   try {
    377     locale loc(locale::classic(), new ctype_byname<char>(static_cast<char const*>(0)));
    378     CPPUNIT_ASSERT( false );
    379   }
    380   catch (runtime_error const& /* e */) {
    381     //CPPUNIT_MESSAGE( e.what() );
    382   }
    383   catch (...) {
    384     CPPUNIT_ASSERT( false );
    385   }
    386 #    endif
    387 
    388   try {
    389     locale loc(locale::classic(), new ctype_byname<char>("yasli_language"));
    390     CPPUNIT_FAIL;
    391   }
    392   catch (runtime_error const& /* e */) {
    393     //CPPUNIT_MESSAGE( e.what() );
    394   }
    395   catch (...) {
    396     CPPUNIT_FAIL;
    397   }
    398 
    399 #    if  defined(STLPORT) || !defined(__GNUC__)
    400   try {
    401     locale loc(locale::classic(), new codecvt_byname<char, char, mbstate_t>(static_cast<char const*>(0)));
    402     CPPUNIT_FAIL;
    403   }
    404   catch (runtime_error const& /* e */) {
    405     //CPPUNIT_MESSAGE( e.what() );
    406   }
    407   catch (...) {
    408     CPPUNIT_FAIL;
    409   }
    410 #    endif
    411 
    412   try {
    413     locale loc(locale::classic(), new codecvt_byname<char, char, mbstate_t>("yasli_language"));
    414     //STLport implementation do not care about name pass to this facet.
    415 #    if !defined (STLPORT)
    416     CPPUNIT_FAIL;
    417 #    endif
    418   }
    419   catch (runtime_error const& /* e */) {
    420     //CPPUNIT_MESSAGE( e.what() );
    421   }
    422   catch (...) {
    423     CPPUNIT_FAIL;
    424   }
    425 
    426   try {
    427     locale loc(locale::classic(), new ctype_byname<char>("fr_FR"));
    428     CPPUNIT_ASSERT( has_facet<ctype<char> >(loc) );
    429     ctype<char> const& ct = use_facet<ctype<char> >(loc);
    430     CPPUNIT_ASSERT( ct.is(ctype_base::mask(ctype_base::print | ctype_base::lower | ctype_base::alpha), '') );
    431   }
    432   catch (runtime_error const& /* e */) {
    433     //CPPUNIT_MESSAGE( e.what() );
    434   }
    435   catch (...) {
    436     CPPUNIT_FAIL;
    437   }
    438 
    439   try {
    440     locale loc(locale::classic(), new ctype_byname<char>("C"));
    441     ctype<char> const& cfacet_byname = use_facet<ctype<char> >(loc);
    442     ctype<char> const& cfacet = use_facet<ctype<char> >(locale::classic());
    443 
    444     for (char c = 0;; ++c) {
    445       CPPUNIT_CHECK(cfacet_byname.is(ctype_base::space, c) == cfacet.is(ctype_base::space, c));
    446       if (cfacet_byname.is(ctype_base::print, c) != cfacet.is(ctype_base::print, c))
    447       {
    448         CPPUNIT_CHECK(cfacet_byname.is(ctype_base::print, c) == cfacet.is(ctype_base::print, c));
    449       }
    450       CPPUNIT_CHECK(cfacet_byname.is(ctype_base::cntrl, c) == cfacet.is(ctype_base::cntrl, c));
    451       CPPUNIT_CHECK(cfacet_byname.is(ctype_base::upper, c) == cfacet.is(ctype_base::upper, c));
    452       CPPUNIT_CHECK(cfacet_byname.is(ctype_base::lower, c) == cfacet.is(ctype_base::lower, c));
    453       CPPUNIT_CHECK(cfacet_byname.is(ctype_base::alpha, c) == cfacet.is(ctype_base::alpha, c));
    454       CPPUNIT_CHECK(cfacet_byname.is(ctype_base::digit, c) == cfacet.is(ctype_base::digit, c));
    455       CPPUNIT_CHECK(cfacet_byname.is(ctype_base::punct, c) == cfacet.is(ctype_base::punct, c));
    456       CPPUNIT_CHECK(cfacet_byname.is(ctype_base::xdigit, c) == cfacet.is(ctype_base::xdigit, c));
    457       CPPUNIT_CHECK(cfacet_byname.is(ctype_base::alnum, c) == cfacet.is(ctype_base::alnum, c));
    458       CPPUNIT_CHECK(cfacet_byname.is(ctype_base::graph, c) == cfacet.is(ctype_base::graph, c));
    459       if (c == 127) break;
    460     }
    461   }
    462   catch (runtime_error const& /* e */) {
    463     /* CPPUNIT_MESSAGE( e.what() ); */
    464     CPPUNIT_FAIL;
    465   }
    466   catch (...) {
    467     CPPUNIT_FAIL;
    468   }
    469 
    470 #    if !defined (STLPORT) || !defined (_STLP_NO_WCHAR_T)
    471 #      if  defined(STLPORT) || !defined(__GNUC__)
    472   try {
    473     locale loc(locale::classic(), new ctype_byname<wchar_t>(static_cast<char const*>(0)));
    474     CPPUNIT_FAIL;
    475   }
    476   catch (runtime_error const&) {
    477   }
    478   catch (...) {
    479     CPPUNIT_FAIL;
    480   }
    481 #      endif
    482 
    483   try {
    484     locale loc(locale::classic(), new ctype_byname<wchar_t>("yasli_language"));
    485     CPPUNIT_FAIL;
    486   }
    487   catch (runtime_error const&) {
    488   }
    489   catch (...) {
    490     CPPUNIT_FAIL;
    491   }
    492 
    493 #      if  defined(STLPORT) || !defined(__GNUC__)
    494   try {
    495     locale loc(locale::classic(), new codecvt_byname<wchar_t, char, mbstate_t>(static_cast<char const*>(0)));
    496     CPPUNIT_FAIL;
    497   }
    498   catch (runtime_error const& /* e */) {
    499     //CPPUNIT_MESSAGE( e.what() );
    500   }
    501   catch (...) {
    502     CPPUNIT_FAIL;
    503   }
    504 #      endif
    505 
    506   try {
    507     locale loc(locale::classic(), new codecvt_byname<wchar_t, char, mbstate_t>("yasli_language"));
    508     CPPUNIT_FAIL;
    509   }
    510   catch (runtime_error const& /* e */) {
    511     //CPPUNIT_MESSAGE( e.what() );
    512   }
    513   catch (...) {
    514     CPPUNIT_FAIL;
    515   }
    516 #    endif
    517 #  endif
    518 }
    519 
    520 #endif
    521