/*
**********************************************************************
-* Copyright (C) 2002, International Business Machines
+* Copyright (C) 2002-2004, International Business Machines
* Corporation and others. All Rights Reserved.
**********************************************************************
* Date Name Description
**********************************************************************
*/
-#include <stdio.h>
-#include <stdlib.h>
#include "unicode/utypes.h"
#include "unicode/putil.h"
+#include "unicode/uclean.h"
#include "cmemory.h"
#include "cstring.h"
#include "filestrm.h"
+#include "uarrsort.h"
#include "unewdata.h"
#include "uoptions.h"
#include "uprops.h"
#include "propname.h"
#include "uassert.h"
+#include <stdio.h>
+
// TODO: Clean up and comment this code.
//----------------------------------------------------------------------
#include "unicode/uchar.h"
#include "unicode/uscript.h"
+#include "unicode/unorm.h"
class AliasName {
public:
NameToEnumEntry(int32_t a, int32_t b) { nameIndex=a; enumValue=b; }
};
-// Sort function for NameToEnumEntry (sort by name index)
-U_CAPI int compareNameToEnumEntry(const void* e1, const void* e2) {
- return ((NameToEnumEntry*)e1)->nameIndex - ((NameToEnumEntry*)e2)->nameIndex;
+// Sort function for NameToEnumEntry (sort by name)
+U_CFUNC int32_t
+compareNameToEnumEntry(const void * /*context*/, const void* e1, const void* e2) {
+ return
+ STRING_TABLE[((NameToEnumEntry*)e1)->nameIndex].
+ compare(STRING_TABLE[((NameToEnumEntry*)e2)->nameIndex]);
}
//----------------------------------------------------------------------
};
// Sort function for EnumToNameGroupEntry (sort by name index)
-U_CAPI int compareEnumToNameGroupEntry(const void* e1, const void* e2) {
+U_CFUNC int32_t
+compareEnumToNameGroupEntry(const void * /*context*/, const void* e1, const void* e2) {
return ((EnumToNameGroupEntry*)e1)->enumValue - ((EnumToNameGroupEntry*)e2)->enumValue;
}
};
// Sort function for EnumToValueEntry (sort by enum)
-U_CAPI int compareEnumToValueEntry(const void* e1, const void* e2) {
+U_CFUNC int32_t
+compareEnumToValueEntry(const void * /*context*/, const void* e1, const void* e2) {
return ((EnumToValueEntry*)e1)->enumValue - ((EnumToValueEntry*)e2)->enumValue;
}
// first string must be "" -- we skip it
U_ASSERT(*propertyNames[0].str == 0);
for (i=1 /*sic*/; i<propertyNameCount; ++i) {
- stringPool_size += uprv_strlen(propertyNames[i].str) + 1;
+ stringPool_size += (int32_t)(uprv_strlen(propertyNames[i].str) + 1);
}
stringPool = MALLOC(char, stringPool_size);
stringPool_offsetArray = MALLOC(Offset, stringPool_count);
stringPool_offsetArray[0] = -1; // we don't use this entry
for (i=1 /*sic*/; i<propertyNameCount; ++i) {
const char* str = propertyNames[i].str;
- int32_t len = uprv_strlen(str);
+ int32_t len = (int32_t)uprv_strlen(str);
uprv_strcpy(p, str);
p += len;
*p++ = 0;
#define COMPUTE_OFFSET(foo) COMPUTE_OFFSET2(foo,int32_t)
#define COMPUTE_OFFSET2(foo,type) \
- if (debug>0) printf(#foo "\t offset=%4d size=%5d\n", off, foo##_size); \
- foo##_offset = off; \
- U_ASSERT(IS_VALID_OFFSET(off + foo##_size)); \
- U_ASSERT(foo##_offset % sizeof(type) == 0); \
+ if (debug>0)\
+ printf(#foo "\t offset=%4d size=%5d\n", off, (int)foo##_size);\
+ foo##_offset = off;\
+ U_ASSERT(IS_VALID_OFFSET(off + foo##_size));\
+ U_ASSERT(foo##_offset % sizeof(type) == 0);\
off = (Offset) (off + foo##_size);
COMPUTE_OFFSET(enumToName); // 0:
- COMPUTE_OFFSET(nameToEnum); // 2:
- COMPUTE_OFFSET(enumToValue); // 3:
- COMPUTE_OFFSET(valueMap); // 4:
+ COMPUTE_OFFSET(nameToEnum); // 2:
+ COMPUTE_OFFSET(enumToValue); // 3:
+ COMPUTE_OFFSET(valueMap); // 4:
for (i=0; i<valueMap_count; ++i) {
if (debug>0) {
printf(" enumToName[%d]\t offset=%4d size=%5d\n",
- i, off, valueEnumToName_size[i]);
+ (int)i, off, (int)valueEnumToName_size[i]);
}
valueEnumToName_offset[i] = off; // 5:
if (debug>0) {
printf(" nameToEnum[%d]\t offset=%4d size=%5d\n",
- i, off, valueNameToEnum_size[i]);
+ (int)i, off, (int)valueNameToEnum_size[i]);
}
valueNameToEnum_offset[i] = off; // 6:
COMPUTE_OFFSET2(stringPool,char); // 99:
total_size = off;
- if (debug>0) printf("total size=%5d\n\n", total_size);
+ if (debug>0) printf("total size=%5d\n\n", (int)total_size);
U_ASSERT(total_size <= (MAX_OFFSET+1));
}
void Builder::fixupNCEnumToNameGroup(NonContiguousEnumToOffset* e2ng) {
int32_t i;
- EnumValue* e = e2ng->getEnumArray();
+ /*EnumValue* e = e2ng->getEnumArray();*/
Offset* p = e2ng->getOffsetArray();
for (i=0; i<e2ng->count; ++i) {
p[i] = nameGroupPool_offset + sizeof(Offset) * p[i];
header.nameToEnum_offset = nameToEnum_offset;
header.enumToValue_offset = enumToValue_offset;
// header meta-info used by Java:
- U_ASSERT(total_size > 0 && total_size < 0x7FFF);
+ U_ASSERT(total_size > 0 && total_size < 0x7FFF);
header.total_size = (int16_t) total_size;
header.valueMap_offset = valueMap_offset;
header.valueMap_count = (int16_t) valueMap_count;
header.stringPool_offset = stringPool_offset;
header.stringPool_count = (int16_t) stringPool_count - 1; // don't include "" entry
- U_ASSERT(valueMap_count <= 0x7FFF);
- U_ASSERT(nameGroupPool_count <= 0x7FFF);
- U_ASSERT(stringPool_count <= 0x7FFF);
+ U_ASSERT(valueMap_count <= 0x7FFF);
+ U_ASSERT(nameGroupPool_count <= 0x7FFF);
+ U_ASSERT(stringPool_count <= 0x7FFF);
// 3:
Offset* p = enumToValue->getOffsetArray();
- EnumValue* e = enumToValue->getEnumArray();
+ /*EnumValue* e = enumToValue->getEnumArray();*/
U_ASSERT(valueMap_count == enumToValue->count);
for (i=0; i<valueMap_count; ++i) {
p[i] = (Offset)(valueMap_offset + sizeof(ValueMap) * i);
APPEND(nameGroupPool);
APPEND(stringPool);
- U_ASSERT(p == limit);
+ if (p != limit) {
+ fprintf(stderr, "p != limit; p = %p, limit = %p", p, limit);
+ exit(1);
+ }
return result;
}
{VERSION_0, VERSION_1, VERSION_2, VERSION_3} /* Unicode version */
};
-// Glue for C<->C++
-U_CAPI int compareAliasNames(const void* elem1, const void* elem2) {
- return ((const AliasName*)elem1)->compare(*(const AliasName*)elem2);
-}
-
class genpname {
// command-line options
};
int main(int argc, char *argv[]) {
+ UErrorCode status = U_ZERO_ERROR;
+ u_init(&status);
+ if (U_FAILURE(status) && status != U_FILE_ACCESS_ERROR) {
+ // Note: u_init() will try to open ICU property data.
+ // failures here are expected when building ICU from scratch.
+ // ignore them.
+ fprintf(stderr, "genpname: can not initialize ICU. Status = %s\n",
+ u_errorName(status));
+ exit(1);
+ }
+
genpname app;
U_MAIN_INIT_ARGS(argc, argv);
- return app.MMain(argc, argv);
+ int retVal = app.MMain(argc, argv);
+ u_cleanup();
+ return retVal;
}
static UOption options[]={
NameToEnumEntry(names[j], p.enumValue);
}
}
- qsort((void*) nameIndex, nameIndexCount, sizeof(nameIndex[0]),
- compareNameToEnumEntry);
+
+ /*
+ * use a stable sort to ensure consistent results between
+ * genpname.cpp and the propname.cpp swapping code
+ */
+ UErrorCode errorCode = U_ZERO_ERROR;
+ uprv_sortArray(nameIndex, nameIndexCount, sizeof(nameIndex[0]),
+ compareNameToEnumEntry, NULL, TRUE, &errorCode);
if (debug>1) {
- printf("Alias names: %d\n", nameIndexCount);
+ printf("Alias names: %d\n", (int)nameIndexCount);
for (i=0; i<nameIndexCount; ++i) {
printf("%s => %d\n",
STRING_TABLE[nameIndex[i].nameIndex].str,
- nameIndex[i].enumValue);
+ (int)nameIndex[i].enumValue);
}
printf("\n");
}
const Alias& p = list[i];
enumIndex[i] = EnumToNameGroupEntry(p.enumValue, p.nameGroupIndex);
}
- qsort((void*) enumIndex, count, sizeof(enumIndex[0]),
- compareEnumToNameGroupEntry);
+
+ UErrorCode errorCode = U_ZERO_ERROR;
+ uprv_sortArray(enumIndex, count, sizeof(enumIndex[0]),
+ compareEnumToNameGroupEntry, NULL, FALSE, &errorCode);
if (debug>1) {
- printf("Property enums: %d\n", count);
+ printf("Property enums: %d\n", (int)count);
for (i=0; i<count; ++i) {
printf("%d => %d: ",
- enumIndex[i].enumValue,
- enumIndex[i].nameGroupIndex);
+ (int)enumIndex[i].enumValue,
+ (int)enumIndex[i].nameGroupIndex);
UBool done = FALSE;
for (j=enumIndex[i].nameGroupIndex; !done; ++j) {
k = NAME_GROUP[j];
return enumIndex;
}
-int genpname::MMain(int argc, char* argv[]) {
-
+int genpname::MMain(int argc, char* argv[])
+{
int32_t i, j;
+ UErrorCode status = U_ZERO_ERROR;
+
+ u_init(&status);
+ if (U_FAILURE(status) && status != U_FILE_ACCESS_ERROR) {
+ fprintf(stderr, "Error: u_init returned %s\n", u_errorName(status));
+ status = U_ZERO_ERROR;
+ }
+
/* preset then read command line options */
options[3].value=u_getDataDirectory();
debug < 0 || debug > 9) {
fprintf(stderr,
"usage: %s [-options]\n"
- "\tcreate " U_ICUDATA_NAME "_" PNAME_DATA_NAME "." PNAME_DATA_TYPE "\n"
+ "\tcreate " PNAME_DATA_NAME "." PNAME_DATA_TYPE "\n"
"options:\n"
"\t-h or -? or --help this usage text\n"
"\t-v or --verbose turn on verbose output\n"
verbose = options[4].doesOccur;
// ------------------------------------------------------------
- // Sort the string table. This produces the proper sorting
- // using the actual comparison function we will use.
- qsort((void*) STRING_TABLE, STRING_COUNT, sizeof(STRING_TABLE[0]),
- compareAliasNames);
+ // Do not sort the string table, instead keep it in data.h order.
+ // This simplifies data swapping and testing thereof because the string
+ // table itself need not be sorted during swapping.
+ // The NameToEnum sorter sorts each such map's string offsets instead.
+
if (debug>1) {
- printf("String pool: %d\n", STRING_COUNT);
- }
- for (i=0; i<STRING_COUNT; ++i) {
- REMAP[STRING_TABLE[i].index] = i;
- if (debug>1) {
- if (i != 0) printf(", ");
- printf("%s (%d)", STRING_TABLE[i].str, STRING_TABLE[i].index);
+ printf("String pool: %d\n", (int)STRING_COUNT);
+ for (i=0; i<STRING_COUNT; ++i) {
+ if (i != 0) {
+ printf(", ");
+ }
+ printf("%s (%d)", STRING_TABLE[i].str, (int)STRING_TABLE[i].index);
}
- }
- if (debug>1) {
printf("\n\n");
}
- // ------------------------------------------------------------
- // Fixup the NAME_GROUP indices so they match the sorted order
- for (i=0; i<NAME_GROUP_COUNT; ++i) {
- // keep negative entries (end markers) negative
- if (NAME_GROUP[i] < 0) {
- NAME_GROUP[i] = -REMAP[-NAME_GROUP[i]];
- } else {
- NAME_GROUP[i] = REMAP[NAME_GROUP[i]];
- }
- }
-
// ------------------------------------------------------------
// Create top-level property indices
++j;
}
enumToValue_count = j;
- qsort((void*) enumToValue, enumToValue_count, sizeof(enumToValue[0]),
- compareEnumToValueEntry);
+
+ uprv_sortArray(enumToValue, enumToValue_count, sizeof(enumToValue[0]),
+ compareEnumToValueEntry, NULL, FALSE, &status);
// ------------------------------------------------------------
// Build PropertyAliases layout in memory
UNewDataMemory *pdata;
UErrorCode status = U_ZERO_ERROR;
- pdata = udata_create(destdir, PNAME_DATA_TYPE, U_ICUDATA_NAME "_" PNAME_DATA_NAME, &dataInfo,
+ pdata = udata_create(destdir, PNAME_DATA_TYPE, PNAME_DATA_NAME, &dataInfo,
useCopyright ? U_COPYRIGHT_STRING : 0, &status);
if (U_FAILURE(status)) {
die("Unable to create data memory");