1 /* Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
2 
3    This program is free software; you can redistribute it and/or modify
4    it under the terms of the GNU General Public License, version 2.0,
5    as published by the Free Software Foundation.
6 
7    This program is also distributed with certain software (including
8    but not limited to OpenSSL) that is licensed under separate terms,
9    as designated in a particular file or component or in included license
10    documentation.  The authors of MySQL hereby grant you an additional
11    permission to link the program and your derivative works with the
12    separately licensed software that they have included with MySQL.
13 
14    This program is distributed in the hope that it will be useful,
15    but WITHOUT ANY WARRANTY; without even the implied warranty of
16    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17    GNU General Public License, version 2.0, for more details.
18 
19    You should have received a copy of the GNU General Public License
20    along with this program; if not, write to the Free Software
21    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA */
22 
23 /* can't use -lmysys because this prog is used to create -lstrings */
24 
25 
26 #include <my_global.h>
27 #include <ctype.h>
28 #include <string.h>
29 #include <unistd.h>
30 
31 #define CHARSETS_SUBDIR "sql/share/charsets"
32 #define CTYPE_TABLE_SIZE      257
33 #define TO_LOWER_TABLE_SIZE   256
34 #define TO_UPPER_TABLE_SIZE   256
35 #define SORT_ORDER_TABLE_SIZE 256
36 #define ROW_LEN 16
37 
38 void print_arrays_for(char *set);
39 
40 char *prog;
41 char buf[1024], *p, *endptr;
42 
43 int
main(int argc,char ** argv)44 main(int argc, char **argv)
45 {
46   prog = *argv;
47 
48   if (argc < 2) {
49     fprintf(stderr, "usage: %s source-dir [charset [, charset]]\n", prog);
50     exit(EXIT_FAILURE);
51   }
52 
53   --argc; ++argv;       /* skip program name */
54 
55   if (chdir(*argv) != 0) {
56     fprintf(stderr, "%s: can't cd to %s\n", prog, *argv);
57     exit(EXIT_FAILURE);
58   }
59   --argc; ++argv;
60 
61   if (chdir(CHARSETS_SUBDIR) != 0) {
62     fprintf(stderr, "%s: can't cd to %s\n", prog, CHARSETS_SUBDIR);
63     exit(EXIT_FAILURE);
64   }
65 
66   while (argc--)
67     print_arrays_for(*argv++);
68 
69   exit(EXIT_SUCCESS);
70 }
71 
72 void
print_array(FILE * f,const char * set,const char * name,int n)73 print_array(FILE *f, const char *set, const char *name, int n)
74 {
75   int i;
76   char val[100];
77 
78   printf("uchar %s_%s[] = {\n", name, set);
79 
80   p = buf;
81   *buf = '\0';
82   for (i = 0; i < n; ++i)
83   {
84     /* get a word from f */
85     endptr = p;
86     for (;;)
87     {
88       while (isspace(*endptr))
89         ++endptr;
90       if (*endptr && *endptr != '#')    /* not comment */
91         break;
92       if ((fgets(buf, sizeof(buf), f)) == NULL)
93         return;         /* XXX: break silently */
94       endptr = buf;
95     }
96 
97     p = val;
98     while (!isspace(*endptr))
99       *p++ = *endptr++;
100     *p = '\0';
101     p = endptr;
102 
103     /* write the value out */
104 
105     if (i == 0 || i % ROW_LEN == n % ROW_LEN)
106       printf("  ");
107 
108     printf("%3d", (unsigned char) strtol(val, (char **) NULL, 16));
109 
110     if (i < n - 1)
111       printf(",");
112 
113     if ((i+1) % ROW_LEN == n % ROW_LEN)
114       printf("\n");
115   }
116 
117   printf("};\n\n");
118 }
119 
120 void
print_arrays_for(char * set)121 print_arrays_for(char *set)
122 {
123   FILE *f;
124 
125   snprintf(buf, sizeof(buf), "%s.conf", set);
126 
127   if ((f = fopen(buf, "r")) == NULL) {
128     fprintf(stderr, "%s: can't read conf file for charset %s\n", prog, set);
129     exit(EXIT_FAILURE);
130   }
131 
132   printf("\
133 /* The %s character set.  Generated automatically by configure and\n\
134  * the %s program\n\
135  */\n\n",
136 	 set, prog);
137 
138   /* it would be nice if this used the code in mysys/charset.c, but... */
139   print_array(f, set, "ctype",      CTYPE_TABLE_SIZE);
140   print_array(f, set, "to_lower",   TO_LOWER_TABLE_SIZE);
141   print_array(f, set, "to_upper",   TO_UPPER_TABLE_SIZE);
142   print_array(f, set, "sort_order", SORT_ORDER_TABLE_SIZE);
143   printf("\n");
144 
145   fclose(f);
146 
147   return;
148 }
149