src/java.base/macosx/native/libjava/HostLocaleProviderAdapter_md.c
changeset 47216 71c04702a3d5
parent 25859 3317bb8137f4
child 58972 dc998d4a227e
equal deleted inserted replaced
47215:4ebc2e2fb97c 47216:71c04702a3d5
       
     1 /*
       
     2  * Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
       
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
       
     4  *
       
     5  * This code is free software; you can redistribute it and/or modify it
       
     6  * under the terms of the GNU General Public License version 2 only, as
       
     7  * published by the Free Software Foundation.  Oracle designates this
       
     8  * particular file as subject to the "Classpath" exception as provided
       
     9  * by Oracle in the LICENSE file that accompanied this code.
       
    10  *
       
    11  * This code is distributed in the hope that it will be useful, but WITHOUT
       
    12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
       
    13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
       
    14  * version 2 for more details (a copy is included in the LICENSE file that
       
    15  * accompanied this code).
       
    16  *
       
    17  * You should have received a copy of the GNU General Public License version
       
    18  * 2 along with this work; if not, write to the Free Software Foundation,
       
    19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
       
    20  *
       
    21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
       
    22  * or visit www.oracle.com if you need additional information or have any
       
    23  * questions.
       
    24  */
       
    25 
       
    26 #include "sun_util_locale_provider_HostLocaleProviderAdapterImpl.h"
       
    27 #include "jni_util.h"
       
    28 #include <CoreFoundation/CoreFoundation.h>
       
    29 #include <stdio.h>
       
    30 
       
    31 #define BUFLEN 256
       
    32 
       
    33 static CFDateFormatterStyle convertDateFormatterStyle(jint javaStyle);
       
    34 static CFNumberFormatterStyle convertNumberFormatterStyle(jint javaStyle);
       
    35 static void copyArrayElements(JNIEnv *env, CFArrayRef cfarray, jobjectArray jarray, CFIndex sindex, int dindex, int count);
       
    36 static jstring getNumberSymbolString(JNIEnv *env, jstring jlangtag, jstring jdefault, CFStringRef type);
       
    37 static jchar getNumberSymbolChar(JNIEnv *env, jstring jlangtag, jchar jdefault, CFStringRef type);
       
    38 
       
    39 // from java_props_macosx.c
       
    40 extern char * getMacOSXLocale(int cat);
       
    41 extern char * getPosixLocale(int cat);
       
    42 
       
    43 /*
       
    44  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
    45  * Method:    getDefaultLocale
       
    46  * Signature: (I)Ljava/lang/String;
       
    47  */
       
    48 JNIEXPORT jstring JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getDefaultLocale
       
    49   (JNIEnv *env, jclass cls, jint cat) {
       
    50     char * localeString = NULL;
       
    51     int posixCat;
       
    52     jstring ret = NULL;
       
    53 
       
    54     switch (cat) {
       
    55         case sun_util_locale_provider_HostLocaleProviderAdapterImpl_CAT_DISPLAY:
       
    56             posixCat = LC_MESSAGES;
       
    57             break;
       
    58         case sun_util_locale_provider_HostLocaleProviderAdapterImpl_CAT_FORMAT:
       
    59         default:
       
    60             posixCat = LC_CTYPE;
       
    61             break;
       
    62     }
       
    63 
       
    64     localeString = getMacOSXLocale(posixCat);
       
    65     if (localeString == NULL) {
       
    66         localeString = getPosixLocale(posixCat);
       
    67         if (localeString == NULL) {
       
    68             JNU_ThrowOutOfMemoryError(env, NULL);
       
    69             return NULL;
       
    70         }
       
    71     }
       
    72     ret = (*env)->NewStringUTF(env, localeString);
       
    73     free(localeString);
       
    74 
       
    75     return ret;
       
    76 }
       
    77 
       
    78 /*
       
    79  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
    80  * Method:    getDateTimePatternNative
       
    81  * Signature: (IILjava/lang/String;)Ljava/lang/String;
       
    82  */
       
    83 JNIEXPORT jstring JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getDateTimePatternNative
       
    84   (JNIEnv *env, jclass cls, jint dateStyle, jint timeStyle, jstring jlangtag) {
       
    85     jstring ret = NULL;
       
    86     CFLocaleRef cflocale = CFLocaleCopyCurrent();
       
    87 
       
    88     if (cflocale != NULL) {
       
    89         CFDateFormatterRef df = CFDateFormatterCreate(kCFAllocatorDefault,
       
    90                                                   cflocale,
       
    91                                                   convertDateFormatterStyle(dateStyle),
       
    92                                                   convertDateFormatterStyle(timeStyle));
       
    93         if (df != NULL) {
       
    94             char buf[BUFLEN];
       
    95             CFStringRef formatStr = CFDateFormatterGetFormat(df);
       
    96             CFStringGetCString(formatStr, buf, BUFLEN, kCFStringEncodingUTF8);
       
    97             ret = (*env)->NewStringUTF(env, buf);
       
    98             CFRelease(df);
       
    99         }
       
   100         CFRelease(cflocale);
       
   101     }
       
   102 
       
   103     return ret;
       
   104 }
       
   105 
       
   106 /*
       
   107  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   108  * Method:    getCalendarID
       
   109  * Signature: (Ljava/lang/String;)Ljava/lang/String;
       
   110  */
       
   111 JNIEXPORT jstring JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getCalendarID
       
   112   (JNIEnv *env, jclass cls, jstring jlangtag) {
       
   113     jstring ret = NULL;
       
   114     CFLocaleRef cflocale = CFLocaleCopyCurrent();
       
   115 
       
   116     if (cflocale != NULL) {
       
   117         char buf[BUFLEN];
       
   118         CFTypeRef calid = CFLocaleGetValue(cflocale, kCFLocaleCalendarIdentifier);
       
   119         CFStringGetCString((CFStringRef)calid, buf, BUFLEN, kCFStringEncodingUTF8);
       
   120         ret = (*env)->NewStringUTF(env, buf);
       
   121         CFRelease(cflocale);
       
   122     }
       
   123 
       
   124     return ret;
       
   125 }
       
   126 
       
   127 /*
       
   128  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   129  * Method:    getAmPmStrings
       
   130  * Signature: (Ljava/lang/String;[Ljava/lang/String;)[Ljava/lang/String;
       
   131  */
       
   132 JNIEXPORT jobjectArray JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getAmPmStrings
       
   133   (JNIEnv *env, jclass cls, jstring jlangtag, jobjectArray ampms) {
       
   134     CFLocaleRef cflocale = CFLocaleCopyCurrent();
       
   135     jstring tmp_string;
       
   136     if (cflocale != NULL) {
       
   137         CFDateFormatterRef df = CFDateFormatterCreate(kCFAllocatorDefault,
       
   138                                                   cflocale,
       
   139                                                   kCFDateFormatterFullStyle,
       
   140                                                   kCFDateFormatterFullStyle);
       
   141         if (df != NULL) {
       
   142             char buf[BUFLEN];
       
   143             CFStringRef amStr = CFDateFormatterCopyProperty(df, kCFDateFormatterAMSymbol);
       
   144             if (amStr != NULL) {
       
   145                 CFStringGetCString(amStr, buf, BUFLEN, kCFStringEncodingUTF8);
       
   146                 CFRelease(amStr);
       
   147                 tmp_string = (*env)->NewStringUTF(env, buf);
       
   148                 if (tmp_string != NULL) {
       
   149                     (*env)->SetObjectArrayElement(env, ampms, 0, tmp_string);
       
   150                 }
       
   151             }
       
   152             if (!(*env)->ExceptionCheck(env)){
       
   153                 CFStringRef pmStr = CFDateFormatterCopyProperty(df, kCFDateFormatterPMSymbol);
       
   154                 if (pmStr != NULL) {
       
   155                     CFStringGetCString(pmStr, buf, BUFLEN, kCFStringEncodingUTF8);
       
   156                     CFRelease(pmStr);
       
   157                     tmp_string = (*env)->NewStringUTF(env, buf);
       
   158                     if (tmp_string != NULL) {
       
   159                         (*env)->SetObjectArrayElement(env, ampms, 1, tmp_string);
       
   160                     }
       
   161                 }
       
   162             }
       
   163             CFRelease(df);
       
   164         }
       
   165         CFRelease(cflocale);
       
   166     }
       
   167 
       
   168     return ampms;
       
   169 }
       
   170 
       
   171 /*
       
   172  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   173  * Method:    getEras
       
   174  * Signature: (Ljava/lang/String;[Ljava/lang/String;)[Ljava/lang/String;
       
   175  */
       
   176 JNIEXPORT jobjectArray JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getEras
       
   177   (JNIEnv *env, jclass cls, jstring jlangtag, jobjectArray eras) {
       
   178     CFLocaleRef cflocale = CFLocaleCopyCurrent();
       
   179     if (cflocale != NULL) {
       
   180         CFDateFormatterRef df = CFDateFormatterCreate(kCFAllocatorDefault,
       
   181                                                   cflocale,
       
   182                                                   kCFDateFormatterFullStyle,
       
   183                                                   kCFDateFormatterFullStyle);
       
   184         if (df != NULL) {
       
   185             CFArrayRef cferas = CFDateFormatterCopyProperty(df, kCFDateFormatterEraSymbols);
       
   186             if (cferas != NULL) {
       
   187                 copyArrayElements(env, cferas, eras, 0, 0, CFArrayGetCount(cferas));
       
   188                 CFRelease(cferas);
       
   189             }
       
   190             CFRelease(df);
       
   191         }
       
   192         CFRelease(cflocale);
       
   193     }
       
   194 
       
   195     return eras;
       
   196 }
       
   197 
       
   198 /*
       
   199  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   200  * Method:    getMonths
       
   201  * Signature: (Ljava/lang/String;[Ljava/lang/String;)[Ljava/lang/String;
       
   202  */
       
   203 JNIEXPORT jobjectArray JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getMonths
       
   204   (JNIEnv *env, jclass cls, jstring jlangtag, jobjectArray months) {
       
   205     CFLocaleRef cflocale = CFLocaleCopyCurrent();
       
   206     if (cflocale != NULL) {
       
   207         CFDateFormatterRef df = CFDateFormatterCreate(kCFAllocatorDefault,
       
   208                                                   cflocale,
       
   209                                                   kCFDateFormatterFullStyle,
       
   210                                                   kCFDateFormatterFullStyle);
       
   211         if (df != NULL) {
       
   212             CFArrayRef cfmonths = CFDateFormatterCopyProperty(df, kCFDateFormatterMonthSymbols);
       
   213             if (cfmonths != NULL) {
       
   214                 copyArrayElements(env, cfmonths, months, 0, 0, CFArrayGetCount(cfmonths));
       
   215                 CFRelease(cfmonths);
       
   216             }
       
   217             CFRelease(df);
       
   218         }
       
   219         CFRelease(cflocale);
       
   220     }
       
   221 
       
   222     return months;
       
   223 }
       
   224 
       
   225 /*
       
   226  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   227  * Method:    getShortMonths
       
   228  * Signature: (Ljava/lang/String;[Ljava/lang/String;)[Ljava/lang/String;
       
   229  */
       
   230 JNIEXPORT jobjectArray JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getShortMonths
       
   231   (JNIEnv *env, jclass cls, jstring jlangtag, jobjectArray smonths) {
       
   232     CFLocaleRef cflocale = CFLocaleCopyCurrent();
       
   233     if (cflocale != NULL) {
       
   234         CFDateFormatterRef df = CFDateFormatterCreate(kCFAllocatorDefault,
       
   235                                                   cflocale,
       
   236                                                   kCFDateFormatterFullStyle,
       
   237                                                   kCFDateFormatterFullStyle);
       
   238         if (df != NULL) {
       
   239             CFArrayRef cfsmonths = CFDateFormatterCopyProperty(df, kCFDateFormatterShortMonthSymbols);
       
   240             if (cfsmonths != NULL) {
       
   241                 copyArrayElements(env, cfsmonths, smonths, 0, 0, CFArrayGetCount(cfsmonths));
       
   242                 CFRelease(cfsmonths);
       
   243             }
       
   244             CFRelease(df);
       
   245         }
       
   246         CFRelease(cflocale);
       
   247     }
       
   248 
       
   249     return smonths;
       
   250 }
       
   251 
       
   252 /*
       
   253  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   254  * Method:    getWeekdays
       
   255  * Signature: (Ljava/lang/String;[Ljava/lang/String;)[Ljava/lang/String;
       
   256  */
       
   257 JNIEXPORT jobjectArray JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getWeekdays
       
   258   (JNIEnv *env, jclass cls, jstring jlangtag, jobjectArray wdays) {
       
   259     CFLocaleRef cflocale = CFLocaleCopyCurrent();
       
   260     if (cflocale != NULL) {
       
   261         CFDateFormatterRef df = CFDateFormatterCreate(kCFAllocatorDefault,
       
   262                                                   cflocale,
       
   263                                                   kCFDateFormatterFullStyle,
       
   264                                                   kCFDateFormatterFullStyle);
       
   265         if (df != NULL) {
       
   266             CFArrayRef cfwdays = CFDateFormatterCopyProperty(df, kCFDateFormatterWeekdaySymbols);
       
   267             if (cfwdays != NULL) {
       
   268                 copyArrayElements(env, cfwdays, wdays, 0, 1, CFArrayGetCount(cfwdays));
       
   269                 CFRelease(cfwdays);
       
   270             }
       
   271             CFRelease(df);
       
   272         }
       
   273         CFRelease(cflocale);
       
   274     }
       
   275 
       
   276     return wdays;
       
   277 }
       
   278 
       
   279 /*
       
   280  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   281  * Method:    getShortWeekdays
       
   282  * Signature: (Ljava/lang/String;[Ljava/lang/String;)[Ljava/lang/String;
       
   283  */
       
   284 JNIEXPORT jobjectArray JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getShortWeekdays
       
   285   (JNIEnv *env, jclass cls, jstring jlangtag, jobjectArray swdays) {
       
   286     CFLocaleRef cflocale = CFLocaleCopyCurrent();
       
   287     if (cflocale != NULL) {
       
   288         CFDateFormatterRef df = CFDateFormatterCreate(kCFAllocatorDefault,
       
   289                                                   cflocale,
       
   290                                                   kCFDateFormatterFullStyle,
       
   291                                                   kCFDateFormatterFullStyle);
       
   292         if (df != NULL) {
       
   293             CFArrayRef cfswdays = CFDateFormatterCopyProperty(df, kCFDateFormatterShortWeekdaySymbols);
       
   294             if (cfswdays != NULL) {
       
   295                 copyArrayElements(env, cfswdays, swdays, 0, 1, CFArrayGetCount(cfswdays));
       
   296                 CFRelease(cfswdays);
       
   297             }
       
   298             CFRelease(df);
       
   299         }
       
   300         CFRelease(cflocale);
       
   301     }
       
   302 
       
   303     return swdays;
       
   304 }
       
   305 
       
   306 /*
       
   307  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   308  * Method:    getNumberPatternNative
       
   309  * Signature: (ILjava/lang/String;)Ljava/lang/String;
       
   310  */
       
   311 JNIEXPORT jstring JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getNumberPatternNative
       
   312   (JNIEnv *env, jclass cls, jint numberStyle, jstring jlangtag) {
       
   313     jstring ret = NULL;
       
   314     CFLocaleRef cflocale = CFLocaleCopyCurrent();
       
   315     if (cflocale != NULL) {
       
   316         CFNumberFormatterRef nf = CFNumberFormatterCreate(kCFAllocatorDefault,
       
   317                                                   cflocale,
       
   318                                                   convertNumberFormatterStyle(numberStyle));
       
   319         if (nf != NULL) {
       
   320             char buf[BUFLEN];
       
   321             CFStringRef formatStr = CFNumberFormatterGetFormat(nf);
       
   322             CFStringGetCString(formatStr, buf, BUFLEN, kCFStringEncodingUTF8);
       
   323             ret = (*env)->NewStringUTF(env, buf);
       
   324             CFRelease(nf);
       
   325         }
       
   326         CFRelease(cflocale);
       
   327     }
       
   328 
       
   329     return ret;
       
   330 }
       
   331 
       
   332 /*
       
   333  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   334  * Method:    getCurrencySymbol
       
   335  * Signature: (Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;
       
   336  */
       
   337 JNIEXPORT jstring JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getCurrencySymbol
       
   338   (JNIEnv *env, jclass cls, jstring jlangtag, jstring currencySymbol) {
       
   339     return getNumberSymbolString(env, jlangtag, currencySymbol, kCFNumberFormatterCurrencySymbol);
       
   340 }
       
   341 
       
   342 /*
       
   343  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   344  * Method:    getDecimalSeparator
       
   345  * Signature: (Ljava/lang/String;C)C
       
   346  */
       
   347 JNIEXPORT jchar JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getDecimalSeparator
       
   348   (JNIEnv *env, jclass cls, jstring jlangtag, jchar decimalSeparator) {
       
   349     return getNumberSymbolChar(env, jlangtag, decimalSeparator, kCFNumberFormatterDecimalSeparator);
       
   350 }
       
   351 
       
   352 /*
       
   353  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   354  * Method:    getGroupingSeparator
       
   355  * Signature: (Ljava/lang/String;C)C
       
   356  */
       
   357 JNIEXPORT jchar JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getGroupingSeparator
       
   358   (JNIEnv *env, jclass cls, jstring jlangtag, jchar groupingSeparator) {
       
   359     return getNumberSymbolChar(env, jlangtag, groupingSeparator, kCFNumberFormatterGroupingSeparator);
       
   360 }
       
   361 
       
   362 /*
       
   363  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   364  * Method:    getInfinity
       
   365  * Signature: (Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;
       
   366  */
       
   367 JNIEXPORT jstring JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getInfinity
       
   368   (JNIEnv *env, jclass cls, jstring jlangtag, jstring infinity) {
       
   369     return getNumberSymbolString(env, jlangtag, infinity, kCFNumberFormatterInfinitySymbol);
       
   370 }
       
   371 
       
   372 /*
       
   373  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   374  * Method:    getInternationalCurrencySymbol
       
   375  * Signature: (Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;
       
   376  */
       
   377 JNIEXPORT jstring JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getInternationalCurrencySymbol
       
   378   (JNIEnv *env, jclass cls, jstring jlangtag, jstring internationalCurrencySymbol) {
       
   379     return getNumberSymbolString(env, jlangtag, internationalCurrencySymbol, kCFNumberFormatterInternationalCurrencySymbol);
       
   380 }
       
   381 
       
   382 /*
       
   383  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   384  * Method:    getMinusSign
       
   385  * Signature: (Ljava/lang/String;C)C
       
   386  */
       
   387 JNIEXPORT jchar JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getMinusSign
       
   388   (JNIEnv *env, jclass cls, jstring jlangtag, jchar minusSign) {
       
   389     return getNumberSymbolChar(env, jlangtag, minusSign, kCFNumberFormatterMinusSign);
       
   390 }
       
   391 
       
   392 /*
       
   393  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   394  * Method:    getMonetaryDecimalSeparator
       
   395  * Signature: (Ljava/lang/String;C)C
       
   396  */
       
   397 JNIEXPORT jchar JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getMonetaryDecimalSeparator
       
   398   (JNIEnv *env, jclass cls, jstring jlangtag, jchar monetaryDecimalSeparator) {
       
   399     return getNumberSymbolChar(env, jlangtag, monetaryDecimalSeparator, kCFNumberFormatterCurrencyDecimalSeparator);
       
   400 }
       
   401 
       
   402 /*
       
   403  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   404  * Method:    getNaN
       
   405  * Signature: (Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;
       
   406  */
       
   407 JNIEXPORT jstring JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getNaN
       
   408   (JNIEnv *env, jclass cls, jstring jlangtag, jstring nan) {
       
   409     return getNumberSymbolString(env, jlangtag, nan, kCFNumberFormatterNaNSymbol);
       
   410 }
       
   411 
       
   412 /*
       
   413  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   414  * Method:    getPercent
       
   415  * Signature: (Ljava/lang/String;C)C
       
   416  */
       
   417 JNIEXPORT jchar JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getPercent
       
   418   (JNIEnv *env, jclass cls, jstring jlangtag, jchar percent) {
       
   419     return getNumberSymbolChar(env, jlangtag, percent, kCFNumberFormatterPercentSymbol);
       
   420 }
       
   421 
       
   422 /*
       
   423  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   424  * Method:    getPerMill
       
   425  * Signature: (Ljava/lang/String;C)C
       
   426  */
       
   427 JNIEXPORT jchar JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getPerMill
       
   428   (JNIEnv *env, jclass cls, jstring jlangtag, jchar perMill) {
       
   429     return getNumberSymbolChar(env, jlangtag, perMill, kCFNumberFormatterPerMillSymbol);
       
   430 }
       
   431 
       
   432 /*
       
   433  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   434  * Method:    getZeroDigit
       
   435  * Signature: (Ljava/lang/String;C)C
       
   436  */
       
   437 JNIEXPORT jchar JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getZeroDigit
       
   438   (JNIEnv *env, jclass cls, jstring jlangtag, jchar zeroDigit) {
       
   439     // The following code *should* work, but not for some reason :o
       
   440     //
       
   441     //return getNumberSymbolChar(env, jlangtag, zeroDigit, kCFNumberFormatterZeroSymbol);
       
   442     //
       
   443     // so here is a workaround.
       
   444     jchar ret = zeroDigit;
       
   445     CFLocaleRef cflocale = CFLocaleCopyCurrent();
       
   446 
       
   447     if (cflocale != NULL) {
       
   448         CFNumberFormatterRef nf = CFNumberFormatterCreate(kCFAllocatorDefault,
       
   449                                                   cflocale,
       
   450                                                   kCFNumberFormatterNoStyle);
       
   451         if (nf != NULL) {
       
   452             int zero = 0;
       
   453             CFStringRef str = CFNumberFormatterCreateStringWithValue(kCFAllocatorDefault,
       
   454                               nf, kCFNumberIntType, &zero);
       
   455             if (str != NULL) {
       
   456                 if (CFStringGetLength(str) > 0) {
       
   457                     ret = CFStringGetCharacterAtIndex(str, 0);
       
   458                 }
       
   459                 CFRelease(str);
       
   460             }
       
   461 
       
   462             CFRelease(nf);
       
   463         }
       
   464 
       
   465         CFRelease(cflocale);
       
   466     }
       
   467 
       
   468     return ret;
       
   469 }
       
   470 
       
   471 /*
       
   472  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   473  * Method:    getExponentSeparator
       
   474  * Signature: (Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;
       
   475  */
       
   476 JNIEXPORT jstring JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getExponentSeparator
       
   477   (JNIEnv *env, jclass cls, jstring jlangtag, jstring exponent) {
       
   478     return getNumberSymbolString(env, jlangtag, exponent, kCFNumberFormatterExponentSymbol);
       
   479 }
       
   480 
       
   481 /*
       
   482  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   483  * Method:    getCalendarInt
       
   484  * Signature: (Ljava/lang/String;I)I
       
   485  */
       
   486 JNIEXPORT jint JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getCalendarInt
       
   487   (JNIEnv *env, jclass cls, jstring jlangtag, jint type) {
       
   488     jint ret = 0;
       
   489     CFCalendarRef cfcal = CFCalendarCopyCurrent();
       
   490 
       
   491     if (cfcal != NULL) {
       
   492         switch (type) {
       
   493             case sun_util_locale_provider_HostLocaleProviderAdapterImpl_CD_FIRSTDAYOFWEEK:
       
   494                 ret = CFCalendarGetFirstWeekday(cfcal);
       
   495                 break;
       
   496             case sun_util_locale_provider_HostLocaleProviderAdapterImpl_CD_MINIMALDAYSINFIRSTWEEK:
       
   497                 ret = CFCalendarGetMinimumDaysInFirstWeek(cfcal);
       
   498                 break;
       
   499             default:
       
   500                 ret = 0;
       
   501         }
       
   502 
       
   503         CFRelease(cfcal);
       
   504     }
       
   505 
       
   506     return ret;
       
   507 }
       
   508 
       
   509 /*
       
   510  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   511  * Method:    getDisplayString
       
   512  * Signature: (Ljava/lang/String;ILjava/lang/String;)Ljava/lang/String;
       
   513  */
       
   514 JNIEXPORT jstring JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getDisplayString
       
   515   (JNIEnv *env, jclass cls, jstring jlangtag, jint type, jstring value) {
       
   516     jstring ret = NULL;
       
   517 
       
   518     const char *clangtag = (*env)->GetStringUTFChars(env, jlangtag, 0);
       
   519     if (clangtag != NULL) {
       
   520         const char *cvalue = (*env)->GetStringUTFChars(env, value, 0);
       
   521         if (cvalue != NULL) {
       
   522             CFStringRef cflangtag =
       
   523                 CFStringCreateWithCString(kCFAllocatorDefault, clangtag, kCFStringEncodingUTF8);
       
   524             if (cflangtag != NULL) {
       
   525                 CFLocaleRef cflocale = CFLocaleCreate(kCFAllocatorDefault, cflangtag);
       
   526                 if (cflocale != NULL) {
       
   527                     CFStringRef cfvalue =
       
   528                         CFStringCreateWithCString(kCFAllocatorDefault, cvalue, kCFStringEncodingUTF8);
       
   529                     if (cfvalue != NULL) {
       
   530                         CFStringRef str = NULL;
       
   531                         switch (type) {
       
   532                             case sun_util_locale_provider_HostLocaleProviderAdapterImpl_DN_LOCALE_LANGUAGE:
       
   533                                 str = CFLocaleCopyDisplayNameForPropertyValue(cflocale, kCFLocaleLanguageCode, cfvalue);
       
   534                                 break;
       
   535                             case sun_util_locale_provider_HostLocaleProviderAdapterImpl_DN_LOCALE_SCRIPT:
       
   536                                 str = CFLocaleCopyDisplayNameForPropertyValue(cflocale, kCFLocaleScriptCode, cfvalue);
       
   537                                 break;
       
   538                             case sun_util_locale_provider_HostLocaleProviderAdapterImpl_DN_LOCALE_REGION:
       
   539                                 str = CFLocaleCopyDisplayNameForPropertyValue(cflocale, kCFLocaleCountryCode, cfvalue);
       
   540                                 break;
       
   541                             case sun_util_locale_provider_HostLocaleProviderAdapterImpl_DN_LOCALE_VARIANT:
       
   542                                 str = CFLocaleCopyDisplayNameForPropertyValue(cflocale, kCFLocaleVariantCode, cfvalue);
       
   543                                 break;
       
   544                             case sun_util_locale_provider_HostLocaleProviderAdapterImpl_DN_CURRENCY_CODE:
       
   545                                 str = CFLocaleCopyDisplayNameForPropertyValue(cflocale, kCFLocaleCurrencyCode, cfvalue);
       
   546                                 break;
       
   547                             case sun_util_locale_provider_HostLocaleProviderAdapterImpl_DN_CURRENCY_SYMBOL:
       
   548                                 str = CFLocaleCopyDisplayNameForPropertyValue(cflocale, kCFLocaleCurrencySymbol, cfvalue);
       
   549                                 break;
       
   550                         }
       
   551                         if (str != NULL) {
       
   552                             char buf[BUFLEN];
       
   553                             CFStringGetCString(str, buf, BUFLEN, kCFStringEncodingUTF8);
       
   554                             CFRelease(str);
       
   555                             ret = (*env)->NewStringUTF(env, buf);
       
   556                         }
       
   557                         CFRelease(cfvalue);
       
   558                     }
       
   559                     CFRelease(cflocale);
       
   560                 }
       
   561                 CFRelease(cflangtag);
       
   562             }
       
   563             (*env)->ReleaseStringUTFChars(env, value, cvalue);
       
   564         }
       
   565         (*env)->ReleaseStringUTFChars(env, jlangtag, clangtag);
       
   566     }
       
   567 
       
   568     return ret;
       
   569 }
       
   570 
       
   571 /*
       
   572  * Class:     sun_util_locale_provider_HostLocaleProviderAdapterImpl
       
   573  * Method:    getTimeZoneDisplayString
       
   574  * Signature: (Ljava/lang/String;ILjava/lang/String;)Ljava/lang/String;
       
   575  */
       
   576 JNIEXPORT jstring JNICALL Java_sun_util_locale_provider_HostLocaleProviderAdapterImpl_getTimeZoneDisplayString
       
   577   (JNIEnv *env, jclass cls, jstring jlangtag, jint type, jstring tzid) {
       
   578     jstring ret = NULL;
       
   579 
       
   580     const char *clangtag = (*env)->GetStringUTFChars(env, jlangtag, 0);
       
   581     if (clangtag != NULL) {
       
   582         const char *ctzid = (*env)->GetStringUTFChars(env, tzid, 0);
       
   583         if (ctzid != NULL) {
       
   584             CFStringRef cflangtag =
       
   585                 CFStringCreateWithCString(kCFAllocatorDefault, clangtag, kCFStringEncodingUTF8);
       
   586             if (cflangtag != NULL) {
       
   587                 CFLocaleRef cflocale = CFLocaleCreate(kCFAllocatorDefault, cflangtag);
       
   588                 if (cflocale != NULL) {
       
   589                     CFStringRef cftzid =
       
   590                         CFStringCreateWithCString(kCFAllocatorDefault, ctzid, kCFStringEncodingUTF8);
       
   591                     if (cftzid != NULL) {
       
   592                         CFTimeZoneRef cftz = CFTimeZoneCreateWithName(kCFAllocatorDefault, cftzid, false);
       
   593                         if (cftz != NULL) {
       
   594                             CFStringRef str = NULL;
       
   595                             switch (type) {
       
   596                                 case sun_util_locale_provider_HostLocaleProviderAdapterImpl_DN_TZ_SHORT_STANDARD:
       
   597                                     str = CFTimeZoneCopyLocalizedName(cftz, kCFTimeZoneNameStyleShortStandard, cflocale);
       
   598                                     break;
       
   599                                 case sun_util_locale_provider_HostLocaleProviderAdapterImpl_DN_TZ_SHORT_DST:
       
   600                                     str = CFTimeZoneCopyLocalizedName(cftz, kCFTimeZoneNameStyleShortDaylightSaving, cflocale);
       
   601                                     break;
       
   602                                 case sun_util_locale_provider_HostLocaleProviderAdapterImpl_DN_TZ_LONG_STANDARD:
       
   603                                     str = CFTimeZoneCopyLocalizedName(cftz, kCFTimeZoneNameStyleStandard, cflocale);
       
   604                                     break;
       
   605                                 case sun_util_locale_provider_HostLocaleProviderAdapterImpl_DN_TZ_LONG_DST:
       
   606                                     str = CFTimeZoneCopyLocalizedName(cftz, kCFTimeZoneNameStyleDaylightSaving, cflocale);
       
   607                                     break;
       
   608                             }
       
   609                             if (str != NULL) {
       
   610                                 char buf[BUFLEN];
       
   611                                 CFStringGetCString(str, buf, BUFLEN, kCFStringEncodingUTF8);
       
   612                                 CFRelease(str);
       
   613                                 ret = (*env)->NewStringUTF(env, buf);
       
   614                             }
       
   615                             CFRelease(cftz);
       
   616                         }
       
   617                         CFRelease(cftzid);
       
   618                     }
       
   619                     CFRelease(cflocale);
       
   620                 }
       
   621                 CFRelease(cflangtag);
       
   622             }
       
   623             (*env)->ReleaseStringUTFChars(env, tzid, ctzid);
       
   624         }
       
   625         (*env)->ReleaseStringUTFChars(env, jlangtag, clangtag);
       
   626     }
       
   627 
       
   628     return ret;
       
   629 }
       
   630 
       
   631 static CFDateFormatterStyle convertDateFormatterStyle(jint javaStyle) {
       
   632     switch (javaStyle) {
       
   633         case 0: // FULL
       
   634             return kCFDateFormatterFullStyle;
       
   635         case 1: // LONG
       
   636             return kCFDateFormatterLongStyle;
       
   637         case 2: // MEDIUM
       
   638             return kCFDateFormatterMediumStyle;
       
   639         case 3: // LONG
       
   640             return kCFDateFormatterShortStyle;
       
   641         case -1: // No style
       
   642         default:
       
   643             return kCFDateFormatterNoStyle;
       
   644     }
       
   645 }
       
   646 
       
   647 static CFNumberFormatterStyle convertNumberFormatterStyle(jint javaStyle) {
       
   648     switch (javaStyle) {
       
   649         case sun_util_locale_provider_HostLocaleProviderAdapterImpl_NF_CURRENCY:
       
   650             return kCFNumberFormatterCurrencyStyle;
       
   651         case sun_util_locale_provider_HostLocaleProviderAdapterImpl_NF_INTEGER:
       
   652             return kCFNumberFormatterDecimalStyle;
       
   653         case sun_util_locale_provider_HostLocaleProviderAdapterImpl_NF_NUMBER:
       
   654             return kCFNumberFormatterDecimalStyle;
       
   655         case sun_util_locale_provider_HostLocaleProviderAdapterImpl_NF_PERCENT:
       
   656             return kCFNumberFormatterPercentStyle;
       
   657         default:
       
   658             return kCFNumberFormatterNoStyle;
       
   659     }
       
   660 }
       
   661 
       
   662 static void copyArrayElements(JNIEnv *env, CFArrayRef cfarray, jobjectArray jarray, CFIndex sindex, int dindex, int count) {
       
   663     char buf[BUFLEN];
       
   664     jstring tmp_string;
       
   665 
       
   666     for (; count > 0; sindex++, dindex++, count--) {
       
   667         CFStringGetCString(CFArrayGetValueAtIndex(cfarray, sindex), buf, BUFLEN, kCFStringEncodingUTF8);
       
   668         tmp_string = (*env)->NewStringUTF(env, buf);
       
   669         if (tmp_string != NULL) {
       
   670             (*env)->SetObjectArrayElement(env, jarray, dindex, tmp_string);
       
   671         } else {
       
   672             break;
       
   673         }
       
   674     }
       
   675 }
       
   676 
       
   677 static jstring getNumberSymbolString(JNIEnv *env, jstring jlangtag, jstring jdefault, CFStringRef type) {
       
   678     char buf[BUFLEN];
       
   679     jstring ret = jdefault;
       
   680     CFLocaleRef cflocale = CFLocaleCopyCurrent();
       
   681 
       
   682     if (cflocale != NULL) {
       
   683         CFNumberFormatterRef nf = CFNumberFormatterCreate(kCFAllocatorDefault,
       
   684                                                   cflocale,
       
   685                                                   kCFNumberFormatterNoStyle);
       
   686         if (nf != NULL) {
       
   687             CFStringRef str = CFNumberFormatterCopyProperty(nf, type);
       
   688             if (str != NULL) {
       
   689                 CFStringGetCString(str, buf, BUFLEN, kCFStringEncodingUTF8);
       
   690                 CFRelease(str);
       
   691                 ret = (*env)->NewStringUTF(env, buf);
       
   692             }
       
   693 
       
   694             CFRelease(nf);
       
   695         }
       
   696 
       
   697         CFRelease(cflocale);
       
   698     }
       
   699 
       
   700     return ret;
       
   701 }
       
   702 
       
   703 static jchar getNumberSymbolChar(JNIEnv *env, jstring jlangtag, jchar jdefault, CFStringRef type) {
       
   704     jchar ret = jdefault;
       
   705     CFLocaleRef cflocale = CFLocaleCopyCurrent();
       
   706 
       
   707     if (cflocale != NULL) {
       
   708         CFNumberFormatterRef nf = CFNumberFormatterCreate(kCFAllocatorDefault,
       
   709                                                   cflocale,
       
   710                                                   kCFNumberFormatterNoStyle);
       
   711         if (nf != NULL) {
       
   712             CFStringRef str = CFNumberFormatterCopyProperty(nf, type);
       
   713             if (str != NULL) {
       
   714                 if (CFStringGetLength(str) > 0) {
       
   715                     ret = CFStringGetCharacterAtIndex(str, 0);
       
   716                 }
       
   717                 CFRelease(str);
       
   718             }
       
   719 
       
   720             CFRelease(nf);
       
   721         }
       
   722 
       
   723         CFRelease(cflocale);
       
   724     }
       
   725 
       
   726     return ret;
       
   727 }