]> git.saurik.com Git - apple/icu.git/blobdiff - icuSources/tools/genrb/wrtxml.c
ICU-8.11.1.tar.gz
[apple/icu.git] / icuSources / tools / genrb / wrtxml.c
index 57813b769a0bb248fa7b3439b293ba1ad36b5903..4e0cd73121b7617d42de6e2c99cdbd5d87a16b68 100644 (file)
@@ -1,7 +1,7 @@
 /*
 *******************************************************************************
 *
-*   Copyright (C) 2002-2004, International Business Machines
+*   Copyright (C) 2002-2006, International Business Machines
 *   Corporation and others.  All Rights Reserved.
 *
 *******************************************************************************
@@ -123,166 +123,46 @@ static uint32_t computeCRC(char *ptr, uint32_t len, uint32_t lastcrc){
     return(crc);
 }
 
-/*check the language with ISO 639 standard*/
-static UBool checkISOLanguage(char* language) {
-    int i = 0;
-    int result = -1;
-
-    while(ISOLanguages[i] != '\0') {
-        result = uprv_strcmp(language, ISOLanguages[i]);
-        if(result == 0) {
-            return TRUE;
-        }
-        i++;
-    }
-    return FALSE;
-}
-
-/*check the language with ISO 639 standard*/
-static UBool checkISOCountry(char* country) {
-    int i = 0;
-    int result = -1;
-
-    while(ISOCountries[i]!='\0') {
-        result = uprv_strcmp(country, ISOCountries[i]);
-        if(result == 0) {
-            return TRUE;
+static void strnrepchr(char* src, int32_t srcLen, char s, char r){
+    int32_t i = 0;
+    for(i=0;i<srcLen;i++){
+        if(src[i]==s){
+            src[i]=r;
         }
-        i++;
     }
-    return FALSE;
 }
-
 /* Parse the filename, and get its language information.
  * If it fails to get the language information from the filename,
  * use "en" as the default value for language
  */
-static char* parseFilename(const char* fileName, char* lang) {
-    char* pos;
-    char* pos2;
-    int32_t first;
-    int32_t second;
-    char* str0 = NULL;
-    char* str1 = NULL;
-    char* str2 = NULL;
-    char* str3 = NULL;
-    int32_t index = 0;
-    UBool ISO_tag = TRUE;
-
-    ISOLanguages = uloc_getISOLanguages();
-    ISOCountries = uloc_getISOCountries();
-
-    pos = uprv_strrchr(fileName, U_FILE_SEP_CHAR);
-    pos2 = uprv_strrchr(fileName, '.');
-
-    if(pos == NULL) {
-        first = -1;
-    }else {
-        first = (int32_t)(pos - fileName);
-    }
-    if(pos2 == NULL) {
-        second = (int32_t)uprv_strlen(fileName);
-    } else {
-        second = (int32_t)(pos2 - fileName);
-    }
-    index = (int32_t)(second - first - 1);
-    str0 = uprv_malloc(sizeof(char) * index + 1);
-    uprv_memset(str0, 0, sizeof(char) * index + 1);
-    uprv_strncpy(str0, fileName + first + 1, index);
-
-    pos = uprv_strchr( str0, '_' );
-    first = (int32_t)(pos - str0);
-    if (pos == NULL) {
-        str1 = uprv_malloc(sizeof(char)*uprv_strlen(str0)+1);
-        uprv_memset(str1, 0, sizeof(char)*uprv_strlen(str0)+1);
-        uprv_strcpy(str1, str0);
-    } else {
-        str1 = uprv_malloc(sizeof(char)*first+1);
-        uprv_memset(str1, 0, sizeof(char)*first+1);
-        uprv_strncpy(str1, str0, first);
-        pos = uprv_strrchr( str0, '_' );
-        second = (int32_t)(pos - str0);
-        if(first != second && second-first != 1) {
-            index = second - first-1;
-            str2 = uprv_malloc(sizeof(char)*index+1);
-            uprv_memset(str2, 0, sizeof(char)*index+1);
-            uprv_strncpy(str2, str0 + first + 1, index );
-            index = (int32_t)(uprv_strlen(str0) - second -1);
-            str3 = uprv_malloc(sizeof(char)*index+1);
-            uprv_memset(str3, 0, sizeof(char)*index+1);
-            uprv_strncpy(str3, str0 + second + 1, index);
-        } else if(first == second) {
-            index = first;
-            str1 = uprv_malloc(sizeof(char)*first+1);
-            uprv_memset(str1, 0, sizeof(char)*first+1);
-            uprv_strncpy(str1, str0, index );
-            index = (int32_t)(uprv_strlen(str0) - second -1);
-            str2 = uprv_malloc(sizeof(char)*index+1);
-            uprv_memset(str2, 0, sizeof(char)*index+1);
-            uprv_strncpy(str2, str0 + second + 1, index );
-        }
-    }
-
-    if (str2 == NULL && str3 == NULL) {
-        ISO_tag = checkISOLanguage(str1);
-        if(ISO_tag) {
-            lang = uprv_malloc(sizeof(char)*uprv_strlen(str1)+1);
-            uprv_memset(lang, 0, sizeof(char)*uprv_strlen(str1)+1);
-            uprv_strcpy(lang, str1);
-        }
-    } else if(str3 == NULL){
-        ISO_tag = checkISOLanguage(str1);
-        if (ISO_tag) {
-            ISO_tag = checkISOCountry(str2);
-            if (ISO_tag) {
-                lang = uprv_malloc(sizeof(char)*uprv_strlen(str1)+1);
-                uprv_memset(lang, 0, sizeof(char)*uprv_strlen(str1)+1);
-                uprv_strcpy(lang, str1);
-            }
-        } else {
-            ISO_tag = checkISOLanguage(str2);
-            if (ISO_tag) {
-                lang = uprv_malloc(sizeof(char)*uprv_strlen(str2)+1);
-                uprv_memset(lang, 0, sizeof(char)*uprv_strlen(str2)+1);
-                uprv_strcpy(lang, str2);
-            }
-        }
-    } else {
-        ISO_tag = checkISOLanguage(str1);
-        if(ISO_tag) {
-            ISO_tag = checkISOCountry(str2);
-            if (ISO_tag) {
-                lang = uprv_malloc(sizeof(char)*uprv_strlen(str1)+1);
-                uprv_memset(lang, 0, sizeof(char)*uprv_strlen(str1)+1);
-                uprv_strcpy(lang, str1);
-            }
-        } else {
-            ISO_tag = checkISOLanguage(str2);
-            if(ISO_tag) {
-                ISO_tag = checkISOCountry(str3);
-                if (ISO_tag) {
-                    lang = uprv_malloc(sizeof(char)*uprv_strlen(str2)+1);
-                    uprv_memset(lang, 0, sizeof(char)*uprv_strlen(str2)+1);
-                    uprv_strcpy(lang, str2);
-                }
-            }
-        }
-    }
-
-    if(str0 != NULL){
-        uprv_free(str0);
+static char* parseFilename(const char* id, char* lang) {
+    int idLen = uprv_strlen(id);
+    char* localeID = (char*) uprv_malloc(idLen);
+    int pos = 0;
+    int canonCapacity = 0;
+    char* canon = NULL;
+    int canonLen = 0;
+    /*int i;*/
+    UErrorCode status = U_ZERO_ERROR;
+    char *ext = uprv_strchr(id, '.');
+    if(ext!=NULL){
+        pos = ext-id;
+    }else{
+        pos = idLen;
     }
+    uprv_memcpy(localeID, id, pos);
+    localeID[pos]=0; /* NUL terminate the string */
+    
+    canonCapacity =pos*3;
+    canon = (char*) uprv_malloc(canonCapacity);
+    canonLen = uloc_canonicalize(localeID, canon, canonCapacity, &status);
 
-    if(str1 != NULL){
-        uprv_free(str1);
+    if(U_FAILURE(status)){
+        fprintf(stderr, "Could not canonicalize the locale ID: %s. Error: %s\n", localeID, u_errorName(status));
+        exit(status);
     }
-    if(str2 != NULL){
-        uprv_free(str2);
-    }
-    if(str3 != NULL){
-        uprv_free(str3);
-    }
-    return lang;
+    strnrepchr(canon, canonLen, '_', '-');
+    return canon;
 }
 
 static const char* xmlHeader = "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n"
@@ -291,7 +171,7 @@ static const char* xmlHeader = "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n"
 static const char* bundleStart = "<xliff version = \"1.0\">\n";
 static const char* bundleEnd   = "</xliff>\n";
 
-void res_write_xml(struct SResource *res, const char* id, const char* language, UErrorCode *status);
+void res_write_xml(struct SResource *res, const char* id, const char* language, UBool isTopLevel, UErrorCode *status);
 
 static char* convertAndEscape(char** pDest, int32_t destCap, int32_t* destLength,
                               const UChar* src, int32_t srcLen, UErrorCode* status){
@@ -408,6 +288,7 @@ static char* convertAndEscape(char** pDest, int32_t destCap, int32_t* destLength
             temp = (char*) uprv_malloc(sizeof(char)*destCap);
             if(temp==NULL){
                 *status=U_MEMORY_ALLOCATION_ERROR;
+                uprv_free(dest);
                 return NULL;
             }
             uprv_memmove(temp,dest,destLen);
@@ -428,13 +309,7 @@ static char* convertAndEscape(char** pDest, int32_t destCap, int32_t* destLength
 #define LF       0x000D
 #define AT_SIGN  0x0040
 
-static const UChar tokens[][11] = {
-    {0x0040, 0x0074, 0x0072, 0x0061, 0x006e, 0x0073, 0x006c, 0x0061, 0x0074, 0x0065, 0x0000}, /* @translate */
-    {0x0040, 0x006e, 0x006f, 0x0074, 0x0065, 0x0000}                                          /* @note */
-};
 
-static const UChar yes[] = {  0x0079, 0x0065, 0x0073, 0x0000}; /* yes */
-static const UChar no[] ={ 0x006e, 0x006f, 0x0000 };           /* no */
 
 
 
@@ -597,7 +472,7 @@ string_write_xml(struct SResource *res, const char* id, const char* language, UE
 
     char* sid = NULL;
     const char* strStart = "<trans-unit xml:space = \"preserve\" id = \"";
-    const char* valStrStart = "<source xml:lang = \"";
+    const char* valStrStart = "<source ";
     const char* valStrEnd = "</source>\n";
     const char* strEnd = "</trans-unit>\n";
 
@@ -622,8 +497,8 @@ string_write_xml(struct SResource *res, const char* id, const char* language, UE
         write_tabs(out);
 
         T_FileStream_write(out,valStrStart, (int32_t)uprv_strlen(valStrStart));
-        T_FileStream_write(out,language, (int32_t)uprv_strlen(language));
-        T_FileStream_write(out,"\">", 2);
+       /* T_FileStream_write(out,language, (int32_t)uprv_strlen(language)); */
+        T_FileStream_write(out,">", 1);
 
         buf = convertAndEscape(&buf,0,&bufLen,res->u.fString.fChars,res->u.fString.fLength,status);
 
@@ -662,8 +537,8 @@ string_write_xml(struct SResource *res, const char* id, const char* language, UE
         write_tabs(out);
         T_FileStream_write(out,valStrStart, (int32_t)uprv_strlen(valStrStart));
 
-        T_FileStream_write(out,language, (int32_t)uprv_strlen(language));
-        T_FileStream_write(out,"\">", 2);
+        /*T_FileStream_write(out,language, (int32_t)uprv_strlen(language));*/
+        T_FileStream_write(out,">", 1);
 
         buf = convertAndEscape(&buf,0,&bufLen,res->u.fString.fChars,res->u.fString.fLength,status);
         if(U_FAILURE(*status)){
@@ -802,7 +677,7 @@ array_write_xml( struct SResource *res, const char* id, const char* language, UE
         index++;
         subId = getID(sid, c, subId);
 
-        res_write_xml(current, subId, language, status);
+        res_write_xml(current, subId, language, FALSE, status);
         uprv_free(subId);
         subId = NULL;
         if(U_FAILURE(*status)){
@@ -823,7 +698,7 @@ intvector_write_xml( struct SResource *res, const char* id, const char* language
     const char* end   = "</group>\n";
     const char* startKey= "resname=\"";
 
-    const char* intStart = "<trans-unit restype = \"int\" xml:space = \"preserve\" translate=\"no\" id = \"";
+    const char* intStart = "<trans-unit restype = \"int\" xml:space = \"preserve\"  id = \"";
     const char* valIntStart = "<source>";
     const char* valIntEnd = "</source>\n";
     const char* intEnd = "</trans-unit>\n";
@@ -990,9 +865,18 @@ bin_write_xml( struct SResource *res, const char* id, const char* language, UErr
     if(res->u.fBinaryValue.fFileName!=NULL){
         uprv_strcpy(fileName, res->u.fBinaryValue.fFileName);
         f = uprv_strrchr(fileName, '\\');
-        f++;
+        if (f != NULL) {
+            f++;
+        }
+        else {
+            f = fileName;
+        }
         ext = uprv_strrchr(fileName, '.');
 
+        if (ext == NULL) {
+            fprintf(stderr, "Error: %s is an unknown binary filename type.\n", fileName);
+            exit(U_ILLEGAL_ARGUMENT_ERROR);
+        }
         if(uprv_strcmp(ext, ".jpg")==0 || uprv_strcmp(ext, ".jpeg")==0 || uprv_strcmp(ext, ".gif")==0 ){
             m_type = "\"image";
         } else if(uprv_strcmp(ext, ".wav")==0 || uprv_strcmp(ext, ".au")==0 ){
@@ -1107,16 +991,16 @@ bin_write_xml( struct SResource *res, const char* id, const char* language, UErr
         write_tabs(out);
         T_FileStream_write(out,end,(int32_t)uprv_strlen(end));
 
-        uprv_free(fn);
         uprv_free(sid);
         sid = NULL;
     }
+    uprv_free(fn);
 }
 
 
 
 static void
-table_write_xml(struct SResource *res, const char* id, const char* language, UErrorCode *status) {
+table_write_xml(struct SResource *res, const char* id, const char* language, UBool isTopLevel, UErrorCode *status) {
 
     uint32_t  i         = 0;
 
@@ -1140,6 +1024,13 @@ table_write_xml(struct SResource *res, const char* id, const char* language, UEr
         if(res->fKey<0 || uprv_strcmp(srBundle->fKeys+res->fKey ,"")==0){
             T_FileStream_write(out, start, (int32_t)uprv_strlen(start));
 
+            if(isTopLevel){
+                int32_t len = uprv_strlen(id);
+                T_FileStream_write(out, idstr, (int32_t)uprv_strlen(idstr));
+                T_FileStream_write(out, id,len);
+                T_FileStream_write(out, "\" ", 2);
+                id="";
+            }
             sid = getID(id, NULL, sid);
             /* only write the id if the sid!="" */
             if(sid[0]!='\0'){
@@ -1149,6 +1040,7 @@ table_write_xml(struct SResource *res, const char* id, const char* language, UEr
 
             }
 
+
             if(res->fComment!=NULL && res->fComment->fChars != NULL){
                 printComments(res->fComment, sid, FALSE, status);
                 printNoteElements(res->fComment, status);
@@ -1181,7 +1073,7 @@ table_write_xml(struct SResource *res, const char* id, const char* language, UEr
         save = current = res->u.fTable.fFirst;
         i       = 0;
         while (current != NULL) {
-            res_write_xml(current, sid, language, status);
+            res_write_xml(current, sid, language, FALSE, status);
 
             if(U_FAILURE(*status)){
                 return;
@@ -1228,7 +1120,7 @@ table_write_xml(struct SResource *res, const char* id, const char* language, UEr
 }
 
 void
-res_write_xml(struct SResource *res, const char* id, const char* language, UErrorCode *status) {
+res_write_xml(struct SResource *res, const char* id,  const char* language, UBool isTopLevel, UErrorCode *status) {
 
     if (U_FAILURE(*status)) {
         return ;
@@ -1256,7 +1148,7 @@ res_write_xml(struct SResource *res, const char* id, const char* language, UErro
              return;
         case URES_TABLE:
         case URES_TABLE32:
-             table_write_xml     (res, id, language, status);
+             table_write_xml     (res, id, language, isTopLevel, status);
              return;
 
         default:
@@ -1276,7 +1168,7 @@ bundle_write_xml(struct SRBRoot *bundle, const char *outputDir,const char* outpu
     char* outputFileName = NULL;
     char* originalFileName = NULL;
     const char* fileStart = "<file xml:space = \"preserve\" source-language = \"";
-    const char* file1 = "\" datatype = \"text\" ";
+    const char* file1 = "\" datatype = \"ICUResourceBundle\" ";
     const char* file2 = "original = \"";
     const char* file3 = "\" tool = \"genrb\" ";
     const char* file4 = "date = \"";
@@ -1321,10 +1213,10 @@ bundle_write_xml(struct SRBRoot *bundle, const char *outputDir,const char* outpu
     uprv_free(temp);
     temp = NULL;
 
-    /*check file name*/
+
     if (language == NULL) {
-        lang = parseFilename(filename, lang);
-        if (lang == NULL) {
+/*        lang = parseFilename(filename, lang);
+        if (lang == NULL) {*/
             /* now check if locale name is valid or not
              * this is to cater for situation where
              * pegasusServer.txt contains
@@ -1348,7 +1240,7 @@ bundle_write_xml(struct SRBRoot *bundle, const char *outputDir,const char* outpu
                  fprintf(stderr, "Error: The file name and table name do not contain a valid language code. Please use -l option to specify it.\n");
                  exit(U_ILLEGAL_ARGUMENT_ERROR);
              }
-        }
+       /* }*/
     } else {
         lang = uprv_malloc(sizeof(char)*uprv_strlen(language) +1);
         uprv_memset(lang, 0, sizeof(char)*uprv_strlen(language) +1);
@@ -1387,14 +1279,14 @@ bundle_write_xml(struct SRBRoot *bundle, const char *outputDir,const char* outpu
     }
 
     if (U_FAILURE(*status)) {
-        return;
+        goto cleanup_bundle_write_xml;
     }
 
     out= T_FileStream_open(xmlfileName,"w");
 
     if(out==NULL){
         *status = U_FILE_ACCESS_ERROR;
-        return;
+        goto cleanup_bundle_write_xml;
     }
     T_FileStream_write(out,xmlHeader, (int32_t)uprv_strlen(xmlHeader));
 
@@ -1403,7 +1295,7 @@ bundle_write_xml(struct SRBRoot *bundle, const char *outputDir,const char* outpu
         enc = outputEnc;
         conv=ucnv_open(enc,status);
         if(U_FAILURE(*status)){
-            return;
+            goto cleanup_bundle_write_xml;
         }
     }
     T_FileStream_write(out,bundleStart, (int32_t)uprv_strlen(bundleStart));
@@ -1435,7 +1327,7 @@ bundle_write_xml(struct SRBRoot *bundle, const char *outputDir,const char* outpu
     T_FileStream_write(out,bodyStart, (int32_t)uprv_strlen(bodyStart));
 
 
-    res_write_xml(bundle->fRoot, srBundle->fLocale, lang, status);
+    res_write_xml(bundle->fRoot, bundle->fLocale, lang, TRUE, status);
 
     tabCount--;
     write_tabs(out);
@@ -1450,6 +1342,7 @@ bundle_write_xml(struct SRBRoot *bundle, const char *outputDir,const char* outpu
 
     ucnv_close(conv);
 
+cleanup_bundle_write_xml:
     if(originalFileName!= NULL) {
         uprv_free(originalFileName);
         originalFileName = NULL;