diff --git a/tools/winebuild/res32.c b/tools/winebuild/res32.c index a0209ad6f2a..80890f55458 100644 --- a/tools/winebuild/res32.c +++ b/tools/winebuild/res32.c @@ -35,6 +35,7 @@ typedef unsigned short WCHAR; struct string_id { WCHAR *str; /* ptr to Unicode string */ + unsigned int len; /* len in characters */ unsigned short id; /* integer id if str is NULL */ }; @@ -92,19 +93,6 @@ static inline struct resource *add_resource( DLLSPEC *spec ) return &spec->resources[spec->nb_resources++]; } -static inline unsigned int strlenW( const WCHAR *str ) -{ - const WCHAR *s = str; - while (*s) s++; - return s - str; -} - -static inline int strcmpW( const WCHAR *str1, const WCHAR *str2 ) -{ - while (*str1 && (*str1 == *str2)) { str1++; str2++; } - return *str1 - *str2; -} - static struct res_name *add_name( struct res_type *type, struct resource *res ) { struct res_name *name; @@ -132,8 +120,11 @@ static struct res_type *add_type( struct res_tree *tree, struct resource *res ) /* get a string from the current resource file */ static void get_string( struct string_id *str ) { + unsigned int i = 0; + size_t start_pos = input_buffer_pos; WCHAR wc = get_word(); + str->len = 0; if (wc == 0xffff) { str->str = NULL; @@ -141,10 +132,11 @@ static void get_string( struct string_id *str ) } else { - WCHAR *p = xmalloc( (strlenW( (const WCHAR *)(input_buffer + input_buffer_pos) - 1) + 1) * sizeof(WCHAR) ); - str->str = p; - str->id = 0; - if ((*p++ = wc)) while ((*p++ = get_word())); + input_buffer_pos = start_pos; + while (get_word()) str->len++; + str->str = xmalloc( str->len * sizeof(WCHAR) ); + input_buffer_pos = start_pos; + while ((wc = get_word())) str->str[i++] = wc; } } @@ -153,8 +145,8 @@ static void put_string( const struct string_id *str ) { if (str->str) { - const WCHAR *p = str->str; - while (*p) put_word( *p++ ); + unsigned int i; + for (i = 0; i < str->len; i++) put_word( str->str[i] ); put_word( 0 ); } else @@ -253,13 +245,18 @@ int load_res32_file( const char *name, DLLSPEC *spec ) /* compare two unicode strings/ids */ static int cmp_string( const struct string_id *str1, const struct string_id *str2 ) { + unsigned int i; + if (!str1->str) { if (!str2->str) return str1->id - str2->id; return 1; /* an id compares larger than a string */ } if (!str2->str) return -1; - return strcmpW( str1->str, str2->str ); + + for (i = 0; i < str1->len && i < str2->len; i++) + if (str1->str[i] != str2->str[i]) return str1->str[i] - str2->str[i]; + return str1->len - str2->len; } /* compare two resources for sorting the resource directory */ @@ -278,11 +275,13 @@ static int cmp_res( const void *ptr1, const void *ptr2 ) static char *format_res_string( const struct string_id *str ) { - int i, len = str->str ? strlenW(str->str) + 1 : 5; - char *ret = xmalloc( len ); + unsigned int i; + char *ret; - if (!str->str) sprintf( ret, "%04x", str->id ); - else for (i = 0; i < len; i++) ret[i] = str->str[i]; /* dumb W->A conversion */ + if (!str->str) return strmake( "#%04x", str->id ); + ret = xmalloc( str->len + 1 ); + for (i = 0; i < str->len; i++) ret[i] = str->str[i]; /* dumb W->A conversion */ + ret[i] = 0; return ret; } @@ -365,7 +364,7 @@ static struct res_tree *build_resource_tree( DLLSPEC *spec, unsigned int *dir_si if (type->type->str) { type->name_offset = offset | 0x80000000; - offset += (strlenW(type->type->str)+1) * sizeof(WCHAR); + offset += (type->type->len + 1) * sizeof(WCHAR); } else type->name_offset = type->type->id; @@ -374,7 +373,7 @@ static struct res_tree *build_resource_tree( DLLSPEC *spec, unsigned int *dir_si if (name->name->str) { name->name_offset = offset | 0x80000000; - offset += (strlenW(name->name->str)+1) * sizeof(WCHAR); + offset += (name->name->len + 1) * sizeof(WCHAR); } else name->name_offset = name->name->id; for (k = 0, res = name->res; k < name->nb_languages; k++, res++) @@ -399,13 +398,13 @@ static void free_resource_tree( struct res_tree *tree ) } /* output a Unicode string */ -static void output_string( const WCHAR *name ) +static void output_string( const struct string_id *str ) { - int i, len = strlenW(name); - output( "\t.short 0x%04x", len ); - for (i = 0; i < len; i++) output( ",0x%04x", name[i] ); + unsigned int i; + output( "\t.short 0x%04x", str->len ); + for (i = 0; i < str->len; i++) output( ",0x%04x", str->str[i] ); output( " /* " ); - for (i = 0; i < len; i++) output( "%c", isprint((char)name[i]) ? (char)name[i] : '?' ); + for (i = 0; i < str->len; i++) output( "%c", isprint((char)str->str[i]) ? (char)str->str[i] : '?' ); output( " */\n" ); } @@ -480,9 +479,9 @@ void output_resources( DLLSPEC *spec ) for (i = 0, type = tree->types; i < tree->nb_types; i++, type++) { - if (type->type->str) output_string( type->type->str ); + if (type->type->str) output_string( type->type ); for (n = 0, name = type->names; n < type->nb_names; n++, name++) - if (name->name->str) output_string( name->name->str ); + if (name->name->str) output_string( name->name ); } /* resource data */ @@ -503,11 +502,12 @@ void output_resources( DLLSPEC *spec ) } /* output a Unicode string in binary format */ -static void output_bin_string( const WCHAR *name ) +static void output_bin_string( const struct string_id *str ) { - int i, len = strlenW(name); - put_word( len ); - for (i = 0; i < len; i++) put_word( name[i] ); + unsigned int i; + + put_word( str->len ); + for (i = 0; i < str->len; i++) put_word( str->str[i] ); } /* output a resource directory in binary format */ @@ -588,9 +588,9 @@ void output_bin_resources( DLLSPEC *spec, unsigned int start_rva ) for (i = 0, type = tree->types; i < tree->nb_types; i++, type++) { - if (type->type->str) output_bin_string( type->type->str ); + if (type->type->str) output_bin_string( type->type ); for (n = 0, name = type->names; n < type->nb_names; n++, name++) - if (name->name->str) output_bin_string( name->name->str ); + if (name->name->str) output_bin_string( name->name ); } /* resource data */ @@ -610,10 +610,10 @@ static unsigned int get_resource_header_size( const struct resource *res ) unsigned int size = 5 * sizeof(unsigned int) + 2 * sizeof(unsigned short); if (!res->type.str) size += 2 * sizeof(unsigned short); - else size += (strlenW(res->type.str) + 1) * sizeof(WCHAR); + else size += (res->type.len + 1) * sizeof(WCHAR); if (!res->name.str) size += 2 * sizeof(unsigned short); - else size += (strlenW(res->name.str) + 1) * sizeof(WCHAR); + else size += (res->name.len + 1) * sizeof(WCHAR); return size; }