]> jfr.im git - irc/quakenet/snircd.git/blob - ircd/ircd_snprintf.c
Initial import of 2.10.12.01
[irc/quakenet/snircd.git] / ircd / ircd_snprintf.c
1 /*
2 * IRC - Internet Relay Chat, ircd/ircd_snprintf.c
3 * Copyright (C) 2000 Kevin L. Mitchell <klmitch@mit.edu>
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 1, or (at your option)
8 * any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18 */
19 /** @file
20 * @brief IRC-specific printf() clone implementation.
21 * @version $Id: ircd_snprintf.c,v 1.18 2004/12/11 05:13:45 klmitch Exp $
22 */
23 #include "config.h"
24
25 #include "client.h"
26 #include "channel.h"
27 #include "ircd_log.h"
28 #include "ircd_snprintf.h"
29 #include "struct.h"
30
31 /* #include <assert.h> -- Now using assert in ircd_log.h */
32 #include <errno.h>
33 #include <stddef.h>
34 #include <stdlib.h>
35 #include <string.h>
36 #include <time.h>
37
38 /* Inhibit complaints when we use GCC extensions */
39 #if defined(__GNUC__) && defined(HAVE_LONG_LONG)
40 # define EXTENSION __extension__
41 #else
42 /** Fallback (empty) definition of EXTENSION. */
43 # define EXTENSION
44 #endif
45
46 /* Find the largest type */
47 #ifdef HAVE_LONG_LONG
48 EXTENSION typedef long long _large_t;
49 EXTENSION typedef unsigned long long _ularge_t;
50 # define SIZEOF__LARGE_T SIZEOF_LONG_LONG
51 /* Oh, if long long happens to be the size of void *, set _pointer_t, too */
52 # if SIZEOF_LONG_LONG == SIZEOF_VOID_P
53 typedef _ularge_t _pointer_t;
54 # define HAVE_POINTER_T
55 # endif
56 #else
57 /** Fallback definition of the largest integer type. */
58 typedef long _large_t;
59 /** Fallback definition of the largest unsigned integer type. */
60 typedef unsigned long _ularge_t;
61 /** Fallback definition of SIZEOF__LARGE_T. */
62 # define SIZEOF__LARGE_T SIZEOF_LONG
63 #endif
64
65 /* Select something for _pointer_t */
66 #ifndef HAVE_POINTER_T
67 # if SIZEOF_LONG == SIZEOF_VOID_P
68 /** Unsigned integer type large enough to hold a pointer. */
69 typedef unsigned long _pointer_t;
70 # elif SIZEOF_INT == SIZEOF_VOID_P
71 typedef unsigned int _pointer_t;
72 # else
73 # error Unable to find a suitable type for _pointer_t
74 # endif
75 #endif /* HAVE_POINTER_T */
76
77 /** rough length sufficient to hold an octal number, since those can be large */
78 #define INTBUF_LEN (SIZEOF__LARGE_T * 3)
79
80 /** Return minimum of \a i1 and \a i2. */
81 #define SNP_MIN(i1, i2) ((i1) < (i2) ? (i1) : (i2))
82 /** Return maximum of \a i1 and \a i2. */
83 #define SNP_MAX(i1, i2) ((i1) > (i2) ? (i1) : (i2))
84 /** Indicate total number of bytes "pseudo-output" in buffer. */
85 #define TOTAL(buf_p) ((buf_p)->buf_loc + \
86 SNP_MAX((buf_p)->buf_overflow, (buf_p)->overflow))
87
88 #define WIDTH_MAX 999 /**< keep from overflowing width */
89
90 /** data about the output buffer */
91 struct BufData {
92 char *buf; /**< pointer to buffer */
93 size_t buf_size; /**< maximum size of buffer */
94 size_t buf_overflow; /**< how much buffer has been overflowed */
95 size_t buf_loc; /**< where we are in the buffer */
96 short limit; /**< max # of chars to convert */
97 size_t overflow; /**< how much we overflowed the limit */
98 };
99
100 /** initializer for BufData */
101 #define BUFDATA_INIT { 0, 0, 0, 0, 0, 0 }
102
103 /** data about format fields */
104 struct FieldData {
105 unsigned int flags; /**< flags describing argument */
106 short base; /**< base for integer conversions */
107 short width; /**< width of field */
108 short prec; /**< precision of field */
109 union {
110 _ularge_t v_int; /**< an integer value */
111 long double v_float; /**< a floating point value -- NOT SUPPORTED */
112 void *v_ptr; /**< a pointer value */
113 } value; /**< value of a field */
114 };
115
116 /** initializer for FieldData */
117 #define FIELDDATA_INIT { 0, 0, 0, 0, { 0 } }
118
119 /* Specifier flags */
120 #define FLAG_MINUS 0x00000001 /**< found a '-' flag */
121 #define FLAG_PLUS 0x00000002 /**< found a '+' flag */
122 #define FLAG_SPACE 0x00000004 /**< found a ' ' flag */
123 #define FLAG_ALT 0x00000008 /**< found a '#' flag */
124 #define FLAG_ZERO 0x00000010 /**< found a '0' flag */
125 #define FLAG_COLON 0x00000020 /**< found a ':' flag */
126
127 #define FLAG_RESERVED1 0x00000040 /**< reserved for future expansion */
128 #define FLAG_RESERVED0 0x00000080 /**< reserved for future expansion */
129
130 /* integer types */
131 #define TYPE_CHAR 0x00000100 /**< number is a char */
132 #define TYPE_SHORT 0x00000200 /**< number is a short */
133 #define TYPE_LONG 0x00000400 /**< number is a long */
134 #define TYPE_QUAD 0x00000800 /**< number is a quad */
135
136 /* special integer types */
137 #define TYPE_INTMAX 0x00001000 /**< number is an intmax_t */
138 #define TYPE_PTRDIFF 0x00002000 /**< number is a ptrdiff_t */
139 #define TYPE_SIZE 0x00004000 /**< number is a size_t */
140 #define TYPE_TIME 0x00008000 /**< number is a time_t */
141 #define TYPE_POINTER 0x00010000 /**< number is a pointer_t */
142
143 /* floating point types */
144 #define TYPE_LONGDOUBLE 0x00020000 /**< number is a long double */
145
146 #define TYPE_RESERVED1 0x00040000 /**< reserved for future expansion */
147 #define TYPE_RESERVED0 0x00080000 /**< reserved for future expansion */
148
149 /** Mask to get just the type data */
150 #define TYPE_MASK (TYPE_CHAR | TYPE_SHORT | TYPE_LONG | TYPE_QUAD | \
151 TYPE_INTMAX | TYPE_PTRDIFF | TYPE_SIZE | TYPE_TIME | \
152 TYPE_POINTER | TYPE_LONGDOUBLE)
153
154 /* type of argument to extract */
155 #define ARG_INT 0x00100000 /**< argument is an integer */
156 #define ARG_FLOAT 0x00200000 /**< argument is a float */
157 #define ARG_PTR 0x00300000 /**< argument is a pointer */
158
159 #define ARG_RESERVED11 0x00400000 /**< reserved for future expansion */
160 #define ARG_RESERVED10 0x00500000 /**< reserved for future expansion */
161 #define ARG_RESERVED9 0x00600000 /**< reserved for future expansion */
162 #define ARG_RESERVED8 0x00700000 /**< reserved for future expansion */
163 #define ARG_RESERVED7 0x00800000 /**< reserved for future expansion */
164 #define ARG_RESERVED6 0x00900000 /**< reserved for future expansion */
165 #define ARG_RESERVED5 0x00a00000 /**< reserved for future expansion */
166 #define ARG_RESERVED4 0x00b00000 /**< reserved for future expansion */
167 #define ARG_RESERVED3 0x00c00000 /**< reserved for future expansion */
168 #define ARG_RESERVED2 0x00d00000 /**< reserved for future expansion */
169 #define ARG_RESERVED1 0x00e00000 /**< reserved for future expansion */
170 #define ARG_RESERVED0 0x00f00000 /**< reserved for future expansion */
171
172 /* Mask to get just the argument data */
173 #define ARG_MASK 0x00f00000 /**< masks off non-argument bits */
174
175 /* type of conversion to perform */
176 #define CONV_INT 0x01000000 /**< convert integers */
177 #define CONV_FLOAT 0x02000000 /**< convert floats */
178 #define CONV_CHAR 0x03000000 /**< convert chars */
179 #define CONV_STRING 0x04000000 /**< convert strings */
180 #define CONV_VARARGS 0x05000000 /**< convert a %v */
181 #define CONV_CLIENT 0x06000000 /**< convert a struct Client */
182 #define CONV_CHANNEL 0x07000000 /**< convert a struct Channel */
183
184 #define CONV_RESERVED7 0x08000000 /**< reserved for future expansion */
185 #define CONV_RESERVED6 0x09000000 /**< reserved for future expansion */
186 #define CONV_RESERVED5 0x0a000000 /**< reserved for future expansion */
187 #define CONV_RESERVED4 0x0b000000 /**< reserved for future expansion */
188 #define CONV_RESERVED3 0x0c000000 /**< reserved for future expansion */
189 #define CONV_RESERVED2 0x0d000000 /**< reserved for future expansion */
190 #define CONV_RESERVED1 0x0e000000 /**< reserved for future expansion */
191 #define CONV_RESERVED0 0x0f000000 /**< reserved for future expansion */
192
193 /* Mask to get just the conversion data */
194 #define CONV_MASK 0x0f000000 /**< masks off non-conversion bits */
195
196 /* Value information flags */
197 #define INFO_RESERVED0 0x10000000 /**< reserved for future expansion */
198 #define INFO_UPPERCASE 0x20000000 /**< use uppercase characters */
199 #define INFO_UNSIGNED 0x40000000 /**< number is unsigned */
200 #define INFO_NEGATIVE 0x80000000 /**< number is negative */
201
202 #define BASE_OCTAL 9 /**< octal base; bits-per-char * 3 */
203 #define BASE_DECIMAL -1000 /**< decimal base; 10 ** 3 */
204 #define BASE_HEX 12 /**< hexadecimal base; bits-per-char * 3 */
205
206
207 /* padding... 1 2 3 4 5 */
208 /* 12345678901234567890123456789012345678901234567890 */
209 /** Predefined space padding. */
210 static char spaces[] = " ";
211 /** Predefined zero padding. */
212 static char zeros[] = "00000000000000000000000000000000000000000000000000";
213
214 /** Length of predefined padding strings. */
215 #define PAD_LENGTH (sizeof(spaces) - 1)
216
217 /*
218 * Note that these string tables have characters reversed. There is, of
219 * course, a reason for this; check out how they're built in doprintf.
220 */
221
222 /** string table for octal values */
223 static char *octal[] = {
224 "", "1", "2", "3", "4", "5", "6", "7",
225 "01", "11", "21", "31", "41", "51", "61", "71",
226 "02", "12", "22", "32", "42", "52", "62", "72",
227 "03", "13", "23", "33", "43", "53", "63", "73",
228 "04", "14", "24", "34", "44", "54", "64", "74",
229 "05", "15", "25", "35", "45", "55", "65", "75",
230 "06", "16", "26", "36", "46", "56", "66", "76",
231 "07", "17", "27", "37", "47", "57", "67", "77",
232 "001", "101", "201", "301", "401", "501", "601", "701",
233 "011", "111", "211", "311", "411", "511", "611", "711",
234 "021", "121", "221", "321", "421", "521", "621", "721",
235 "031", "131", "231", "331", "431", "531", "631", "731",
236 "041", "141", "241", "341", "441", "541", "641", "741",
237 "051", "151", "251", "351", "451", "551", "651", "751",
238 "061", "161", "261", "361", "461", "561", "661", "761",
239 "071", "171", "271", "371", "471", "571", "671", "771",
240 "002", "102", "202", "302", "402", "502", "602", "702",
241 "012", "112", "212", "312", "412", "512", "612", "712",
242 "022", "122", "222", "322", "422", "522", "622", "722",
243 "032", "132", "232", "332", "432", "532", "632", "732",
244 "042", "142", "242", "342", "442", "542", "642", "742",
245 "052", "152", "252", "352", "452", "552", "652", "752",
246 "062", "162", "262", "362", "462", "562", "662", "762",
247 "072", "172", "272", "372", "472", "572", "672", "772",
248 "003", "103", "203", "303", "403", "503", "603", "703",
249 "013", "113", "213", "313", "413", "513", "613", "713",
250 "023", "123", "223", "323", "423", "523", "623", "723",
251 "033", "133", "233", "333", "433", "533", "633", "733",
252 "043", "143", "243", "343", "443", "543", "643", "743",
253 "053", "153", "253", "353", "453", "553", "653", "753",
254 "063", "163", "263", "363", "463", "563", "663", "763",
255 "073", "173", "273", "373", "473", "573", "673", "773",
256 "004", "104", "204", "304", "404", "504", "604", "704",
257 "014", "114", "214", "314", "414", "514", "614", "714",
258 "024", "124", "224", "324", "424", "524", "624", "724",
259 "034", "134", "234", "334", "434", "534", "634", "734",
260 "044", "144", "244", "344", "444", "544", "644", "744",
261 "054", "154", "254", "354", "454", "554", "654", "754",
262 "064", "164", "264", "364", "464", "564", "664", "764",
263 "074", "174", "274", "374", "474", "574", "674", "774",
264 "005", "105", "205", "305", "405", "505", "605", "705",
265 "015", "115", "215", "315", "415", "515", "615", "715",
266 "025", "125", "225", "325", "425", "525", "625", "725",
267 "035", "135", "235", "335", "435", "535", "635", "735",
268 "045", "145", "245", "345", "445", "545", "645", "745",
269 "055", "155", "255", "355", "455", "555", "655", "755",
270 "065", "165", "265", "365", "465", "565", "665", "765",
271 "075", "175", "275", "375", "475", "575", "675", "775",
272 "006", "106", "206", "306", "406", "506", "606", "706",
273 "016", "116", "216", "316", "416", "516", "616", "716",
274 "026", "126", "226", "326", "426", "526", "626", "726",
275 "036", "136", "236", "336", "436", "536", "636", "736",
276 "046", "146", "246", "346", "446", "546", "646", "746",
277 "056", "156", "256", "356", "456", "556", "656", "756",
278 "066", "166", "266", "366", "466", "566", "666", "766",
279 "076", "176", "276", "376", "476", "576", "676", "776",
280 "007", "107", "207", "307", "407", "507", "607", "707",
281 "017", "117", "217", "317", "417", "517", "617", "717",
282 "027", "127", "227", "327", "427", "527", "627", "727",
283 "037", "137", "237", "337", "437", "537", "637", "737",
284 "047", "147", "247", "347", "447", "547", "647", "747",
285 "057", "157", "257", "357", "457", "557", "657", "757",
286 "067", "167", "267", "367", "467", "567", "667", "767",
287 "077", "177", "277", "377", "477", "577", "677", "777"
288 };
289
290 /** string table for decimal values */
291 static char *decimal[] = {
292 "", "1", "2", "3", "4", "5", "6", "7", "8", "9",
293 "01", "11", "21", "31", "41", "51", "61", "71", "81", "91",
294 "02", "12", "22", "32", "42", "52", "62", "72", "82", "92",
295 "03", "13", "23", "33", "43", "53", "63", "73", "83", "93",
296 "04", "14", "24", "34", "44", "54", "64", "74", "84", "94",
297 "05", "15", "25", "35", "45", "55", "65", "75", "85", "95",
298 "06", "16", "26", "36", "46", "56", "66", "76", "86", "96",
299 "07", "17", "27", "37", "47", "57", "67", "77", "87", "97",
300 "08", "18", "28", "38", "48", "58", "68", "78", "88", "98",
301 "09", "19", "29", "39", "49", "59", "69", "79", "89", "99",
302 "001", "101", "201", "301", "401", "501", "601", "701", "801", "901",
303 "011", "111", "211", "311", "411", "511", "611", "711", "811", "911",
304 "021", "121", "221", "321", "421", "521", "621", "721", "821", "921",
305 "031", "131", "231", "331", "431", "531", "631", "731", "831", "931",
306 "041", "141", "241", "341", "441", "541", "641", "741", "841", "941",
307 "051", "151", "251", "351", "451", "551", "651", "751", "851", "951",
308 "061", "161", "261", "361", "461", "561", "661", "761", "861", "961",
309 "071", "171", "271", "371", "471", "571", "671", "771", "871", "971",
310 "081", "181", "281", "381", "481", "581", "681", "781", "881", "981",
311 "091", "191", "291", "391", "491", "591", "691", "791", "891", "991",
312 "002", "102", "202", "302", "402", "502", "602", "702", "802", "902",
313 "012", "112", "212", "312", "412", "512", "612", "712", "812", "912",
314 "022", "122", "222", "322", "422", "522", "622", "722", "822", "922",
315 "032", "132", "232", "332", "432", "532", "632", "732", "832", "932",
316 "042", "142", "242", "342", "442", "542", "642", "742", "842", "942",
317 "052", "152", "252", "352", "452", "552", "652", "752", "852", "952",
318 "062", "162", "262", "362", "462", "562", "662", "762", "862", "962",
319 "072", "172", "272", "372", "472", "572", "672", "772", "872", "972",
320 "082", "182", "282", "382", "482", "582", "682", "782", "882", "982",
321 "092", "192", "292", "392", "492", "592", "692", "792", "892", "992",
322 "003", "103", "203", "303", "403", "503", "603", "703", "803", "903",
323 "013", "113", "213", "313", "413", "513", "613", "713", "813", "913",
324 "023", "123", "223", "323", "423", "523", "623", "723", "823", "923",
325 "033", "133", "233", "333", "433", "533", "633", "733", "833", "933",
326 "043", "143", "243", "343", "443", "543", "643", "743", "843", "943",
327 "053", "153", "253", "353", "453", "553", "653", "753", "853", "953",
328 "063", "163", "263", "363", "463", "563", "663", "763", "863", "963",
329 "073", "173", "273", "373", "473", "573", "673", "773", "873", "973",
330 "083", "183", "283", "383", "483", "583", "683", "783", "883", "983",
331 "093", "193", "293", "393", "493", "593", "693", "793", "893", "993",
332 "004", "104", "204", "304", "404", "504", "604", "704", "804", "904",
333 "014", "114", "214", "314", "414", "514", "614", "714", "814", "914",
334 "024", "124", "224", "324", "424", "524", "624", "724", "824", "924",
335 "034", "134", "234", "334", "434", "534", "634", "734", "834", "934",
336 "044", "144", "244", "344", "444", "544", "644", "744", "844", "944",
337 "054", "154", "254", "354", "454", "554", "654", "754", "854", "954",
338 "064", "164", "264", "364", "464", "564", "664", "764", "864", "964",
339 "074", "174", "274", "374", "474", "574", "674", "774", "874", "974",
340 "084", "184", "284", "384", "484", "584", "684", "784", "884", "984",
341 "094", "194", "294", "394", "494", "594", "694", "794", "894", "994",
342 "005", "105", "205", "305", "405", "505", "605", "705", "805", "905",
343 "015", "115", "215", "315", "415", "515", "615", "715", "815", "915",
344 "025", "125", "225", "325", "425", "525", "625", "725", "825", "925",
345 "035", "135", "235", "335", "435", "535", "635", "735", "835", "935",
346 "045", "145", "245", "345", "445", "545", "645", "745", "845", "945",
347 "055", "155", "255", "355", "455", "555", "655", "755", "855", "955",
348 "065", "165", "265", "365", "465", "565", "665", "765", "865", "965",
349 "075", "175", "275", "375", "475", "575", "675", "775", "875", "975",
350 "085", "185", "285", "385", "485", "585", "685", "785", "885", "985",
351 "095", "195", "295", "395", "495", "595", "695", "795", "895", "995",
352 "006", "106", "206", "306", "406", "506", "606", "706", "806", "906",
353 "016", "116", "216", "316", "416", "516", "616", "716", "816", "916",
354 "026", "126", "226", "326", "426", "526", "626", "726", "826", "926",
355 "036", "136", "236", "336", "436", "536", "636", "736", "836", "936",
356 "046", "146", "246", "346", "446", "546", "646", "746", "846", "946",
357 "056", "156", "256", "356", "456", "556", "656", "756", "856", "956",
358 "066", "166", "266", "366", "466", "566", "666", "766", "866", "966",
359 "076", "176", "276", "376", "476", "576", "676", "776", "876", "976",
360 "086", "186", "286", "386", "486", "586", "686", "786", "886", "986",
361 "096", "196", "296", "396", "496", "596", "696", "796", "896", "996",
362 "007", "107", "207", "307", "407", "507", "607", "707", "807", "907",
363 "017", "117", "217", "317", "417", "517", "617", "717", "817", "917",
364 "027", "127", "227", "327", "427", "527", "627", "727", "827", "927",
365 "037", "137", "237", "337", "437", "537", "637", "737", "837", "937",
366 "047", "147", "247", "347", "447", "547", "647", "747", "847", "947",
367 "057", "157", "257", "357", "457", "557", "657", "757", "857", "957",
368 "067", "167", "267", "367", "467", "567", "667", "767", "867", "967",
369 "077", "177", "277", "377", "477", "577", "677", "777", "877", "977",
370 "087", "187", "287", "387", "487", "587", "687", "787", "887", "987",
371 "097", "197", "297", "397", "497", "597", "697", "797", "897", "997",
372 "008", "108", "208", "308", "408", "508", "608", "708", "808", "908",
373 "018", "118", "218", "318", "418", "518", "618", "718", "818", "918",
374 "028", "128", "228", "328", "428", "528", "628", "728", "828", "928",
375 "038", "138", "238", "338", "438", "538", "638", "738", "838", "938",
376 "048", "148", "248", "348", "448", "548", "648", "748", "848", "948",
377 "058", "158", "258", "358", "458", "558", "658", "758", "858", "958",
378 "068", "168", "268", "368", "468", "568", "668", "768", "868", "968",
379 "078", "178", "278", "378", "478", "578", "678", "778", "878", "978",
380 "088", "188", "288", "388", "488", "588", "688", "788", "888", "988",
381 "098", "198", "298", "398", "498", "598", "698", "798", "898", "998",
382 "009", "109", "209", "309", "409", "509", "609", "709", "809", "909",
383 "019", "119", "219", "319", "419", "519", "619", "719", "819", "919",
384 "029", "129", "229", "329", "429", "529", "629", "729", "829", "929",
385 "039", "139", "239", "339", "439", "539", "639", "739", "839", "939",
386 "049", "149", "249", "349", "449", "549", "649", "749", "849", "949",
387 "059", "159", "259", "359", "459", "559", "659", "759", "859", "959",
388 "069", "169", "269", "369", "469", "569", "669", "769", "869", "969",
389 "079", "179", "279", "379", "479", "579", "679", "779", "879", "979",
390 "089", "189", "289", "389", "489", "589", "689", "789", "889", "989",
391 "099", "199", "299", "399", "499", "599", "699", "799", "899", "999"
392 };
393
394 /** string table for lower-case hexadecimal values */
395 static char *hex[] = {
396 "", "1", "2", "3", "4", "5", "6", "7",
397 "8", "9", "a", "b", "c", "d", "e", "f",
398 "01", "11", "21", "31", "41", "51", "61", "71",
399 "81", "91", "a1", "b1", "c1", "d1", "e1", "f1",
400 "02", "12", "22", "32", "42", "52", "62", "72",
401 "82", "92", "a2", "b2", "c2", "d2", "e2", "f2",
402 "03", "13", "23", "33", "43", "53", "63", "73",
403 "83", "93", "a3", "b3", "c3", "d3", "e3", "f3",
404 "04", "14", "24", "34", "44", "54", "64", "74",
405 "84", "94", "a4", "b4", "c4", "d4", "e4", "f4",
406 "05", "15", "25", "35", "45", "55", "65", "75",
407 "85", "95", "a5", "b5", "c5", "d5", "e5", "f5",
408 "06", "16", "26", "36", "46", "56", "66", "76",
409 "86", "96", "a6", "b6", "c6", "d6", "e6", "f6",
410 "07", "17", "27", "37", "47", "57", "67", "77",
411 "87", "97", "a7", "b7", "c7", "d7", "e7", "f7",
412 "08", "18", "28", "38", "48", "58", "68", "78",
413 "88", "98", "a8", "b8", "c8", "d8", "e8", "f8",
414 "09", "19", "29", "39", "49", "59", "69", "79",
415 "89", "99", "a9", "b9", "c9", "d9", "e9", "f9",
416 "0a", "1a", "2a", "3a", "4a", "5a", "6a", "7a",
417 "8a", "9a", "aa", "ba", "ca", "da", "ea", "fa",
418 "0b", "1b", "2b", "3b", "4b", "5b", "6b", "7b",
419 "8b", "9b", "ab", "bb", "cb", "db", "eb", "fb",
420 "0c", "1c", "2c", "3c", "4c", "5c", "6c", "7c",
421 "8c", "9c", "ac", "bc", "cc", "dc", "ec", "fc",
422 "0d", "1d", "2d", "3d", "4d", "5d", "6d", "7d",
423 "8d", "9d", "ad", "bd", "cd", "dd", "ed", "fd",
424 "0e", "1e", "2e", "3e", "4e", "5e", "6e", "7e",
425 "8e", "9e", "ae", "be", "ce", "de", "ee", "fe",
426 "0f", "1f", "2f", "3f", "4f", "5f", "6f", "7f",
427 "8f", "9f", "af", "bf", "cf", "df", "ef", "ff",
428 "001", "101", "201", "301", "401", "501", "601", "701",
429 "801", "901", "a01", "b01", "c01", "d01", "e01", "f01",
430 "011", "111", "211", "311", "411", "511", "611", "711",
431 "811", "911", "a11", "b11", "c11", "d11", "e11", "f11",
432 "021", "121", "221", "321", "421", "521", "621", "721",
433 "821", "921", "a21", "b21", "c21", "d21", "e21", "f21",
434 "031", "131", "231", "331", "431", "531", "631", "731",
435 "831", "931", "a31", "b31", "c31", "d31", "e31", "f31",
436 "041", "141", "241", "341", "441", "541", "641", "741",
437 "841", "941", "a41", "b41", "c41", "d41", "e41", "f41",
438 "051", "151", "251", "351", "451", "551", "651", "751",
439 "851", "951", "a51", "b51", "c51", "d51", "e51", "f51",
440 "061", "161", "261", "361", "461", "561", "661", "761",
441 "861", "961", "a61", "b61", "c61", "d61", "e61", "f61",
442 "071", "171", "271", "371", "471", "571", "671", "771",
443 "871", "971", "a71", "b71", "c71", "d71", "e71", "f71",
444 "081", "181", "281", "381", "481", "581", "681", "781",
445 "881", "981", "a81", "b81", "c81", "d81", "e81", "f81",
446 "091", "191", "291", "391", "491", "591", "691", "791",
447 "891", "991", "a91", "b91", "c91", "d91", "e91", "f91",
448 "0a1", "1a1", "2a1", "3a1", "4a1", "5a1", "6a1", "7a1",
449 "8a1", "9a1", "aa1", "ba1", "ca1", "da1", "ea1", "fa1",
450 "0b1", "1b1", "2b1", "3b1", "4b1", "5b1", "6b1", "7b1",
451 "8b1", "9b1", "ab1", "bb1", "cb1", "db1", "eb1", "fb1",
452 "0c1", "1c1", "2c1", "3c1", "4c1", "5c1", "6c1", "7c1",
453 "8c1", "9c1", "ac1", "bc1", "cc1", "dc1", "ec1", "fc1",
454 "0d1", "1d1", "2d1", "3d1", "4d1", "5d1", "6d1", "7d1",
455 "8d1", "9d1", "ad1", "bd1", "cd1", "dd1", "ed1", "fd1",
456 "0e1", "1e1", "2e1", "3e1", "4e1", "5e1", "6e1", "7e1",
457 "8e1", "9e1", "ae1", "be1", "ce1", "de1", "ee1", "fe1",
458 "0f1", "1f1", "2f1", "3f1", "4f1", "5f1", "6f1", "7f1",
459 "8f1", "9f1", "af1", "bf1", "cf1", "df1", "ef1", "ff1",
460 "002", "102", "202", "302", "402", "502", "602", "702",
461 "802", "902", "a02", "b02", "c02", "d02", "e02", "f02",
462 "012", "112", "212", "312", "412", "512", "612", "712",
463 "812", "912", "a12", "b12", "c12", "d12", "e12", "f12",
464 "022", "122", "222", "322", "422", "522", "622", "722",
465 "822", "922", "a22", "b22", "c22", "d22", "e22", "f22",
466 "032", "132", "232", "332", "432", "532", "632", "732",
467 "832", "932", "a32", "b32", "c32", "d32", "e32", "f32",
468 "042", "142", "242", "342", "442", "542", "642", "742",
469 "842", "942", "a42", "b42", "c42", "d42", "e42", "f42",
470 "052", "152", "252", "352", "452", "552", "652", "752",
471 "852", "952", "a52", "b52", "c52", "d52", "e52", "f52",
472 "062", "162", "262", "362", "462", "562", "662", "762",
473 "862", "962", "a62", "b62", "c62", "d62", "e62", "f62",
474 "072", "172", "272", "372", "472", "572", "672", "772",
475 "872", "972", "a72", "b72", "c72", "d72", "e72", "f72",
476 "082", "182", "282", "382", "482", "582", "682", "782",
477 "882", "982", "a82", "b82", "c82", "d82", "e82", "f82",
478 "092", "192", "292", "392", "492", "592", "692", "792",
479 "892", "992", "a92", "b92", "c92", "d92", "e92", "f92",
480 "0a2", "1a2", "2a2", "3a2", "4a2", "5a2", "6a2", "7a2",
481 "8a2", "9a2", "aa2", "ba2", "ca2", "da2", "ea2", "fa2",
482 "0b2", "1b2", "2b2", "3b2", "4b2", "5b2", "6b2", "7b2",
483 "8b2", "9b2", "ab2", "bb2", "cb2", "db2", "eb2", "fb2",
484 "0c2", "1c2", "2c2", "3c2", "4c2", "5c2", "6c2", "7c2",
485 "8c2", "9c2", "ac2", "bc2", "cc2", "dc2", "ec2", "fc2",
486 "0d2", "1d2", "2d2", "3d2", "4d2", "5d2", "6d2", "7d2",
487 "8d2", "9d2", "ad2", "bd2", "cd2", "dd2", "ed2", "fd2",
488 "0e2", "1e2", "2e2", "3e2", "4e2", "5e2", "6e2", "7e2",
489 "8e2", "9e2", "ae2", "be2", "ce2", "de2", "ee2", "fe2",
490 "0f2", "1f2", "2f2", "3f2", "4f2", "5f2", "6f2", "7f2",
491 "8f2", "9f2", "af2", "bf2", "cf2", "df2", "ef2", "ff2",
492 "003", "103", "203", "303", "403", "503", "603", "703",
493 "803", "903", "a03", "b03", "c03", "d03", "e03", "f03",
494 "013", "113", "213", "313", "413", "513", "613", "713",
495 "813", "913", "a13", "b13", "c13", "d13", "e13", "f13",
496 "023", "123", "223", "323", "423", "523", "623", "723",
497 "823", "923", "a23", "b23", "c23", "d23", "e23", "f23",
498 "033", "133", "233", "333", "433", "533", "633", "733",
499 "833", "933", "a33", "b33", "c33", "d33", "e33", "f33",
500 "043", "143", "243", "343", "443", "543", "643", "743",
501 "843", "943", "a43", "b43", "c43", "d43", "e43", "f43",
502 "053", "153", "253", "353", "453", "553", "653", "753",
503 "853", "953", "a53", "b53", "c53", "d53", "e53", "f53",
504 "063", "163", "263", "363", "463", "563", "663", "763",
505 "863", "963", "a63", "b63", "c63", "d63", "e63", "f63",
506 "073", "173", "273", "373", "473", "573", "673", "773",
507 "873", "973", "a73", "b73", "c73", "d73", "e73", "f73",
508 "083", "183", "283", "383", "483", "583", "683", "783",
509 "883", "983", "a83", "b83", "c83", "d83", "e83", "f83",
510 "093", "193", "293", "393", "493", "593", "693", "793",
511 "893", "993", "a93", "b93", "c93", "d93", "e93", "f93",
512 "0a3", "1a3", "2a3", "3a3", "4a3", "5a3", "6a3", "7a3",
513 "8a3", "9a3", "aa3", "ba3", "ca3", "da3", "ea3", "fa3",
514 "0b3", "1b3", "2b3", "3b3", "4b3", "5b3", "6b3", "7b3",
515 "8b3", "9b3", "ab3", "bb3", "cb3", "db3", "eb3", "fb3",
516 "0c3", "1c3", "2c3", "3c3", "4c3", "5c3", "6c3", "7c3",
517 "8c3", "9c3", "ac3", "bc3", "cc3", "dc3", "ec3", "fc3",
518 "0d3", "1d3", "2d3", "3d3", "4d3", "5d3", "6d3", "7d3",
519 "8d3", "9d3", "ad3", "bd3", "cd3", "dd3", "ed3", "fd3",
520 "0e3", "1e3", "2e3", "3e3", "4e3", "5e3", "6e3", "7e3",
521 "8e3", "9e3", "ae3", "be3", "ce3", "de3", "ee3", "fe3",
522 "0f3", "1f3", "2f3", "3f3", "4f3", "5f3", "6f3", "7f3",
523 "8f3", "9f3", "af3", "bf3", "cf3", "df3", "ef3", "ff3",
524 "004", "104", "204", "304", "404", "504", "604", "704",
525 "804", "904", "a04", "b04", "c04", "d04", "e04", "f04",
526 "014", "114", "214", "314", "414", "514", "614", "714",
527 "814", "914", "a14", "b14", "c14", "d14", "e14", "f14",
528 "024", "124", "224", "324", "424", "524", "624", "724",
529 "824", "924", "a24", "b24", "c24", "d24", "e24", "f24",
530 "034", "134", "234", "334", "434", "534", "634", "734",
531 "834", "934", "a34", "b34", "c34", "d34", "e34", "f34",
532 "044", "144", "244", "344", "444", "544", "644", "744",
533 "844", "944", "a44", "b44", "c44", "d44", "e44", "f44",
534 "054", "154", "254", "354", "454", "554", "654", "754",
535 "854", "954", "a54", "b54", "c54", "d54", "e54", "f54",
536 "064", "164", "264", "364", "464", "564", "664", "764",
537 "864", "964", "a64", "b64", "c64", "d64", "e64", "f64",
538 "074", "174", "274", "374", "474", "574", "674", "774",
539 "874", "974", "a74", "b74", "c74", "d74", "e74", "f74",
540 "084", "184", "284", "384", "484", "584", "684", "784",
541 "884", "984", "a84", "b84", "c84", "d84", "e84", "f84",
542 "094", "194", "294", "394", "494", "594", "694", "794",
543 "894", "994", "a94", "b94", "c94", "d94", "e94", "f94",
544 "0a4", "1a4", "2a4", "3a4", "4a4", "5a4", "6a4", "7a4",
545 "8a4", "9a4", "aa4", "ba4", "ca4", "da4", "ea4", "fa4",
546 "0b4", "1b4", "2b4", "3b4", "4b4", "5b4", "6b4", "7b4",
547 "8b4", "9b4", "ab4", "bb4", "cb4", "db4", "eb4", "fb4",
548 "0c4", "1c4", "2c4", "3c4", "4c4", "5c4", "6c4", "7c4",
549 "8c4", "9c4", "ac4", "bc4", "cc4", "dc4", "ec4", "fc4",
550 "0d4", "1d4", "2d4", "3d4", "4d4", "5d4", "6d4", "7d4",
551 "8d4", "9d4", "ad4", "bd4", "cd4", "dd4", "ed4", "fd4",
552 "0e4", "1e4", "2e4", "3e4", "4e4", "5e4", "6e4", "7e4",
553 "8e4", "9e4", "ae4", "be4", "ce4", "de4", "ee4", "fe4",
554 "0f4", "1f4", "2f4", "3f4", "4f4", "5f4", "6f4", "7f4",
555 "8f4", "9f4", "af4", "bf4", "cf4", "df4", "ef4", "ff4",
556 "005", "105", "205", "305", "405", "505", "605", "705",
557 "805", "905", "a05", "b05", "c05", "d05", "e05", "f05",
558 "015", "115", "215", "315", "415", "515", "615", "715",
559 "815", "915", "a15", "b15", "c15", "d15", "e15", "f15",
560 "025", "125", "225", "325", "425", "525", "625", "725",
561 "825", "925", "a25", "b25", "c25", "d25", "e25", "f25",
562 "035", "135", "235", "335", "435", "535", "635", "735",
563 "835", "935", "a35", "b35", "c35", "d35", "e35", "f35",
564 "045", "145", "245", "345", "445", "545", "645", "745",
565 "845", "945", "a45", "b45", "c45", "d45", "e45", "f45",
566 "055", "155", "255", "355", "455", "555", "655", "755",
567 "855", "955", "a55", "b55", "c55", "d55", "e55", "f55",
568 "065", "165", "265", "365", "465", "565", "665", "765",
569 "865", "965", "a65", "b65", "c65", "d65", "e65", "f65",
570 "075", "175", "275", "375", "475", "575", "675", "775",
571 "875", "975", "a75", "b75", "c75", "d75", "e75", "f75",
572 "085", "185", "285", "385", "485", "585", "685", "785",
573 "885", "985", "a85", "b85", "c85", "d85", "e85", "f85",
574 "095", "195", "295", "395", "495", "595", "695", "795",
575 "895", "995", "a95", "b95", "c95", "d95", "e95", "f95",
576 "0a5", "1a5", "2a5", "3a5", "4a5", "5a5", "6a5", "7a5",
577 "8a5", "9a5", "aa5", "ba5", "ca5", "da5", "ea5", "fa5",
578 "0b5", "1b5", "2b5", "3b5", "4b5", "5b5", "6b5", "7b5",
579 "8b5", "9b5", "ab5", "bb5", "cb5", "db5", "eb5", "fb5",
580 "0c5", "1c5", "2c5", "3c5", "4c5", "5c5", "6c5", "7c5",
581 "8c5", "9c5", "ac5", "bc5", "cc5", "dc5", "ec5", "fc5",
582 "0d5", "1d5", "2d5", "3d5", "4d5", "5d5", "6d5", "7d5",
583 "8d5", "9d5", "ad5", "bd5", "cd5", "dd5", "ed5", "fd5",
584 "0e5", "1e5", "2e5", "3e5", "4e5", "5e5", "6e5", "7e5",
585 "8e5", "9e5", "ae5", "be5", "ce5", "de5", "ee5", "fe5",
586 "0f5", "1f5", "2f5", "3f5", "4f5", "5f5", "6f5", "7f5",
587 "8f5", "9f5", "af5", "bf5", "cf5", "df5", "ef5", "ff5",
588 "006", "106", "206", "306", "406", "506", "606", "706",
589 "806", "906", "a06", "b06", "c06", "d06", "e06", "f06",
590 "016", "116", "216", "316", "416", "516", "616", "716",
591 "816", "916", "a16", "b16", "c16", "d16", "e16", "f16",
592 "026", "126", "226", "326", "426", "526", "626", "726",
593 "826", "926", "a26", "b26", "c26", "d26", "e26", "f26",
594 "036", "136", "236", "336", "436", "536", "636", "736",
595 "836", "936", "a36", "b36", "c36", "d36", "e36", "f36",
596 "046", "146", "246", "346", "446", "546", "646", "746",
597 "846", "946", "a46", "b46", "c46", "d46", "e46", "f46",
598 "056", "156", "256", "356", "456", "556", "656", "756",
599 "856", "956", "a56", "b56", "c56", "d56", "e56", "f56",
600 "066", "166", "266", "366", "466", "566", "666", "766",
601 "866", "966", "a66", "b66", "c66", "d66", "e66", "f66",
602 "076", "176", "276", "376", "476", "576", "676", "776",
603 "876", "976", "a76", "b76", "c76", "d76", "e76", "f76",
604 "086", "186", "286", "386", "486", "586", "686", "786",
605 "886", "986", "a86", "b86", "c86", "d86", "e86", "f86",
606 "096", "196", "296", "396", "496", "596", "696", "796",
607 "896", "996", "a96", "b96", "c96", "d96", "e96", "f96",
608 "0a6", "1a6", "2a6", "3a6", "4a6", "5a6", "6a6", "7a6",
609 "8a6", "9a6", "aa6", "ba6", "ca6", "da6", "ea6", "fa6",
610 "0b6", "1b6", "2b6", "3b6", "4b6", "5b6", "6b6", "7b6",
611 "8b6", "9b6", "ab6", "bb6", "cb6", "db6", "eb6", "fb6",
612 "0c6", "1c6", "2c6", "3c6", "4c6", "5c6", "6c6", "7c6",
613 "8c6", "9c6", "ac6", "bc6", "cc6", "dc6", "ec6", "fc6",
614 "0d6", "1d6", "2d6", "3d6", "4d6", "5d6", "6d6", "7d6",
615 "8d6", "9d6", "ad6", "bd6", "cd6", "dd6", "ed6", "fd6",
616 "0e6", "1e6", "2e6", "3e6", "4e6", "5e6", "6e6", "7e6",
617 "8e6", "9e6", "ae6", "be6", "ce6", "de6", "ee6", "fe6",
618 "0f6", "1f6", "2f6", "3f6", "4f6", "5f6", "6f6", "7f6",
619 "8f6", "9f6", "af6", "bf6", "cf6", "df6", "ef6", "ff6",
620 "007", "107", "207", "307", "407", "507", "607", "707",
621 "807", "907", "a07", "b07", "c07", "d07", "e07", "f07",
622 "017", "117", "217", "317", "417", "517", "617", "717",
623 "817", "917", "a17", "b17", "c17", "d17", "e17", "f17",
624 "027", "127", "227", "327", "427", "527", "627", "727",
625 "827", "927", "a27", "b27", "c27", "d27", "e27", "f27",
626 "037", "137", "237", "337", "437", "537", "637", "737",
627 "837", "937", "a37", "b37", "c37", "d37", "e37", "f37",
628 "047", "147", "247", "347", "447", "547", "647", "747",
629 "847", "947", "a47", "b47", "c47", "d47", "e47", "f47",
630 "057", "157", "257", "357", "457", "557", "657", "757",
631 "857", "957", "a57", "b57", "c57", "d57", "e57", "f57",
632 "067", "167", "267", "367", "467", "567", "667", "767",
633 "867", "967", "a67", "b67", "c67", "d67", "e67", "f67",
634 "077", "177", "277", "377", "477", "577", "677", "777",
635 "877", "977", "a77", "b77", "c77", "d77", "e77", "f77",
636 "087", "187", "287", "387", "487", "587", "687", "787",
637 "887", "987", "a87", "b87", "c87", "d87", "e87", "f87",
638 "097", "197", "297", "397", "497", "597", "697", "797",
639 "897", "997", "a97", "b97", "c97", "d97", "e97", "f97",
640 "0a7", "1a7", "2a7", "3a7", "4a7", "5a7", "6a7", "7a7",
641 "8a7", "9a7", "aa7", "ba7", "ca7", "da7", "ea7", "fa7",
642 "0b7", "1b7", "2b7", "3b7", "4b7", "5b7", "6b7", "7b7",
643 "8b7", "9b7", "ab7", "bb7", "cb7", "db7", "eb7", "fb7",
644 "0c7", "1c7", "2c7", "3c7", "4c7", "5c7", "6c7", "7c7",
645 "8c7", "9c7", "ac7", "bc7", "cc7", "dc7", "ec7", "fc7",
646 "0d7", "1d7", "2d7", "3d7", "4d7", "5d7", "6d7", "7d7",
647 "8d7", "9d7", "ad7", "bd7", "cd7", "dd7", "ed7", "fd7",
648 "0e7", "1e7", "2e7", "3e7", "4e7", "5e7", "6e7", "7e7",
649 "8e7", "9e7", "ae7", "be7", "ce7", "de7", "ee7", "fe7",
650 "0f7", "1f7", "2f7", "3f7", "4f7", "5f7", "6f7", "7f7",
651 "8f7", "9f7", "af7", "bf7", "cf7", "df7", "ef7", "ff7",
652 "008", "108", "208", "308", "408", "508", "608", "708",
653 "808", "908", "a08", "b08", "c08", "d08", "e08", "f08",
654 "018", "118", "218", "318", "418", "518", "618", "718",
655 "818", "918", "a18", "b18", "c18", "d18", "e18", "f18",
656 "028", "128", "228", "328", "428", "528", "628", "728",
657 "828", "928", "a28", "b28", "c28", "d28", "e28", "f28",
658 "038", "138", "238", "338", "438", "538", "638", "738",
659 "838", "938", "a38", "b38", "c38", "d38", "e38", "f38",
660 "048", "148", "248", "348", "448", "548", "648", "748",
661 "848", "948", "a48", "b48", "c48", "d48", "e48", "f48",
662 "058", "158", "258", "358", "458", "558", "658", "758",
663 "858", "958", "a58", "b58", "c58", "d58", "e58", "f58",
664 "068", "168", "268", "368", "468", "568", "668", "768",
665 "868", "968", "a68", "b68", "c68", "d68", "e68", "f68",
666 "078", "178", "278", "378", "478", "578", "678", "778",
667 "878", "978", "a78", "b78", "c78", "d78", "e78", "f78",
668 "088", "188", "288", "388", "488", "588", "688", "788",
669 "888", "988", "a88", "b88", "c88", "d88", "e88", "f88",
670 "098", "198", "298", "398", "498", "598", "698", "798",
671 "898", "998", "a98", "b98", "c98", "d98", "e98", "f98",
672 "0a8", "1a8", "2a8", "3a8", "4a8", "5a8", "6a8", "7a8",
673 "8a8", "9a8", "aa8", "ba8", "ca8", "da8", "ea8", "fa8",
674 "0b8", "1b8", "2b8", "3b8", "4b8", "5b8", "6b8", "7b8",
675 "8b8", "9b8", "ab8", "bb8", "cb8", "db8", "eb8", "fb8",
676 "0c8", "1c8", "2c8", "3c8", "4c8", "5c8", "6c8", "7c8",
677 "8c8", "9c8", "ac8", "bc8", "cc8", "dc8", "ec8", "fc8",
678 "0d8", "1d8", "2d8", "3d8", "4d8", "5d8", "6d8", "7d8",
679 "8d8", "9d8", "ad8", "bd8", "cd8", "dd8", "ed8", "fd8",
680 "0e8", "1e8", "2e8", "3e8", "4e8", "5e8", "6e8", "7e8",
681 "8e8", "9e8", "ae8", "be8", "ce8", "de8", "ee8", "fe8",
682 "0f8", "1f8", "2f8", "3f8", "4f8", "5f8", "6f8", "7f8",
683 "8f8", "9f8", "af8", "bf8", "cf8", "df8", "ef8", "ff8",
684 "009", "109", "209", "309", "409", "509", "609", "709",
685 "809", "909", "a09", "b09", "c09", "d09", "e09", "f09",
686 "019", "119", "219", "319", "419", "519", "619", "719",
687 "819", "919", "a19", "b19", "c19", "d19", "e19", "f19",
688 "029", "129", "229", "329", "429", "529", "629", "729",
689 "829", "929", "a29", "b29", "c29", "d29", "e29", "f29",
690 "039", "139", "239", "339", "439", "539", "639", "739",
691 "839", "939", "a39", "b39", "c39", "d39", "e39", "f39",
692 "049", "149", "249", "349", "449", "549", "649", "749",
693 "849", "949", "a49", "b49", "c49", "d49", "e49", "f49",
694 "059", "159", "259", "359", "459", "559", "659", "759",
695 "859", "959", "a59", "b59", "c59", "d59", "e59", "f59",
696 "069", "169", "269", "369", "469", "569", "669", "769",
697 "869", "969", "a69", "b69", "c69", "d69", "e69", "f69",
698 "079", "179", "279", "379", "479", "579", "679", "779",
699 "879", "979", "a79", "b79", "c79", "d79", "e79", "f79",
700 "089", "189", "289", "389", "489", "589", "689", "789",
701 "889", "989", "a89", "b89", "c89", "d89", "e89", "f89",
702 "099", "199", "299", "399", "499", "599", "699", "799",
703 "899", "999", "a99", "b99", "c99", "d99", "e99", "f99",
704 "0a9", "1a9", "2a9", "3a9", "4a9", "5a9", "6a9", "7a9",
705 "8a9", "9a9", "aa9", "ba9", "ca9", "da9", "ea9", "fa9",
706 "0b9", "1b9", "2b9", "3b9", "4b9", "5b9", "6b9", "7b9",
707 "8b9", "9b9", "ab9", "bb9", "cb9", "db9", "eb9", "fb9",
708 "0c9", "1c9", "2c9", "3c9", "4c9", "5c9", "6c9", "7c9",
709 "8c9", "9c9", "ac9", "bc9", "cc9", "dc9", "ec9", "fc9",
710 "0d9", "1d9", "2d9", "3d9", "4d9", "5d9", "6d9", "7d9",
711 "8d9", "9d9", "ad9", "bd9", "cd9", "dd9", "ed9", "fd9",
712 "0e9", "1e9", "2e9", "3e9", "4e9", "5e9", "6e9", "7e9",
713 "8e9", "9e9", "ae9", "be9", "ce9", "de9", "ee9", "fe9",
714 "0f9", "1f9", "2f9", "3f9", "4f9", "5f9", "6f9", "7f9",
715 "8f9", "9f9", "af9", "bf9", "cf9", "df9", "ef9", "ff9",
716 "00a", "10a", "20a", "30a", "40a", "50a", "60a", "70a",
717 "80a", "90a", "a0a", "b0a", "c0a", "d0a", "e0a", "f0a",
718 "01a", "11a", "21a", "31a", "41a", "51a", "61a", "71a",
719 "81a", "91a", "a1a", "b1a", "c1a", "d1a", "e1a", "f1a",
720 "02a", "12a", "22a", "32a", "42a", "52a", "62a", "72a",
721 "82a", "92a", "a2a", "b2a", "c2a", "d2a", "e2a", "f2a",
722 "03a", "13a", "23a", "33a", "43a", "53a", "63a", "73a",
723 "83a", "93a", "a3a", "b3a", "c3a", "d3a", "e3a", "f3a",
724 "04a", "14a", "24a", "34a", "44a", "54a", "64a", "74a",
725 "84a", "94a", "a4a", "b4a", "c4a", "d4a", "e4a", "f4a",
726 "05a", "15a", "25a", "35a", "45a", "55a", "65a", "75a",
727 "85a", "95a", "a5a", "b5a", "c5a", "d5a", "e5a", "f5a",
728 "06a", "16a", "26a", "36a", "46a", "56a", "66a", "76a",
729 "86a", "96a", "a6a", "b6a", "c6a", "d6a", "e6a", "f6a",
730 "07a", "17a", "27a", "37a", "47a", "57a", "67a", "77a",
731 "87a", "97a", "a7a", "b7a", "c7a", "d7a", "e7a", "f7a",
732 "08a", "18a", "28a", "38a", "48a", "58a", "68a", "78a",
733 "88a", "98a", "a8a", "b8a", "c8a", "d8a", "e8a", "f8a",
734 "09a", "19a", "29a", "39a", "49a", "59a", "69a", "79a",
735 "89a", "99a", "a9a", "b9a", "c9a", "d9a", "e9a", "f9a",
736 "0aa", "1aa", "2aa", "3aa", "4aa", "5aa", "6aa", "7aa",
737 "8aa", "9aa", "aaa", "baa", "caa", "daa", "eaa", "faa",
738 "0ba", "1ba", "2ba", "3ba", "4ba", "5ba", "6ba", "7ba",
739 "8ba", "9ba", "aba", "bba", "cba", "dba", "eba", "fba",
740 "0ca", "1ca", "2ca", "3ca", "4ca", "5ca", "6ca", "7ca",
741 "8ca", "9ca", "aca", "bca", "cca", "dca", "eca", "fca",
742 "0da", "1da", "2da", "3da", "4da", "5da", "6da", "7da",
743 "8da", "9da", "ada", "bda", "cda", "dda", "eda", "fda",
744 "0ea", "1ea", "2ea", "3ea", "4ea", "5ea", "6ea", "7ea",
745 "8ea", "9ea", "aea", "bea", "cea", "dea", "eea", "fea",
746 "0fa", "1fa", "2fa", "3fa", "4fa", "5fa", "6fa", "7fa",
747 "8fa", "9fa", "afa", "bfa", "cfa", "dfa", "efa", "ffa",
748 "00b", "10b", "20b", "30b", "40b", "50b", "60b", "70b",
749 "80b", "90b", "a0b", "b0b", "c0b", "d0b", "e0b", "f0b",
750 "01b", "11b", "21b", "31b", "41b", "51b", "61b", "71b",
751 "81b", "91b", "a1b", "b1b", "c1b", "d1b", "e1b", "f1b",
752 "02b", "12b", "22b", "32b", "42b", "52b", "62b", "72b",
753 "82b", "92b", "a2b", "b2b", "c2b", "d2b", "e2b", "f2b",
754 "03b", "13b", "23b", "33b", "43b", "53b", "63b", "73b",
755 "83b", "93b", "a3b", "b3b", "c3b", "d3b", "e3b", "f3b",
756 "04b", "14b", "24b", "34b", "44b", "54b", "64b", "74b",
757 "84b", "94b", "a4b", "b4b", "c4b", "d4b", "e4b", "f4b",
758 "05b", "15b", "25b", "35b", "45b", "55b", "65b", "75b",
759 "85b", "95b", "a5b", "b5b", "c5b", "d5b", "e5b", "f5b",
760 "06b", "16b", "26b", "36b", "46b", "56b", "66b", "76b",
761 "86b", "96b", "a6b", "b6b", "c6b", "d6b", "e6b", "f6b",
762 "07b", "17b", "27b", "37b", "47b", "57b", "67b", "77b",
763 "87b", "97b", "a7b", "b7b", "c7b", "d7b", "e7b", "f7b",
764 "08b", "18b", "28b", "38b", "48b", "58b", "68b", "78b",
765 "88b", "98b", "a8b", "b8b", "c8b", "d8b", "e8b", "f8b",
766 "09b", "19b", "29b", "39b", "49b", "59b", "69b", "79b",
767 "89b", "99b", "a9b", "b9b", "c9b", "d9b", "e9b", "f9b",
768 "0ab", "1ab", "2ab", "3ab", "4ab", "5ab", "6ab", "7ab",
769 "8ab", "9ab", "aab", "bab", "cab", "dab", "eab", "fab",
770 "0bb", "1bb", "2bb", "3bb", "4bb", "5bb", "6bb", "7bb",
771 "8bb", "9bb", "abb", "bbb", "cbb", "dbb", "ebb", "fbb",
772 "0cb", "1cb", "2cb", "3cb", "4cb", "5cb", "6cb", "7cb",
773 "8cb", "9cb", "acb", "bcb", "ccb", "dcb", "ecb", "fcb",
774 "0db", "1db", "2db", "3db", "4db", "5db", "6db", "7db",
775 "8db", "9db", "adb", "bdb", "cdb", "ddb", "edb", "fdb",
776 "0eb", "1eb", "2eb", "3eb", "4eb", "5eb", "6eb", "7eb",
777 "8eb", "9eb", "aeb", "beb", "ceb", "deb", "eeb", "feb",
778 "0fb", "1fb", "2fb", "3fb", "4fb", "5fb", "6fb", "7fb",
779 "8fb", "9fb", "afb", "bfb", "cfb", "dfb", "efb", "ffb",
780 "00c", "10c", "20c", "30c", "40c", "50c", "60c", "70c",
781 "80c", "90c", "a0c", "b0c", "c0c", "d0c", "e0c", "f0c",
782 "01c", "11c", "21c", "31c", "41c", "51c", "61c", "71c",
783 "81c", "91c", "a1c", "b1c", "c1c", "d1c", "e1c", "f1c",
784 "02c", "12c", "22c", "32c", "42c", "52c", "62c", "72c",
785 "82c", "92c", "a2c", "b2c", "c2c", "d2c", "e2c", "f2c",
786 "03c", "13c", "23c", "33c", "43c", "53c", "63c", "73c",
787 "83c", "93c", "a3c", "b3c", "c3c", "d3c", "e3c", "f3c",
788 "04c", "14c", "24c", "34c", "44c", "54c", "64c", "74c",
789 "84c", "94c", "a4c", "b4c", "c4c", "d4c", "e4c", "f4c",
790 "05c", "15c", "25c", "35c", "45c", "55c", "65c", "75c",
791 "85c", "95c", "a5c", "b5c", "c5c", "d5c", "e5c", "f5c",
792 "06c", "16c", "26c", "36c", "46c", "56c", "66c", "76c",
793 "86c", "96c", "a6c", "b6c", "c6c", "d6c", "e6c", "f6c",
794 "07c", "17c", "27c", "37c", "47c", "57c", "67c", "77c",
795 "87c", "97c", "a7c", "b7c", "c7c", "d7c", "e7c", "f7c",
796 "08c", "18c", "28c", "38c", "48c", "58c", "68c", "78c",
797 "88c", "98c", "a8c", "b8c", "c8c", "d8c", "e8c", "f8c",
798 "09c", "19c", "29c", "39c", "49c", "59c", "69c", "79c",
799 "89c", "99c", "a9c", "b9c", "c9c", "d9c", "e9c", "f9c",
800 "0ac", "1ac", "2ac", "3ac", "4ac", "5ac", "6ac", "7ac",
801 "8ac", "9ac", "aac", "bac", "cac", "dac", "eac", "fac",
802 "0bc", "1bc", "2bc", "3bc", "4bc", "5bc", "6bc", "7bc",
803 "8bc", "9bc", "abc", "bbc", "cbc", "dbc", "ebc", "fbc",
804 "0cc", "1cc", "2cc", "3cc", "4cc", "5cc", "6cc", "7cc",
805 "8cc", "9cc", "acc", "bcc", "ccc", "dcc", "ecc", "fcc",
806 "0dc", "1dc", "2dc", "3dc", "4dc", "5dc", "6dc", "7dc",
807 "8dc", "9dc", "adc", "bdc", "cdc", "ddc", "edc", "fdc",
808 "0ec", "1ec", "2ec", "3ec", "4ec", "5ec", "6ec", "7ec",
809 "8ec", "9ec", "aec", "bec", "cec", "dec", "eec", "fec",
810 "0fc", "1fc", "2fc", "3fc", "4fc", "5fc", "6fc", "7fc",
811 "8fc", "9fc", "afc", "bfc", "cfc", "dfc", "efc", "ffc",
812 "00d", "10d", "20d", "30d", "40d", "50d", "60d", "70d",
813 "80d", "90d", "a0d", "b0d", "c0d", "d0d", "e0d", "f0d",
814 "01d", "11d", "21d", "31d", "41d", "51d", "61d", "71d",
815 "81d", "91d", "a1d", "b1d", "c1d", "d1d", "e1d", "f1d",
816 "02d", "12d", "22d", "32d", "42d", "52d", "62d", "72d",
817 "82d", "92d", "a2d", "b2d", "c2d", "d2d", "e2d", "f2d",
818 "03d", "13d", "23d", "33d", "43d", "53d", "63d", "73d",
819 "83d", "93d", "a3d", "b3d", "c3d", "d3d", "e3d", "f3d",
820 "04d", "14d", "24d", "34d", "44d", "54d", "64d", "74d",
821 "84d", "94d", "a4d", "b4d", "c4d", "d4d", "e4d", "f4d",
822 "05d", "15d", "25d", "35d", "45d", "55d", "65d", "75d",
823 "85d", "95d", "a5d", "b5d", "c5d", "d5d", "e5d", "f5d",
824 "06d", "16d", "26d", "36d", "46d", "56d", "66d", "76d",
825 "86d", "96d", "a6d", "b6d", "c6d", "d6d", "e6d", "f6d",
826 "07d", "17d", "27d", "37d", "47d", "57d", "67d", "77d",
827 "87d", "97d", "a7d", "b7d", "c7d", "d7d", "e7d", "f7d",
828 "08d", "18d", "28d", "38d", "48d", "58d", "68d", "78d",
829 "88d", "98d", "a8d", "b8d", "c8d", "d8d", "e8d", "f8d",
830 "09d", "19d", "29d", "39d", "49d", "59d", "69d", "79d",
831 "89d", "99d", "a9d", "b9d", "c9d", "d9d", "e9d", "f9d",
832 "0ad", "1ad", "2ad", "3ad", "4ad", "5ad", "6ad", "7ad",
833 "8ad", "9ad", "aad", "bad", "cad", "dad", "ead", "fad",
834 "0bd", "1bd", "2bd", "3bd", "4bd", "5bd", "6bd", "7bd",
835 "8bd", "9bd", "abd", "bbd", "cbd", "dbd", "ebd", "fbd",
836 "0cd", "1cd", "2cd", "3cd", "4cd", "5cd", "6cd", "7cd",
837 "8cd", "9cd", "acd", "bcd", "ccd", "dcd", "ecd", "fcd",
838 "0dd", "1dd", "2dd", "3dd", "4dd", "5dd", "6dd", "7dd",
839 "8dd", "9dd", "add", "bdd", "cdd", "ddd", "edd", "fdd",
840 "0ed", "1ed", "2ed", "3ed", "4ed", "5ed", "6ed", "7ed",
841 "8ed", "9ed", "aed", "bed", "ced", "ded", "eed", "fed",
842 "0fd", "1fd", "2fd", "3fd", "4fd", "5fd", "6fd", "7fd",
843 "8fd", "9fd", "afd", "bfd", "cfd", "dfd", "efd", "ffd",
844 "00e", "10e", "20e", "30e", "40e", "50e", "60e", "70e",
845 "80e", "90e", "a0e", "b0e", "c0e", "d0e", "e0e", "f0e",
846 "01e", "11e", "21e", "31e", "41e", "51e", "61e", "71e",
847 "81e", "91e", "a1e", "b1e", "c1e", "d1e", "e1e", "f1e",
848 "02e", "12e", "22e", "32e", "42e", "52e", "62e", "72e",
849 "82e", "92e", "a2e", "b2e", "c2e", "d2e", "e2e", "f2e",
850 "03e", "13e", "23e", "33e", "43e", "53e", "63e", "73e",
851 "83e", "93e", "a3e", "b3e", "c3e", "d3e", "e3e", "f3e",
852 "04e", "14e", "24e", "34e", "44e", "54e", "64e", "74e",
853 "84e", "94e", "a4e", "b4e", "c4e", "d4e", "e4e", "f4e",
854 "05e", "15e", "25e", "35e", "45e", "55e", "65e", "75e",
855 "85e", "95e", "a5e", "b5e", "c5e", "d5e", "e5e", "f5e",
856 "06e", "16e", "26e", "36e", "46e", "56e", "66e", "76e",
857 "86e", "96e", "a6e", "b6e", "c6e", "d6e", "e6e", "f6e",
858 "07e", "17e", "27e", "37e", "47e", "57e", "67e", "77e",
859 "87e", "97e", "a7e", "b7e", "c7e", "d7e", "e7e", "f7e",
860 "08e", "18e", "28e", "38e", "48e", "58e", "68e", "78e",
861 "88e", "98e", "a8e", "b8e", "c8e", "d8e", "e8e", "f8e",
862 "09e", "19e", "29e", "39e", "49e", "59e", "69e", "79e",
863 "89e", "99e", "a9e", "b9e", "c9e", "d9e", "e9e", "f9e",
864 "0ae", "1ae", "2ae", "3ae", "4ae", "5ae", "6ae", "7ae",
865 "8ae", "9ae", "aae", "bae", "cae", "dae", "eae", "fae",
866 "0be", "1be", "2be", "3be", "4be", "5be", "6be", "7be",
867 "8be", "9be", "abe", "bbe", "cbe", "dbe", "ebe", "fbe",
868 "0ce", "1ce", "2ce", "3ce", "4ce", "5ce", "6ce", "7ce",
869 "8ce", "9ce", "ace", "bce", "cce", "dce", "ece", "fce",
870 "0de", "1de", "2de", "3de", "4de", "5de", "6de", "7de",
871 "8de", "9de", "ade", "bde", "cde", "dde", "ede", "fde",
872 "0ee", "1ee", "2ee", "3ee", "4ee", "5ee", "6ee", "7ee",
873 "8ee", "9ee", "aee", "bee", "cee", "dee", "eee", "fee",
874 "0fe", "1fe", "2fe", "3fe", "4fe", "5fe", "6fe", "7fe",
875 "8fe", "9fe", "afe", "bfe", "cfe", "dfe", "efe", "ffe",
876 "00f", "10f", "20f", "30f", "40f", "50f", "60f", "70f",
877 "80f", "90f", "a0f", "b0f", "c0f", "d0f", "e0f", "f0f",
878 "01f", "11f", "21f", "31f", "41f", "51f", "61f", "71f",
879 "81f", "91f", "a1f", "b1f", "c1f", "d1f", "e1f", "f1f",
880 "02f", "12f", "22f", "32f", "42f", "52f", "62f", "72f",
881 "82f", "92f", "a2f", "b2f", "c2f", "d2f", "e2f", "f2f",
882 "03f", "13f", "23f", "33f", "43f", "53f", "63f", "73f",
883 "83f", "93f", "a3f", "b3f", "c3f", "d3f", "e3f", "f3f",
884 "04f", "14f", "24f", "34f", "44f", "54f", "64f", "74f",
885 "84f", "94f", "a4f", "b4f", "c4f", "d4f", "e4f", "f4f",
886 "05f", "15f", "25f", "35f", "45f", "55f", "65f", "75f",
887 "85f", "95f", "a5f", "b5f", "c5f", "d5f", "e5f", "f5f",
888 "06f", "16f", "26f", "36f", "46f", "56f", "66f", "76f",
889 "86f", "96f", "a6f", "b6f", "c6f", "d6f", "e6f", "f6f",
890 "07f", "17f", "27f", "37f", "47f", "57f", "67f", "77f",
891 "87f", "97f", "a7f", "b7f", "c7f", "d7f", "e7f", "f7f",
892 "08f", "18f", "28f", "38f", "48f", "58f", "68f", "78f",
893 "88f", "98f", "a8f", "b8f", "c8f", "d8f", "e8f", "f8f",
894 "09f", "19f", "29f", "39f", "49f", "59f", "69f", "79f",
895 "89f", "99f", "a9f", "b9f", "c9f", "d9f", "e9f", "f9f",
896 "0af", "1af", "2af", "3af", "4af", "5af", "6af", "7af",
897 "8af", "9af", "aaf", "baf", "caf", "daf", "eaf", "faf",
898 "0bf", "1bf", "2bf", "3bf", "4bf", "5bf", "6bf", "7bf",
899 "8bf", "9bf", "abf", "bbf", "cbf", "dbf", "ebf", "fbf",
900 "0cf", "1cf", "2cf", "3cf", "4cf", "5cf", "6cf", "7cf",
901 "8cf", "9cf", "acf", "bcf", "ccf", "dcf", "ecf", "fcf",
902 "0df", "1df", "2df", "3df", "4df", "5df", "6df", "7df",
903 "8df", "9df", "adf", "bdf", "cdf", "ddf", "edf", "fdf",
904 "0ef", "1ef", "2ef", "3ef", "4ef", "5ef", "6ef", "7ef",
905 "8ef", "9ef", "aef", "bef", "cef", "def", "eef", "fef",
906 "0ff", "1ff", "2ff", "3ff", "4ff", "5ff", "6ff", "7ff",
907 "8ff", "9ff", "aff", "bff", "cff", "dff", "eff", "fff"
908 };
909
910 /** string table for upper-case hexadecimal values */
911 static char *HEX[] = {
912 "", "1", "2", "3", "4", "5", "6", "7",
913 "8", "9", "A", "B", "C", "D", "E", "F",
914 "01", "11", "21", "31", "41", "51", "61", "71",
915 "81", "91", "A1", "B1", "C1", "D1", "E1", "F1",
916 "02", "12", "22", "32", "42", "52", "62", "72",
917 "82", "92", "A2", "B2", "C2", "D2", "E2", "F2",
918 "03", "13", "23", "33", "43", "53", "63", "73",
919 "83", "93", "A3", "B3", "C3", "D3", "E3", "F3",
920 "04", "14", "24", "34", "44", "54", "64", "74",
921 "84", "94", "A4", "B4", "C4", "D4", "E4", "F4",
922 "05", "15", "25", "35", "45", "55", "65", "75",
923 "85", "95", "A5", "B5", "C5", "D5", "E5", "F5",
924 "06", "16", "26", "36", "46", "56", "66", "76",
925 "86", "96", "A6", "B6", "C6", "D6", "E6", "F6",
926 "07", "17", "27", "37", "47", "57", "67", "77",
927 "87", "97", "A7", "B7", "C7", "D7", "E7", "F7",
928 "08", "18", "28", "38", "48", "58", "68", "78",
929 "88", "98", "A8", "B8", "C8", "D8", "E8", "F8",
930 "09", "19", "29", "39", "49", "59", "69", "79",
931 "89", "99", "A9", "B9", "C9", "D9", "E9", "F9",
932 "0A", "1A", "2A", "3A", "4A", "5A", "6A", "7A",
933 "8A", "9A", "AA", "BA", "CA", "DA", "EA", "FA",
934 "0B", "1B", "2B", "3B", "4B", "5B", "6B", "7B",
935 "8B", "9B", "AB", "BB", "CB", "DB", "EB", "FB",
936 "0C", "1C", "2C", "3C", "4C", "5C", "6C", "7C",
937 "8C", "9C", "AC", "BC", "CC", "DC", "EC", "FC",
938 "0D", "1D", "2D", "3D", "4D", "5D", "6D", "7D",
939 "8D", "9D", "AD", "BD", "CD", "DD", "ED", "FD",
940 "0E", "1E", "2E", "3E", "4E", "5E", "6E", "7E",
941 "8E", "9E", "AE", "BE", "CE", "DE", "EE", "FE",
942 "0F", "1F", "2F", "3F", "4F", "5F", "6F", "7F",
943 "8F", "9F", "AF", "BF", "CF", "DF", "EF", "FF",
944 "001", "101", "201", "301", "401", "501", "601", "701",
945 "801", "901", "A01", "B01", "C01", "D01", "E01", "F01",
946 "011", "111", "211", "311", "411", "511", "611", "711",
947 "811", "911", "A11", "B11", "C11", "D11", "E11", "F11",
948 "021", "121", "221", "321", "421", "521", "621", "721",
949 "821", "921", "A21", "B21", "C21", "D21", "E21", "F21",
950 "031", "131", "231", "331", "431", "531", "631", "731",
951 "831", "931", "A31", "B31", "C31", "D31", "E31", "F31",
952 "041", "141", "241", "341", "441", "541", "641", "741",
953 "841", "941", "A41", "B41", "C41", "D41", "E41", "F41",
954 "051", "151", "251", "351", "451", "551", "651", "751",
955 "851", "951", "A51", "B51", "C51", "D51", "E51", "F51",
956 "061", "161", "261", "361", "461", "561", "661", "761",
957 "861", "961", "A61", "B61", "C61", "D61", "E61", "F61",
958 "071", "171", "271", "371", "471", "571", "671", "771",
959 "871", "971", "A71", "B71", "C71", "D71", "E71", "F71",
960 "081", "181", "281", "381", "481", "581", "681", "781",
961 "881", "981", "A81", "B81", "C81", "D81", "E81", "F81",
962 "091", "191", "291", "391", "491", "591", "691", "791",
963 "891", "991", "A91", "B91", "C91", "D91", "E91", "F91",
964 "0A1", "1A1", "2A1", "3A1", "4A1", "5A1", "6A1", "7A1",
965 "8A1", "9A1", "AA1", "BA1", "CA1", "DA1", "EA1", "FA1",
966 "0B1", "1B1", "2B1", "3B1", "4B1", "5B1", "6B1", "7B1",
967 "8B1", "9B1", "AB1", "BB1", "CB1", "DB1", "EB1", "FB1",
968 "0C1", "1C1", "2C1", "3C1", "4C1", "5C1", "6C1", "7C1",
969 "8C1", "9C1", "AC1", "BC1", "CC1", "DC1", "EC1", "FC1",
970 "0D1", "1D1", "2D1", "3D1", "4D1", "5D1", "6D1", "7D1",
971 "8D1", "9D1", "AD1", "BD1", "CD1", "DD1", "ED1", "FD1",
972 "0E1", "1E1", "2E1", "3E1", "4E1", "5E1", "6E1", "7E1",
973 "8E1", "9E1", "AE1", "BE1", "CE1", "DE1", "EE1", "FE1",
974 "0F1", "1F1", "2F1", "3F1", "4F1", "5F1", "6F1", "7F1",
975 "8F1", "9F1", "AF1", "BF1", "CF1", "DF1", "EF1", "FF1",
976 "002", "102", "202", "302", "402", "502", "602", "702",
977 "802", "902", "A02", "B02", "C02", "D02", "E02", "F02",
978 "012", "112", "212", "312", "412", "512", "612", "712",
979 "812", "912", "A12", "B12", "C12", "D12", "E12", "F12",
980 "022", "122", "222", "322", "422", "522", "622", "722",
981 "822", "922", "A22", "B22", "C22", "D22", "E22", "F22",
982 "032", "132", "232", "332", "432", "532", "632", "732",
983 "832", "932", "A32", "B32", "C32", "D32", "E32", "F32",
984 "042", "142", "242", "342", "442", "542", "642", "742",
985 "842", "942", "A42", "B42", "C42", "D42", "E42", "F42",
986 "052", "152", "252", "352", "452", "552", "652", "752",
987 "852", "952", "A52", "B52", "C52", "D52", "E52", "F52",
988 "062", "162", "262", "362", "462", "562", "662", "762",
989 "862", "962", "A62", "B62", "C62", "D62", "E62", "F62",
990 "072", "172", "272", "372", "472", "572", "672", "772",
991 "872", "972", "A72", "B72", "C72", "D72", "E72", "F72",
992 "082", "182", "282", "382", "482", "582", "682", "782",
993 "882", "982", "A82", "B82", "C82", "D82", "E82", "F82",
994 "092", "192", "292", "392", "492", "592", "692", "792",
995 "892", "992", "A92", "B92", "C92", "D92", "E92", "F92",
996 "0A2", "1A2", "2A2", "3A2", "4A2", "5A2", "6A2", "7A2",
997 "8A2", "9A2", "AA2", "BA2", "CA2", "DA2", "EA2", "FA2",
998 "0B2", "1B2", "2B2", "3B2", "4B2", "5B2", "6B2", "7B2",
999 "8B2", "9B2", "AB2", "BB2", "CB2", "DB2", "EB2", "FB2",
1000 "0C2", "1C2", "2C2", "3C2", "4C2", "5C2", "6C2", "7C2",
1001 "8C2", "9C2", "AC2", "BC2", "CC2", "DC2", "EC2", "FC2",
1002 "0D2", "1D2", "2D2", "3D2", "4D2", "5D2", "6D2", "7D2",
1003 "8D2", "9D2", "AD2", "BD2", "CD2", "DD2", "ED2", "FD2",
1004 "0E2", "1E2", "2E2", "3E2", "4E2", "5E2", "6E2", "7E2",
1005 "8E2", "9E2", "AE2", "BE2", "CE2", "DE2", "EE2", "FE2",
1006 "0F2", "1F2", "2F2", "3F2", "4F2", "5F2", "6F2", "7F2",
1007 "8F2", "9F2", "AF2", "BF2", "CF2", "DF2", "EF2", "FF2",
1008 "003", "103", "203", "303", "403", "503", "603", "703",
1009 "803", "903", "A03", "B03", "C03", "D03", "E03", "F03",
1010 "013", "113", "213", "313", "413", "513", "613", "713",
1011 "813", "913", "A13", "B13", "C13", "D13", "E13", "F13",
1012 "023", "123", "223", "323", "423", "523", "623", "723",
1013 "823", "923", "A23", "B23", "C23", "D23", "E23", "F23",
1014 "033", "133", "233", "333", "433", "533", "633", "733",
1015 "833", "933", "A33", "B33", "C33", "D33", "E33", "F33",
1016 "043", "143", "243", "343", "443", "543", "643", "743",
1017 "843", "943", "A43", "B43", "C43", "D43", "E43", "F43",
1018 "053", "153", "253", "353", "453", "553", "653", "753",
1019 "853", "953", "A53", "B53", "C53", "D53", "E53", "F53",
1020 "063", "163", "263", "363", "463", "563", "663", "763",
1021 "863", "963", "A63", "B63", "C63", "D63", "E63", "F63",
1022 "073", "173", "273", "373", "473", "573", "673", "773",
1023 "873", "973", "A73", "B73", "C73", "D73", "E73", "F73",
1024 "083", "183", "283", "383", "483", "583", "683", "783",
1025 "883", "983", "A83", "B83", "C83", "D83", "E83", "F83",
1026 "093", "193", "293", "393", "493", "593", "693", "793",
1027 "893", "993", "A93", "B93", "C93", "D93", "E93", "F93",
1028 "0A3", "1A3", "2A3", "3A3", "4A3", "5A3", "6A3", "7A3",
1029 "8A3", "9A3", "AA3", "BA3", "CA3", "DA3", "EA3", "FA3",
1030 "0B3", "1B3", "2B3", "3B3", "4B3", "5B3", "6B3", "7B3",
1031 "8B3", "9B3", "AB3", "BB3", "CB3", "DB3", "EB3", "FB3",
1032 "0C3", "1C3", "2C3", "3C3", "4C3", "5C3", "6C3", "7C3",
1033 "8C3", "9C3", "AC3", "BC3", "CC3", "DC3", "EC3", "FC3",
1034 "0D3", "1D3", "2D3", "3D3", "4D3", "5D3", "6D3", "7D3",
1035 "8D3", "9D3", "AD3", "BD3", "CD3", "DD3", "ED3", "FD3",
1036 "0E3", "1E3", "2E3", "3E3", "4E3", "5E3", "6E3", "7E3",
1037 "8E3", "9E3", "AE3", "BE3", "CE3", "DE3", "EE3", "FE3",
1038 "0F3", "1F3", "2F3", "3F3", "4F3", "5F3", "6F3", "7F3",
1039 "8F3", "9F3", "AF3", "BF3", "CF3", "DF3", "EF3", "FF3",
1040 "004", "104", "204", "304", "404", "504", "604", "704",
1041 "804", "904", "A04", "B04", "C04", "D04", "E04", "F04",
1042 "014", "114", "214", "314", "414", "514", "614", "714",
1043 "814", "914", "A14", "B14", "C14", "D14", "E14", "F14",
1044 "024", "124", "224", "324", "424", "524", "624", "724",
1045 "824", "924", "A24", "B24", "C24", "D24", "E24", "F24",
1046 "034", "134", "234", "334", "434", "534", "634", "734",
1047 "834", "934", "A34", "B34", "C34", "D34", "E34", "F34",
1048 "044", "144", "244", "344", "444", "544", "644", "744",
1049 "844", "944", "A44", "B44", "C44", "D44", "E44", "F44",
1050 "054", "154", "254", "354", "454", "554", "654", "754",
1051 "854", "954", "A54", "B54", "C54", "D54", "E54", "F54",
1052 "064", "164", "264", "364", "464", "564", "664", "764",
1053 "864", "964", "A64", "B64", "C64", "D64", "E64", "F64",
1054 "074", "174", "274", "374", "474", "574", "674", "774",
1055 "874", "974", "A74", "B74", "C74", "D74", "E74", "F74",
1056 "084", "184", "284", "384", "484", "584", "684", "784",
1057 "884", "984", "A84", "B84", "C84", "D84", "E84", "F84",
1058 "094", "194", "294", "394", "494", "594", "694", "794",
1059 "894", "994", "A94", "B94", "C94", "D94", "E94", "F94",
1060 "0A4", "1A4", "2A4", "3A4", "4A4", "5A4", "6A4", "7A4",
1061 "8A4", "9A4", "AA4", "BA4", "CA4", "DA4", "EA4", "FA4",
1062 "0B4", "1B4", "2B4", "3B4", "4B4", "5B4", "6B4", "7B4",
1063 "8B4", "9B4", "AB4", "BB4", "CB4", "DB4", "EB4", "FB4",
1064 "0C4", "1C4", "2C4", "3C4", "4C4", "5C4", "6C4", "7C4",
1065 "8C4", "9C4", "AC4", "BC4", "CC4", "DC4", "EC4", "FC4",
1066 "0D4", "1D4", "2D4", "3D4", "4D4", "5D4", "6D4", "7D4",
1067 "8D4", "9D4", "AD4", "BD4", "CD4", "DD4", "ED4", "FD4",
1068 "0E4", "1E4", "2E4", "3E4", "4E4", "5E4", "6E4", "7E4",
1069 "8E4", "9E4", "AE4", "BE4", "CE4", "DE4", "EE4", "FE4",
1070 "0F4", "1F4", "2F4", "3F4", "4F4", "5F4", "6F4", "7F4",
1071 "8F4", "9F4", "AF4", "BF4", "CF4", "DF4", "EF4", "FF4",
1072 "005", "105", "205", "305", "405", "505", "605", "705",
1073 "805", "905", "A05", "B05", "C05", "D05", "E05", "F05",
1074 "015", "115", "215", "315", "415", "515", "615", "715",
1075 "815", "915", "A15", "B15", "C15", "D15", "E15", "F15",
1076 "025", "125", "225", "325", "425", "525", "625", "725",
1077 "825", "925", "A25", "B25", "C25", "D25", "E25", "F25",
1078 "035", "135", "235", "335", "435", "535", "635", "735",
1079 "835", "935", "A35", "B35", "C35", "D35", "E35", "F35",
1080 "045", "145", "245", "345", "445", "545", "645", "745",
1081 "845", "945", "A45", "B45", "C45", "D45", "E45", "F45",
1082 "055", "155", "255", "355", "455", "555", "655", "755",
1083 "855", "955", "A55", "B55", "C55", "D55", "E55", "F55",
1084 "065", "165", "265", "365", "465", "565", "665", "765",
1085 "865", "965", "A65", "B65", "C65", "D65", "E65", "F65",
1086 "075", "175", "275", "375", "475", "575", "675", "775",
1087 "875", "975", "A75", "B75", "C75", "D75", "E75", "F75",
1088 "085", "185", "285", "385", "485", "585", "685", "785",
1089 "885", "985", "A85", "B85", "C85", "D85", "E85", "F85",
1090 "095", "195", "295", "395", "495", "595", "695", "795",
1091 "895", "995", "A95", "B95", "C95", "D95", "E95", "F95",
1092 "0A5", "1A5", "2A5", "3A5", "4A5", "5A5", "6A5", "7A5",
1093 "8A5", "9A5", "AA5", "BA5", "CA5", "DA5", "EA5", "FA5",
1094 "0B5", "1B5", "2B5", "3B5", "4B5", "5B5", "6B5", "7B5",
1095 "8B5", "9B5", "AB5", "BB5", "CB5", "DB5", "EB5", "FB5",
1096 "0C5", "1C5", "2C5", "3C5", "4C5", "5C5", "6C5", "7C5",
1097 "8C5", "9C5", "AC5", "BC5", "CC5", "DC5", "EC5", "FC5",
1098 "0D5", "1D5", "2D5", "3D5", "4D5", "5D5", "6D5", "7D5",
1099 "8D5", "9D5", "AD5", "BD5", "CD5", "DD5", "ED5", "FD5",
1100 "0E5", "1E5", "2E5", "3E5", "4E5", "5E5", "6E5", "7E5",
1101 "8E5", "9E5", "AE5", "BE5", "CE5", "DE5", "EE5", "FE5",
1102 "0F5", "1F5", "2F5", "3F5", "4F5", "5F5", "6F5", "7F5",
1103 "8F5", "9F5", "AF5", "BF5", "CF5", "DF5", "EF5", "FF5",
1104 "006", "106", "206", "306", "406", "506", "606", "706",
1105 "806", "906", "A06", "B06", "C06", "D06", "E06", "F06",
1106 "016", "116", "216", "316", "416", "516", "616", "716",
1107 "816", "916", "A16", "B16", "C16", "D16", "E16", "F16",
1108 "026", "126", "226", "326", "426", "526", "626", "726",
1109 "826", "926", "A26", "B26", "C26", "D26", "E26", "F26",
1110 "036", "136", "236", "336", "436", "536", "636", "736",
1111 "836", "936", "A36", "B36", "C36", "D36", "E36", "F36",
1112 "046", "146", "246", "346", "446", "546", "646", "746",
1113 "846", "946", "A46", "B46", "C46", "D46", "E46", "F46",
1114 "056", "156", "256", "356", "456", "556", "656", "756",
1115 "856", "956", "A56", "B56", "C56", "D56", "E56", "F56",
1116 "066", "166", "266", "366", "466", "566", "666", "766",
1117 "866", "966", "A66", "B66", "C66", "D66", "E66", "F66",
1118 "076", "176", "276", "376", "476", "576", "676", "776",
1119 "876", "976", "A76", "B76", "C76", "D76", "E76", "F76",
1120 "086", "186", "286", "386", "486", "586", "686", "786",
1121 "886", "986", "A86", "B86", "C86", "D86", "E86", "F86",
1122 "096", "196", "296", "396", "496", "596", "696", "796",
1123 "896", "996", "A96", "B96", "C96", "D96", "E96", "F96",
1124 "0A6", "1A6", "2A6", "3A6", "4A6", "5A6", "6A6", "7A6",
1125 "8A6", "9A6", "AA6", "BA6", "CA6", "DA6", "EA6", "FA6",
1126 "0B6", "1B6", "2B6", "3B6", "4B6", "5B6", "6B6", "7B6",
1127 "8B6", "9B6", "AB6", "BB6", "CB6", "DB6", "EB6", "FB6",
1128 "0C6", "1C6", "2C6", "3C6", "4C6", "5C6", "6C6", "7C6",
1129 "8C6", "9C6", "AC6", "BC6", "CC6", "DC6", "EC6", "FC6",
1130 "0D6", "1D6", "2D6", "3D6", "4D6", "5D6", "6D6", "7D6",
1131 "8D6", "9D6", "AD6", "BD6", "CD6", "DD6", "ED6", "FD6",
1132 "0E6", "1E6", "2E6", "3E6", "4E6", "5E6", "6E6", "7E6",
1133 "8E6", "9E6", "AE6", "BE6", "CE6", "DE6", "EE6", "FE6",
1134 "0F6", "1F6", "2F6", "3F6", "4F6", "5F6", "6F6", "7F6",
1135 "8F6", "9F6", "AF6", "BF6", "CF6", "DF6", "EF6", "FF6",
1136 "007", "107", "207", "307", "407", "507", "607", "707",
1137 "807", "907", "A07", "B07", "C07", "D07", "E07", "F07",
1138 "017", "117", "217", "317", "417", "517", "617", "717",
1139 "817", "917", "A17", "B17", "C17", "D17", "E17", "F17",
1140 "027", "127", "227", "327", "427", "527", "627", "727",
1141 "827", "927", "A27", "B27", "C27", "D27", "E27", "F27",
1142 "037", "137", "237", "337", "437", "537", "637", "737",
1143 "837", "937", "A37", "B37", "C37", "D37", "E37", "F37",
1144 "047", "147", "247", "347", "447", "547", "647", "747",
1145 "847", "947", "A47", "B47", "C47", "D47", "E47", "F47",
1146 "057", "157", "257", "357", "457", "557", "657", "757",
1147 "857", "957", "A57", "B57", "C57", "D57", "E57", "F57",
1148 "067", "167", "267", "367", "467", "567", "667", "767",
1149 "867", "967", "A67", "B67", "C67", "D67", "E67", "F67",
1150 "077", "177", "277", "377", "477", "577", "677", "777",
1151 "877", "977", "A77", "B77", "C77", "D77", "E77", "F77",
1152 "087", "187", "287", "387", "487", "587", "687", "787",
1153 "887", "987", "A87", "B87", "C87", "D87", "E87", "F87",
1154 "097", "197", "297", "397", "497", "597", "697", "797",
1155 "897", "997", "A97", "B97", "C97", "D97", "E97", "F97",
1156 "0A7", "1A7", "2A7", "3A7", "4A7", "5A7", "6A7", "7A7",
1157 "8A7", "9A7", "AA7", "BA7", "CA7", "DA7", "EA7", "FA7",
1158 "0B7", "1B7", "2B7", "3B7", "4B7", "5B7", "6B7", "7B7",
1159 "8B7", "9B7", "AB7", "BB7", "CB7", "DB7", "EB7", "FB7",
1160 "0C7", "1C7", "2C7", "3C7", "4C7", "5C7", "6C7", "7C7",
1161 "8C7", "9C7", "AC7", "BC7", "CC7", "DC7", "EC7", "FC7",
1162 "0D7", "1D7", "2D7", "3D7", "4D7", "5D7", "6D7", "7D7",
1163 "8D7", "9D7", "AD7", "BD7", "CD7", "DD7", "ED7", "FD7",
1164 "0E7", "1E7", "2E7", "3E7", "4E7", "5E7", "6E7", "7E7",
1165 "8E7", "9E7", "AE7", "BE7", "CE7", "DE7", "EE7", "FE7",
1166 "0F7", "1F7", "2F7", "3F7", "4F7", "5F7", "6F7", "7F7",
1167 "8F7", "9F7", "AF7", "BF7", "CF7", "DF7", "EF7", "FF7",
1168 "008", "108", "208", "308", "408", "508", "608", "708",
1169 "808", "908", "A08", "B08", "C08", "D08", "E08", "F08",
1170 "018", "118", "218", "318", "418", "518", "618", "718",
1171 "818", "918", "A18", "B18", "C18", "D18", "E18", "F18",
1172 "028", "128", "228", "328", "428", "528", "628", "728",
1173 "828", "928", "A28", "B28", "C28", "D28", "E28", "F28",
1174 "038", "138", "238", "338", "438", "538", "638", "738",
1175 "838", "938", "A38", "B38", "C38", "D38", "E38", "F38",
1176 "048", "148", "248", "348", "448", "548", "648", "748",
1177 "848", "948", "A48", "B48", "C48", "D48", "E48", "F48",
1178 "058", "158", "258", "358", "458", "558", "658", "758",
1179 "858", "958", "A58", "B58", "C58", "D58", "E58", "F58",
1180 "068", "168", "268", "368", "468", "568", "668", "768",
1181 "868", "968", "A68", "B68", "C68", "D68", "E68", "F68",
1182 "078", "178", "278", "378", "478", "578", "678", "778",
1183 "878", "978", "A78", "B78", "C78", "D78", "E78", "F78",
1184 "088", "188", "288", "388", "488", "588", "688", "788",
1185 "888", "988", "A88", "B88", "C88", "D88", "E88", "F88",
1186 "098", "198", "298", "398", "498", "598", "698", "798",
1187 "898", "998", "A98", "B98", "C98", "D98", "E98", "F98",
1188 "0A8", "1A8", "2A8", "3A8", "4A8", "5A8", "6A8", "7A8",
1189 "8A8", "9A8", "AA8", "BA8", "CA8", "DA8", "EA8", "FA8",
1190 "0B8", "1B8", "2B8", "3B8", "4B8", "5B8", "6B8", "7B8",
1191 "8B8", "9B8", "AB8", "BB8", "CB8", "DB8", "EB8", "FB8",
1192 "0C8", "1C8", "2C8", "3C8", "4C8", "5C8", "6C8", "7C8",
1193 "8C8", "9C8", "AC8", "BC8", "CC8", "DC8", "EC8", "FC8",
1194 "0D8", "1D8", "2D8", "3D8", "4D8", "5D8", "6D8", "7D8",
1195 "8D8", "9D8", "AD8", "BD8", "CD8", "DD8", "ED8", "FD8",
1196 "0E8", "1E8", "2E8", "3E8", "4E8", "5E8", "6E8", "7E8",
1197 "8E8", "9E8", "AE8", "BE8", "CE8", "DE8", "EE8", "FE8",
1198 "0F8", "1F8", "2F8", "3F8", "4F8", "5F8", "6F8", "7F8",
1199 "8F8", "9F8", "AF8", "BF8", "CF8", "DF8", "EF8", "FF8",
1200 "009", "109", "209", "309", "409", "509", "609", "709",
1201 "809", "909", "A09", "B09", "C09", "D09", "E09", "F09",
1202 "019", "119", "219", "319", "419", "519", "619", "719",
1203 "819", "919", "A19", "B19", "C19", "D19", "E19", "F19",
1204 "029", "129", "229", "329", "429", "529", "629", "729",
1205 "829", "929", "A29", "B29", "C29", "D29", "E29", "F29",
1206 "039", "139", "239", "339", "439", "539", "639", "739",
1207 "839", "939", "A39", "B39", "C39", "D39", "E39", "F39",
1208 "049", "149", "249", "349", "449", "549", "649", "749",
1209 "849", "949", "A49", "B49", "C49", "D49", "E49", "F49",
1210 "059", "159", "259", "359", "459", "559", "659", "759",
1211 "859", "959", "A59", "B59", "C59", "D59", "E59", "F59",
1212 "069", "169", "269", "369", "469", "569", "669", "769",
1213 "869", "969", "A69", "B69", "C69", "D69", "E69", "F69",
1214 "079", "179", "279", "379", "479", "579", "679", "779",
1215 "879", "979", "A79", "B79", "C79", "D79", "E79", "F79",
1216 "089", "189", "289", "389", "489", "589", "689", "789",
1217 "889", "989", "A89", "B89", "C89", "D89", "E89", "F89",
1218 "099", "199", "299", "399", "499", "599", "699", "799",
1219 "899", "999", "A99", "B99", "C99", "D99", "E99", "F99",
1220 "0A9", "1A9", "2A9", "3A9", "4A9", "5A9", "6A9", "7A9",
1221 "8A9", "9A9", "AA9", "BA9", "CA9", "DA9", "EA9", "FA9",
1222 "0B9", "1B9", "2B9", "3B9", "4B9", "5B9", "6B9", "7B9",
1223 "8B9", "9B9", "AB9", "BB9", "CB9", "DB9", "EB9", "FB9",
1224 "0C9", "1C9", "2C9", "3C9", "4C9", "5C9", "6C9", "7C9",
1225 "8C9", "9C9", "AC9", "BC9", "CC9", "DC9", "EC9", "FC9",
1226 "0D9", "1D9", "2D9", "3D9", "4D9", "5D9", "6D9", "7D9",
1227 "8D9", "9D9", "AD9", "BD9", "CD9", "DD9", "ED9", "FD9",
1228 "0E9", "1E9", "2E9", "3E9", "4E9", "5E9", "6E9", "7E9",
1229 "8E9", "9E9", "AE9", "BE9", "CE9", "DE9", "EE9", "FE9",
1230 "0F9", "1F9", "2F9", "3F9", "4F9", "5F9", "6F9", "7F9",
1231 "8F9", "9F9", "AF9", "BF9", "CF9", "DF9", "EF9", "FF9",
1232 "00A", "10A", "20A", "30A", "40A", "50A", "60A", "70A",
1233 "80A", "90A", "A0A", "B0A", "C0A", "D0A", "E0A", "F0A",
1234 "01A", "11A", "21A", "31A", "41A", "51A", "61A", "71A",
1235 "81A", "91A", "A1A", "B1A", "C1A", "D1A", "E1A", "F1A",
1236 "02A", "12A", "22A", "32A", "42A", "52A", "62A", "72A",
1237 "82A", "92A", "A2A", "B2A", "C2A", "D2A", "E2A", "F2A",
1238 "03A", "13A", "23A", "33A", "43A", "53A", "63A", "73A",
1239 "83A", "93A", "A3A", "B3A", "C3A", "D3A", "E3A", "F3A",
1240 "04A", "14A", "24A", "34A", "44A", "54A", "64A", "74A",
1241 "84A", "94A", "A4A", "B4A", "C4A", "D4A", "E4A", "F4A",
1242 "05A", "15A", "25A", "35A", "45A", "55A", "65A", "75A",
1243 "85A", "95A", "A5A", "B5A", "C5A", "D5A", "E5A", "F5A",
1244 "06A", "16A", "26A", "36A", "46A", "56A", "66A", "76A",
1245 "86A", "96A", "A6A", "B6A", "C6A", "D6A", "E6A", "F6A",
1246 "07A", "17A", "27A", "37A", "47A", "57A", "67A", "77A",
1247 "87A", "97A", "A7A", "B7A", "C7A", "D7A", "E7A", "F7A",
1248 "08A", "18A", "28A", "38A", "48A", "58A", "68A", "78A",
1249 "88A", "98A", "A8A", "B8A", "C8A", "D8A", "E8A", "F8A",
1250 "09A", "19A", "29A", "39A", "49A", "59A", "69A", "79A",
1251 "89A", "99A", "A9A", "B9A", "C9A", "D9A", "E9A", "F9A",
1252 "0AA", "1AA", "2AA", "3AA", "4AA", "5AA", "6AA", "7AA",
1253 "8AA", "9AA", "AAA", "BAA", "CAA", "DAA", "EAA", "FAA",
1254 "0BA", "1BA", "2BA", "3BA", "4BA", "5BA", "6BA", "7BA",
1255 "8BA", "9BA", "ABA", "BBA", "CBA", "DBA", "EBA", "FBA",
1256 "0CA", "1CA", "2CA", "3CA", "4CA", "5CA", "6CA", "7CA",
1257 "8CA", "9CA", "ACA", "BCA", "CCA", "DCA", "ECA", "FCA",
1258 "0DA", "1DA", "2DA", "3DA", "4DA", "5DA", "6DA", "7DA",
1259 "8DA", "9DA", "ADA", "BDA", "CDA", "DDA", "EDA", "FDA",
1260 "0EA", "1EA", "2EA", "3EA", "4EA", "5EA", "6EA", "7EA",
1261 "8EA", "9EA", "AEA", "BEA", "CEA", "DEA", "EEA", "FEA",
1262 "0FA", "1FA", "2FA", "3FA", "4FA", "5FA", "6FA", "7FA",
1263 "8FA", "9FA", "AFA", "BFA", "CFA", "DFA", "EFA", "FFA",
1264 "00B", "10B", "20B", "30B", "40B", "50B", "60B", "70B",
1265 "80B", "90B", "A0B", "B0B", "C0B", "D0B", "E0B", "F0B",
1266 "01B", "11B", "21B", "31B", "41B", "51B", "61B", "71B",
1267 "81B", "91B", "A1B", "B1B", "C1B", "D1B", "E1B", "F1B",
1268 "02B", "12B", "22B", "32B", "42B", "52B", "62B", "72B",
1269 "82B", "92B", "A2B", "B2B", "C2B", "D2B", "E2B", "F2B",
1270 "03B", "13B", "23B", "33B", "43B", "53B", "63B", "73B",
1271 "83B", "93B", "A3B", "B3B", "C3B", "D3B", "E3B", "F3B",
1272 "04B", "14B", "24B", "34B", "44B", "54B", "64B", "74B",
1273 "84B", "94B", "A4B", "B4B", "C4B", "D4B", "E4B", "F4B",
1274 "05B", "15B", "25B", "35B", "45B", "55B", "65B", "75B",
1275 "85B", "95B", "A5B", "B5B", "C5B", "D5B", "E5B", "F5B",
1276 "06B", "16B", "26B", "36B", "46B", "56B", "66B", "76B",
1277 "86B", "96B", "A6B", "B6B", "C6B", "D6B", "E6B", "F6B",
1278 "07B", "17B", "27B", "37B", "47B", "57B", "67B", "77B",
1279 "87B", "97B", "A7B", "B7B", "C7B", "D7B", "E7B", "F7B",
1280 "08B", "18B", "28B", "38B", "48B", "58B", "68B", "78B",
1281 "88B", "98B", "A8B", "B8B", "C8B", "D8B", "E8B", "F8B",
1282 "09B", "19B", "29B", "39B", "49B", "59B", "69B", "79B",
1283 "89B", "99B", "A9B", "B9B", "C9B", "D9B", "E9B", "F9B",
1284 "0AB", "1AB", "2AB", "3AB", "4AB", "5AB", "6AB", "7AB",
1285 "8AB", "9AB", "AAB", "BAB", "CAB", "DAB", "EAB", "FAB",
1286 "0BB", "1BB", "2BB", "3BB", "4BB", "5BB", "6BB", "7BB",
1287 "8BB", "9BB", "ABB", "BBB", "CBB", "DBB", "EBB", "FBB",
1288 "0CB", "1CB", "2CB", "3CB", "4CB", "5CB", "6CB", "7CB",
1289 "8CB", "9CB", "ACB", "BCB", "CCB", "DCB", "ECB", "FCB",
1290 "0DB", "1DB", "2DB", "3DB", "4DB", "5DB", "6DB", "7DB",
1291 "8DB", "9DB", "ADB", "BDB", "CDB", "DDB", "EDB", "FDB",
1292 "0EB", "1EB", "2EB", "3EB", "4EB", "5EB", "6EB", "7EB",
1293 "8EB", "9EB", "AEB", "BEB", "CEB", "DEB", "EEB", "FEB",
1294 "0FB", "1FB", "2FB", "3FB", "4FB", "5FB", "6FB", "7FB",
1295 "8FB", "9FB", "AFB", "BFB", "CFB", "DFB", "EFB", "FFB",
1296 "00C", "10C", "20C", "30C", "40C", "50C", "60C", "70C",
1297 "80C", "90C", "A0C", "B0C", "C0C", "D0C", "E0C", "F0C",
1298 "01C", "11C", "21C", "31C", "41C", "51C", "61C", "71C",
1299 "81C", "91C", "A1C", "B1C", "C1C", "D1C", "E1C", "F1C",
1300 "02C", "12C", "22C", "32C", "42C", "52C", "62C", "72C",
1301 "82C", "92C", "A2C", "B2C", "C2C", "D2C", "E2C", "F2C",
1302 "03C", "13C", "23C", "33C", "43C", "53C", "63C", "73C",
1303 "83C", "93C", "A3C", "B3C", "C3C", "D3C", "E3C", "F3C",
1304 "04C", "14C", "24C", "34C", "44C", "54C", "64C", "74C",
1305 "84C", "94C", "A4C", "B4C", "C4C", "D4C", "E4C", "F4C",
1306 "05C", "15C", "25C", "35C", "45C", "55C", "65C", "75C",
1307 "85C", "95C", "A5C", "B5C", "C5C", "D5C", "E5C", "F5C",
1308 "06C", "16C", "26C", "36C", "46C", "56C", "66C", "76C",
1309 "86C", "96C", "A6C", "B6C", "C6C", "D6C", "E6C", "F6C",
1310 "07C", "17C", "27C", "37C", "47C", "57C", "67C", "77C",
1311 "87C", "97C", "A7C", "B7C", "C7C", "D7C", "E7C", "F7C",
1312 "08C", "18C", "28C", "38C", "48C", "58C", "68C", "78C",
1313 "88C", "98C", "A8C", "B8C", "C8C", "D8C", "E8C", "F8C",
1314 "09C", "19C", "29C", "39C", "49C", "59C", "69C", "79C",
1315 "89C", "99C", "A9C", "B9C", "C9C", "D9C", "E9C", "F9C",
1316 "0AC", "1AC", "2AC", "3AC", "4AC", "5AC", "6AC", "7AC",
1317 "8AC", "9AC", "AAC", "BAC", "CAC", "DAC", "EAC", "FAC",
1318 "0BC", "1BC", "2BC", "3BC", "4BC", "5BC", "6BC", "7BC",
1319 "8BC", "9BC", "ABC", "BBC", "CBC", "DBC", "EBC", "FBC",
1320 "0CC", "1CC", "2CC", "3CC", "4CC", "5CC", "6CC", "7CC",
1321 "8CC", "9CC", "ACC", "BCC", "CCC", "DCC", "ECC", "FCC",
1322 "0DC", "1DC", "2DC", "3DC", "4DC", "5DC", "6DC", "7DC",
1323 "8DC", "9DC", "ADC", "BDC", "CDC", "DDC", "EDC", "FDC",
1324 "0EC", "1EC", "2EC", "3EC", "4EC", "5EC", "6EC", "7EC",
1325 "8EC", "9EC", "AEC", "BEC", "CEC", "DEC", "EEC", "FEC",
1326 "0FC", "1FC", "2FC", "3FC", "4FC", "5FC", "6FC", "7FC",
1327 "8FC", "9FC", "AFC", "BFC", "CFC", "DFC", "EFC", "FFC",
1328 "00D", "10D", "20D", "30D", "40D", "50D", "60D", "70D",
1329 "80D", "90D", "A0D", "B0D", "C0D", "D0D", "E0D", "F0D",
1330 "01D", "11D", "21D", "31D", "41D", "51D", "61D", "71D",
1331 "81D", "91D", "A1D", "B1D", "C1D", "D1D", "E1D", "F1D",
1332 "02D", "12D", "22D", "32D", "42D", "52D", "62D", "72D",
1333 "82D", "92D", "A2D", "B2D", "C2D", "D2D", "E2D", "F2D",
1334 "03D", "13D", "23D", "33D", "43D", "53D", "63D", "73D",
1335 "83D", "93D", "A3D", "B3D", "C3D", "D3D", "E3D", "F3D",
1336 "04D", "14D", "24D", "34D", "44D", "54D", "64D", "74D",
1337 "84D", "94D", "A4D", "B4D", "C4D", "D4D", "E4D", "F4D",
1338 "05D", "15D", "25D", "35D", "45D", "55D", "65D", "75D",
1339 "85D", "95D", "A5D", "B5D", "C5D", "D5D", "E5D", "F5D",
1340 "06D", "16D", "26D", "36D", "46D", "56D", "66D", "76D",
1341 "86D", "96D", "A6D", "B6D", "C6D", "D6D", "E6D", "F6D",
1342 "07D", "17D", "27D", "37D", "47D", "57D", "67D", "77D",
1343 "87D", "97D", "A7D", "B7D", "C7D", "D7D", "E7D", "F7D",
1344 "08D", "18D", "28D", "38D", "48D", "58D", "68D", "78D",
1345 "88D", "98D", "A8D", "B8D", "C8D", "D8D", "E8D", "F8D",
1346 "09D", "19D", "29D", "39D", "49D", "59D", "69D", "79D",
1347 "89D", "99D", "A9D", "B9D", "C9D", "D9D", "E9D", "F9D",
1348 "0AD", "1AD", "2AD", "3AD", "4AD", "5AD", "6AD", "7AD",
1349 "8AD", "9AD", "AAD", "BAD", "CAD", "DAD", "EAD", "FAD",
1350 "0BD", "1BD", "2BD", "3BD", "4BD", "5BD", "6BD", "7BD",
1351 "8BD", "9BD", "ABD", "BBD", "CBD", "DBD", "EBD", "FBD",
1352 "0CD", "1CD", "2CD", "3CD", "4CD", "5CD", "6CD", "7CD",
1353 "8CD", "9CD", "ACD", "BCD", "CCD", "DCD", "ECD", "FCD",
1354 "0DD", "1DD", "2DD", "3DD", "4DD", "5DD", "6DD", "7DD",
1355 "8DD", "9DD", "ADD", "BDD", "CDD", "DDD", "EDD", "FDD",
1356 "0ED", "1ED", "2ED", "3ED", "4ED", "5ED", "6ED", "7ED",
1357 "8ED", "9ED", "AED", "BED", "CED", "DED", "EED", "FED",
1358 "0FD", "1FD", "2FD", "3FD", "4FD", "5FD", "6FD", "7FD",
1359 "8FD", "9FD", "AFD", "BFD", "CFD", "DFD", "EFD", "FFD",
1360 "00E", "10E", "20E", "30E", "40E", "50E", "60E", "70E",
1361 "80E", "90E", "A0E", "B0E", "C0E", "D0E", "E0E", "F0E",
1362 "01E", "11E", "21E", "31E", "41E", "51E", "61E", "71E",
1363 "81E", "91E", "A1E", "B1E", "C1E", "D1E", "E1E", "F1E",
1364 "02E", "12E", "22E", "32E", "42E", "52E", "62E", "72E",
1365 "82E", "92E", "A2E", "B2E", "C2E", "D2E", "E2E", "F2E",
1366 "03E", "13E", "23E", "33E", "43E", "53E", "63E", "73E",
1367 "83E", "93E", "A3E", "B3E", "C3E", "D3E", "E3E", "F3E",
1368 "04E", "14E", "24E", "34E", "44E", "54E", "64E", "74E",
1369 "84E", "94E", "A4E", "B4E", "C4E", "D4E", "E4E", "F4E",
1370 "05E", "15E", "25E", "35E", "45E", "55E", "65E", "75E",
1371 "85E", "95E", "A5E", "B5E", "C5E", "D5E", "E5E", "F5E",
1372 "06E", "16E", "26E", "36E", "46E", "56E", "66E", "76E",
1373 "86E", "96E", "A6E", "B6E", "C6E", "D6E", "E6E", "F6E",
1374 "07E", "17E", "27E", "37E", "47E", "57E", "67E", "77E",
1375 "87E", "97E", "A7E", "B7E", "C7E", "D7E", "E7E", "F7E",
1376 "08E", "18E", "28E", "38E", "48E", "58E", "68E", "78E",
1377 "88E", "98E", "A8E", "B8E", "C8E", "D8E", "E8E", "F8E",
1378 "09E", "19E", "29E", "39E", "49E", "59E", "69E", "79E",
1379 "89E", "99E", "A9E", "B9E", "C9E", "D9E", "E9E", "F9E",
1380 "0AE", "1AE", "2AE", "3AE", "4AE", "5AE", "6AE", "7AE",
1381 "8AE", "9AE", "AAE", "BAE", "CAE", "DAE", "EAE", "FAE",
1382 "0BE", "1BE", "2BE", "3BE", "4BE", "5BE", "6BE", "7BE",
1383 "8BE", "9BE", "ABE", "BBE", "CBE", "DBE", "EBE", "FBE",
1384 "0CE", "1CE", "2CE", "3CE", "4CE", "5CE", "6CE", "7CE",
1385 "8CE", "9CE", "ACE", "BCE", "CCE", "DCE", "ECE", "FCE",
1386 "0DE", "1DE", "2DE", "3DE", "4DE", "5DE", "6DE", "7DE",
1387 "8DE", "9DE", "ADE", "BDE", "CDE", "DDE", "EDE", "FDE",
1388 "0EE", "1EE", "2EE", "3EE", "4EE", "5EE", "6EE", "7EE",
1389 "8EE", "9EE", "AEE", "BEE", "CEE", "DEE", "EEE", "FEE",
1390 "0FE", "1FE", "2FE", "3FE", "4FE", "5FE", "6FE", "7FE",
1391 "8FE", "9FE", "AFE", "BFE", "CFE", "DFE", "EFE", "FFE",
1392 "00F", "10F", "20F", "30F", "40F", "50F", "60F", "70F",
1393 "80F", "90F", "A0F", "B0F", "C0F", "D0F", "E0F", "F0F",
1394 "01F", "11F", "21F", "31F", "41F", "51F", "61F", "71F",
1395 "81F", "91F", "A1F", "B1F", "C1F", "D1F", "E1F", "F1F",
1396 "02F", "12F", "22F", "32F", "42F", "52F", "62F", "72F",
1397 "82F", "92F", "A2F", "B2F", "C2F", "D2F", "E2F", "F2F",
1398 "03F", "13F", "23F", "33F", "43F", "53F", "63F", "73F",
1399 "83F", "93F", "A3F", "B3F", "C3F", "D3F", "E3F", "F3F",
1400 "04F", "14F", "24F", "34F", "44F", "54F", "64F", "74F",
1401 "84F", "94F", "A4F", "B4F", "C4F", "D4F", "E4F", "F4F",
1402 "05F", "15F", "25F", "35F", "45F", "55F", "65F", "75F",
1403 "85F", "95F", "A5F", "B5F", "C5F", "D5F", "E5F", "F5F",
1404 "06F", "16F", "26F", "36F", "46F", "56F", "66F", "76F",
1405 "86F", "96F", "A6F", "B6F", "C6F", "D6F", "E6F", "F6F",
1406 "07F", "17F", "27F", "37F", "47F", "57F", "67F", "77F",
1407 "87F", "97F", "A7F", "B7F", "C7F", "D7F", "E7F", "F7F",
1408 "08F", "18F", "28F", "38F", "48F", "58F", "68F", "78F",
1409 "88F", "98F", "A8F", "B8F", "C8F", "D8F", "E8F", "F8F",
1410 "09F", "19F", "29F", "39F", "49F", "59F", "69F", "79F",
1411 "89F", "99F", "A9F", "B9F", "C9F", "D9F", "E9F", "F9F",
1412 "0AF", "1AF", "2AF", "3AF", "4AF", "5AF", "6AF", "7AF",
1413 "8AF", "9AF", "AAF", "BAF", "CAF", "DAF", "EAF", "FAF",
1414 "0BF", "1BF", "2BF", "3BF", "4BF", "5BF", "6BF", "7BF",
1415 "8BF", "9BF", "ABF", "BBF", "CBF", "DBF", "EBF", "FBF",
1416 "0CF", "1CF", "2CF", "3CF", "4CF", "5CF", "6CF", "7CF",
1417 "8CF", "9CF", "ACF", "BCF", "CCF", "DCF", "ECF", "FCF",
1418 "0DF", "1DF", "2DF", "3DF", "4DF", "5DF", "6DF", "7DF",
1419 "8DF", "9DF", "ADF", "BDF", "CDF", "DDF", "EDF", "FDF",
1420 "0EF", "1EF", "2EF", "3EF", "4EF", "5EF", "6EF", "7EF",
1421 "8EF", "9EF", "AEF", "BEF", "CEF", "DEF", "EEF", "FEF",
1422 "0FF", "1FF", "2FF", "3FF", "4FF", "5FF", "6FF", "7FF",
1423 "8FF", "9FF", "AFF", "BFF", "CFF", "DFF", "EFF", "FFF"
1424 };
1425
1426 /** Append a single character to an output buffer.
1427 * @param[in,out] buf_p Buffer to append to.
1428 * @param[in] c Character to append.
1429 */
1430 static void
1431 addc(struct BufData *buf_p, int c)
1432 {
1433 int overflow = 0;
1434
1435 if (buf_p->limit == 0) { /* We've gone past the limit... */
1436 buf_p->overflow++;
1437 overflow++;
1438 } else if (buf_p->limit > 0) /* update the limit */
1439 buf_p->limit--;
1440
1441 if (buf_p->buf_loc >= buf_p->buf_size) { /* We've gone past buffer */
1442 buf_p->buf_overflow++;
1443 overflow++;
1444 }
1445
1446 if (!overflow) /* add the character to the buffer */
1447 buf_p->buf[buf_p->buf_loc++] = c;
1448 }
1449
1450 /** Append a string to an output buffer.
1451 * @param[in,out] buf_p Buffer to append to.
1452 * @param[in] s_len Length of string to append.
1453 * @param[in] s String to append.
1454 */
1455 static void
1456 adds(struct BufData *buf_p, int s_len, const char *s)
1457 {
1458 int overflow = 0;
1459
1460 /* while the string exists and has non-zero length */
1461 while (s_len && *s)
1462 {
1463 /* poor man's inlining; see addc(), above */
1464 if (buf_p->limit == 0) { /* We've gone past the limit... */
1465 buf_p->overflow++;
1466 overflow++;
1467 } else if (buf_p->limit > 0) /* update the limit */
1468 buf_p->limit--;
1469
1470 if (buf_p->buf_loc >= buf_p->buf_size) { /* We've gone past buffer */
1471 buf_p->buf_overflow++;
1472 overflow++;
1473 }
1474
1475 if (!overflow) /* add the character to the buffer */
1476 buf_p->buf[buf_p->buf_loc++] = *s;
1477
1478 s++; /* advance to next character */
1479 if (s_len > 0) /* update string length left to copy */
1480 s_len--;
1481 }
1482 }
1483
1484 /** Add certain padding to an output buffer.
1485 * @param[in,out] buf_p Buffer to append to.
1486 * @param[in] padlen Length of padding to add.
1487 * @param[in] pad Padding string (at least PAD_LENGTH bytes long).
1488 */
1489 static void
1490 do_pad(struct BufData *buf_p, int padlen, char *pad)
1491 {
1492 /* do chunks of PAD_LENGTH first */
1493 for (; padlen > PAD_LENGTH; padlen -= PAD_LENGTH)
1494 adds(buf_p, PAD_LENGTH, pad);
1495
1496 /* add any left-over padding */
1497 adds(buf_p, padlen, pad);
1498 }
1499
1500 /** Return length of string, up to a maximum.
1501 * @param[in] str String to find length for.
1502 * @param[in] maxlen Maximum value to return.
1503 * @return Minimum of \a maxlen and length of \a str.
1504 */
1505 static int
1506 my_strnlen(const char *str, int maxlen)
1507 {
1508 int len = 0;
1509
1510 while (*str++ && maxlen--)
1511 len++;
1512
1513 return len;
1514 }
1515
1516 /** Workhorse printing function.
1517 * @param[in] dest Client to format the message.
1518 * @param[in,out] buf_p Description of output buffer.
1519 * @param[in] fmt Message format string.
1520 * @param[in] vp Variable-length argument list for format string.
1521 */
1522 static void
1523 doprintf(struct Client *dest, struct BufData *buf_p, const char *fmt,
1524 va_list vp)
1525 {
1526 enum {
1527 FLAG, /* Gathering flags */
1528 WIDTH, /* Gathering field width */
1529 DOT, /* Found a dot */
1530 PREC, /* Gathering field precision */
1531 OPT, /* Gathering field options (l, h, q, etc.) */
1532 SPEC /* Looking for field specifier */
1533 } state = FLAG;
1534 struct FieldData fld_s = FIELDDATA_INIT;
1535 const char *fstart = 0;
1536
1537 for (; *fmt; fmt++) {
1538 /* If it's not %, or if it's %%, append it to the string */
1539 if (*fmt != '%' || (*fmt == '%' && *++fmt == '%')) {
1540 addc(buf_p, *fmt); /* add the character to the string */
1541
1542 continue; /* go to the next character */
1543 }
1544
1545 state = FLAG; /* initialize our field data */
1546 fld_s.flags = 0;
1547 fld_s.base = BASE_DECIMAL;
1548 fld_s.width = 0;
1549 fld_s.prec = -1;
1550 fstart = fmt;
1551
1552 for (; *fmt; fmt++) {
1553 switch (*fmt) {
1554 case '-': /* Deal with a minus flag */
1555 if (state == FLAG)
1556 fld_s.flags |= FLAG_MINUS;
1557 else if (state == PREC) { /* precisions may not be negative */
1558 fld_s.prec = -1;
1559 state = OPT; /* prohibit further precision wrangling */
1560 }
1561 continue;
1562
1563 case '+': /* Deal with a plus flag */
1564 if (state == FLAG)
1565 fld_s.flags |= FLAG_PLUS;
1566 continue;
1567
1568 case ' ': /* Deal with a space flag */
1569 if (state == FLAG)
1570 fld_s.flags |= FLAG_SPACE;
1571 continue;
1572
1573 case '#': /* Deal with the so-called "alternate" flag */
1574 if (state == FLAG)
1575 fld_s.flags |= FLAG_ALT;
1576 continue;
1577
1578 case ':': /* Deal with the colon flag */
1579 if (state == FLAG)
1580 fld_s.flags |= FLAG_COLON;
1581 continue;
1582
1583 case '0': /* Deal with a zero flag */
1584 if (state == FLAG) {
1585 fld_s.flags |= FLAG_ZERO;
1586 continue;
1587 }
1588 /*FALLTHROUGH*/
1589 case '1': case '2': case '3': case '4': case '5':
1590 case '6': case '7': case '8': case '9':
1591 if (state == FLAG) /* switch to the WIDTH state if needed? */
1592 state = WIDTH;
1593 else if (state != WIDTH && state != PREC)
1594 continue; /* don't process it any more */
1595
1596 /* convert number */
1597 if (state == WIDTH) {
1598 if (fld_s.width < WIDTH_MAX) /* prevent overflow */
1599 fld_s.width = fld_s.width * 10 + (*fmt - '0');
1600 } else {
1601 if (fld_s.prec < WIDTH_MAX) /* prevent overflow */
1602 fld_s.prec = fld_s.prec * 10 + (*fmt - '0');
1603 }
1604 continue;
1605
1606 case '.': /* We found a '.'; go to precision state */
1607 if (state <= DOT) {
1608 state = PREC;
1609 fld_s.prec = 0;
1610 }
1611 continue;
1612
1613 case '*': /* Grab an argument containing a width or precision */
1614 if (state <= WIDTH && fld_s.width <= 0) {
1615 fld_s.width = (short)va_arg(vp, int); /* Get argument */
1616
1617 state = DOT; /* '.' better be next */
1618
1619 if (fld_s.width < 0) { /* deal with negative width */
1620 fld_s.flags |= FLAG_MINUS;
1621 fld_s.width = -fld_s.width;
1622 }
1623 } else if (state == PREC && fld_s.prec <= 0) {
1624 fld_s.prec = (short)va_arg(vp, int); /* Get argument */
1625
1626 state = OPT; /* No more precision stuff */
1627
1628 if (fld_s.prec < 0) /* deal with negative precision */
1629 fld_s.prec = -1;
1630 }
1631 continue;
1632
1633 case 'h': /* it's a short */
1634 if (state <= OPT) {
1635 state = OPT;
1636 if (fld_s.flags & TYPE_SHORT) /* We support 'hh' */
1637 fld_s.flags |= TYPE_CHAR;
1638 else if (!(fld_s.flags & TYPE_MASK))
1639 fld_s.flags |= TYPE_SHORT;
1640 }
1641 continue;
1642
1643 case 'l': /* it's a long */
1644 if (state <= OPT) {
1645 state = OPT;
1646 if (fld_s.flags & TYPE_LONG) /* We support 'll' */
1647 fld_s.flags |= TYPE_QUAD | TYPE_LONGDOUBLE;
1648 else if (!(fld_s.flags & TYPE_MASK))
1649 fld_s.flags |= TYPE_LONG;
1650 }
1651 continue;
1652
1653 case 'q': case 'L': /* it's a quad or long double */
1654 if (state <= OPT) {
1655 state = OPT;
1656 if (!(fld_s.flags & TYPE_MASK))
1657 fld_s.flags |= TYPE_QUAD | TYPE_LONGDOUBLE;
1658 }
1659 continue;
1660
1661 case 'j': /* it's an intmax_t */
1662 if (state <= OPT) {
1663 state = OPT;
1664 if (!(fld_s.flags & TYPE_MASK))
1665 fld_s.flags |= TYPE_INTMAX;
1666 }
1667 continue;
1668
1669 case 't': /* it's a ptrdiff_t */
1670 if (state <= OPT) {
1671 state = OPT;
1672 if (!(fld_s.flags & TYPE_MASK))
1673 fld_s.flags |= TYPE_PTRDIFF;
1674 }
1675 continue;
1676
1677 case 'z': case 'Z': /* it's a size_t */
1678 if (state <= OPT) {
1679 state = OPT;
1680 if (!(fld_s.flags & TYPE_MASK))
1681 fld_s.flags |= TYPE_SIZE;
1682 }
1683 continue;
1684
1685 case 'T': /* it's a time_t */
1686 if (state <= OPT) {
1687 state = OPT;
1688 if (!(fld_s.flags & TYPE_MASK))
1689 fld_s.flags |= TYPE_TIME;
1690 }
1691 continue;
1692
1693 case 's': /* convert a string */
1694 fld_s.flags &= ~(FLAG_PLUS | FLAG_SPACE | FLAG_ALT | FLAG_ZERO |
1695 FLAG_COLON | TYPE_MASK);
1696 fld_s.flags |= ARG_PTR | CONV_STRING;
1697 break;
1698
1699 case 'd': case 'i':
1700 fld_s.flags &= ~(FLAG_COLON);
1701 fld_s.flags |= ARG_INT | CONV_INT;
1702 break;
1703
1704 case 'X': /* uppercase hexadecimal */
1705 fld_s.flags |= INFO_UPPERCASE;
1706 /*FALLTHROUGH*/
1707 case 'o': case 'x': /* octal or hexadecimal */
1708 if (*fmt == 'o')
1709 fld_s.base = BASE_OCTAL;
1710 else
1711 fld_s.base = BASE_HEX;
1712 /*FALLTHROUGH*/
1713 case 'u': /* Unsigned int */
1714 fld_s.flags &= ~(FLAG_PLUS | FLAG_SPACE | FLAG_COLON);
1715 fld_s.flags |= INFO_UNSIGNED | ARG_INT | CONV_INT;
1716 break;
1717
1718 /* Don't support floating point at this time; it's too complicated */
1719 /* case 'E': case 'G': case 'A': */
1720 /* fld_s.flags |= INFO_UPPERCASE; */
1721 /*FALLTHROUGH*/
1722 /* case 'e': case 'f': case 'g': case 'a': */
1723 /* fld_s.flags |= ARG_FLOAT | CONV_FLOAT; */
1724 /* break; */
1725
1726 case 'c': /* character */
1727 fld_s.flags &= ~(FLAG_PLUS | FLAG_SPACE | FLAG_ALT | FLAG_ZERO |
1728 FLAG_COLON | TYPE_MASK);
1729 fld_s.flags |= INFO_UNSIGNED | ARG_INT | TYPE_CHAR | CONV_CHAR;
1730 fld_s.prec = -1;
1731 break;
1732
1733 case 'p': /* display a pointer */
1734 fld_s.flags &= ~(FLAG_PLUS | FLAG_SPACE | FLAG_COLON | TYPE_MASK);
1735 fld_s.flags |= (FLAG_ALT | FLAG_ZERO | TYPE_POINTER | ARG_PTR |
1736 CONV_INT | INFO_UNSIGNED);
1737 fld_s.prec = (SIZEOF_VOID_P * 2); /* number of characters */
1738 fld_s.base = BASE_HEX;
1739 break;
1740
1741 case 'n': /* write back a character count */
1742 if (fld_s.flags & TYPE_CHAR) /* eg, %hhn */
1743 *((char *)va_arg(vp, int *)) = TOTAL(buf_p);
1744 else if (fld_s.flags & TYPE_SHORT) /* eg, %hn */
1745 *((short *)va_arg(vp, int *)) = TOTAL(buf_p);
1746 else if (fld_s.flags & TYPE_QUAD) /* eg, %qn */
1747 *((int64_t *)va_arg(vp, int64_t *)) = TOTAL(buf_p);
1748 else if (fld_s.flags & TYPE_LONG) /* eg, %ln */
1749 *((long *)va_arg(vp, long *)) = TOTAL(buf_p);
1750 else if (fld_s.flags & TYPE_INTMAX) /* eg, %jn */
1751 *((_large_t *)va_arg(vp, _large_t *)) = TOTAL(buf_p);
1752 else if (fld_s.flags & TYPE_PTRDIFF) /* eg, %tn */
1753 *((ptrdiff_t *)va_arg(vp, ptrdiff_t *)) = TOTAL(buf_p);
1754 else if (fld_s.flags & TYPE_SIZE) /* eg, %zn */
1755 *((size_t *)va_arg(vp, size_t *)) = TOTAL(buf_p);
1756 else if (fld_s.flags & TYPE_TIME) /* eg, %Tn */
1757 *((time_t *)va_arg(vp, time_t *)) = TOTAL(buf_p);
1758 else /* eg, %n */
1759 *((int *)va_arg(vp, int *)) = TOTAL(buf_p);
1760 fld_s.flags = 0; /* no further processing required */
1761 break;
1762
1763 case 'm': /* write out a string describing an errno error */
1764 fld_s.flags &= ~(FLAG_PLUS | FLAG_SPACE | FLAG_ALT | FLAG_ZERO |
1765 FLAG_COLON | TYPE_MASK);
1766 fld_s.flags |= CONV_STRING;
1767 fld_s.value.v_ptr = (void *)strerror(errno);
1768 break;
1769
1770 case 'v': /* here's the infamous %v... */
1771 fld_s.flags &= ~(FLAG_PLUS | FLAG_SPACE | FLAG_ALT | FLAG_ZERO |
1772 FLAG_COLON | TYPE_MASK);
1773 fld_s.flags |= ARG_PTR | CONV_VARARGS;
1774 break;
1775
1776 case 'C': /* convert a client name... */
1777 fld_s.flags &= ~(FLAG_PLUS | FLAG_SPACE | FLAG_ZERO | TYPE_MASK);
1778 fld_s.flags |= ARG_PTR | CONV_CLIENT;
1779 break;
1780
1781 case 'H': /* convert a channel name... */
1782 fld_s.flags &= ~(FLAG_PLUS | FLAG_SPACE | FLAG_ALT | FLAG_ZERO |
1783 FLAG_COLON | TYPE_MASK);
1784 fld_s.flags |= ARG_PTR | CONV_CHANNEL;
1785 break;
1786
1787 default: /* Unsupported, display a message and the entire format */
1788 adds(buf_p, -1, "(Unsupported: %");
1789 adds(buf_p, fmt - fstart + 1, fstart);
1790 addc(buf_p, ')');
1791 fld_s.flags = 0; /* no further processing required */
1792 break;
1793 } /* switch (*fmt) { */
1794
1795 break;
1796 } /* for (; *fmt; fmt++) { */
1797
1798 if (!*fmt) /* hit the end */
1799 break;
1800 else if (!(fld_s.flags & (ARG_MASK | CONV_MASK))) /* is it done? */
1801 continue;
1802
1803 if ((fld_s.flags & ARG_MASK) == ARG_INT) { /* grab an integer argument */
1804 if (fld_s.flags & INFO_UNSIGNED) { /* go direct if unsigned */
1805 if (fld_s.flags & TYPE_CHAR) /* eg, %hhu */
1806 fld_s.value.v_int = (unsigned char)va_arg(vp, unsigned int);
1807 else if (fld_s.flags & TYPE_SHORT) /* eg, %hu */
1808 fld_s.value.v_int = (short)va_arg(vp, unsigned int);
1809 else if (fld_s.flags & TYPE_QUAD) /* eg, %qu */
1810 fld_s.value.v_int = va_arg(vp, uint64_t);
1811 else if (fld_s.flags & TYPE_LONG) /* eg, %lu */
1812 fld_s.value.v_int = va_arg(vp, unsigned long);
1813 else if (fld_s.flags & TYPE_INTMAX) /* eg, %ju */
1814 fld_s.value.v_int = va_arg(vp, _large_t);
1815 else if (fld_s.flags & TYPE_PTRDIFF) /* eg, %tu */
1816 fld_s.value.v_int = va_arg(vp, ptrdiff_t);
1817 else if (fld_s.flags & TYPE_SIZE) /* eg, %zu */
1818 fld_s.value.v_int = va_arg(vp, size_t);
1819 else if (fld_s.flags & TYPE_TIME) /* eg, %Tu */
1820 fld_s.value.v_int = va_arg(vp, time_t);
1821 else if (fld_s.flags & TYPE_POINTER) /* eg, %p */
1822 fld_s.value.v_int = va_arg(vp, _pointer_t);
1823 else /* eg, %u */
1824 fld_s.value.v_int = va_arg(vp, unsigned int);
1825 } else {
1826 _large_t signed_int; /* temp. store the signed integer */
1827
1828 if (fld_s.flags & TYPE_CHAR) /* eg, %hhd */
1829 signed_int = (char)va_arg(vp, unsigned int);
1830 else if (fld_s.flags & TYPE_SHORT) /* eg, %hd */
1831 signed_int = (short)va_arg(vp, unsigned int);
1832 else if (fld_s.flags & TYPE_QUAD) /* eg, %qd */
1833 signed_int = va_arg(vp, int64_t);
1834 else if (fld_s.flags & TYPE_LONG) /* eg, %ld */
1835 signed_int = va_arg(vp, long);
1836 else if (fld_s.flags & TYPE_INTMAX) /* eg, %jd */
1837 signed_int = va_arg(vp, _large_t);
1838 else if (fld_s.flags & TYPE_PTRDIFF) /* eg, %td */
1839 signed_int = va_arg(vp, ptrdiff_t);
1840 else if (fld_s.flags & TYPE_SIZE) /* eg, %zd */
1841 signed_int = va_arg(vp, size_t);
1842 else if (fld_s.flags & TYPE_TIME) /* eg, %Td */
1843 signed_int = va_arg(vp, time_t);
1844 else /* eg, %d */
1845 signed_int = va_arg(vp, int);
1846
1847 if (signed_int < 0) { /* Now figure out if it's negative... */
1848 fld_s.flags |= INFO_NEGATIVE;
1849 fld_s.value.v_int = -signed_int; /* negate safely (I hope) */
1850 } else
1851 fld_s.value.v_int = signed_int;
1852 }
1853 } else if ((fld_s.flags & ARG_MASK) == ARG_FLOAT) { /* extract a float */
1854 if (fld_s.flags & TYPE_LONGDOUBLE) /* eg, %Lf */
1855 fld_s.value.v_float = va_arg(vp, long double);
1856 else /* eg, %f */
1857 fld_s.value.v_float = va_arg(vp, double);
1858 } else if ((fld_s.flags & ARG_MASK) == ARG_PTR) { /* pointer argument */
1859 fld_s.value.v_ptr = va_arg(vp, void *);
1860 }
1861
1862 /* We've eaten the arguments, we have all the information we need for
1863 * the conversion. Time to actually *do* the conversion
1864 */
1865 if ((fld_s.flags & CONV_MASK) == CONV_INT) {
1866 /* convert an integer */
1867 char intbuf[INTBUF_LEN], **table = 0, *tstr;
1868 int ibuf_loc = INTBUF_LEN, ilen, zlen = 0, plen = 0, elen = 0;
1869
1870 if (fld_s.base == BASE_OCTAL) /* select string table to use */
1871 table = octal;
1872 else if (fld_s.base == BASE_DECIMAL)
1873 table = decimal;
1874 else if (fld_s.base == BASE_HEX) { /* have to deal with upper case */
1875 table = (fld_s.flags & INFO_UPPERCASE) ? HEX : hex;
1876 if (fld_s.flags & FLAG_ALT)
1877 elen = 2; /* account for the length of 0x */
1878 }
1879
1880 if (fld_s.prec < 0) { /* default precision is 1 */
1881 if ((fld_s.flags & (FLAG_MINUS | FLAG_ZERO)) == FLAG_ZERO &&
1882 fld_s.width) {
1883 fld_s.prec = fld_s.width - elen;
1884 fld_s.width = 0;
1885 } else
1886 fld_s.prec = 1;
1887 }
1888
1889 /* If there's a sign flag, account for it */
1890 if (fld_s.flags & (FLAG_PLUS | FLAG_SPACE | INFO_NEGATIVE))
1891 elen++;
1892
1893 if (fld_s.base < 0) { /* non-binary base flagged by negative */
1894 fld_s.base = -fld_s.base; /* negate it... */
1895
1896 while (fld_s.value.v_int) { /* and convert it */
1897 tstr = table[fld_s.value.v_int % fld_s.base]; /* which string? */
1898 fld_s.value.v_int /= fld_s.base; /* next value */
1899
1900 ilen = 3; /* if we have to fill in zeros, here's how many */
1901
1902 while (*tstr) { /* add string to intbuf; note growing backwards */
1903 intbuf[--ibuf_loc] = *(tstr++);
1904 ilen--;
1905 }
1906
1907 if (fld_s.value.v_int > 0 && ilen) /* add zeros if needed */
1908 while (ilen--)
1909 intbuf[--ibuf_loc] = '0';
1910 }
1911 } else { /* optimize for powers of 2 */
1912 while (fld_s.value.v_int) { /* which string? */
1913 tstr = table[(fld_s.value.v_int & ((1 << fld_s.base) - 1))];
1914 fld_s.value.v_int >>= fld_s.base; /* next value */
1915
1916 ilen = 3; /* if we have to fill in zeros, here's how many */
1917
1918 while (*tstr) { /* add string to intbuf; note growing backwards */
1919 intbuf[--ibuf_loc] = *(tstr++);
1920 ilen--;
1921 }
1922
1923 if (fld_s.value.v_int > 0 && ilen) /* add zeros if needed */
1924 while (ilen--)
1925 intbuf[--ibuf_loc] = '0';
1926 }
1927 }
1928
1929 ilen = INTBUF_LEN - ibuf_loc; /* how many chars did we add? */
1930
1931 if (fld_s.prec > ilen) /* do we need any leading zeros? */
1932 zlen = fld_s.prec - ilen;
1933
1934 if (fld_s.base == BASE_OCTAL && zlen == 0 && fld_s.flags & FLAG_ALT)
1935 zlen++; /* factor in a leading zero for %#o */
1936
1937 if (fld_s.width > ilen + zlen + elen) /* calculate space padding */
1938 plen = fld_s.width - (ilen + zlen + elen);
1939
1940 if (plen > 0 && !(fld_s.flags & FLAG_MINUS))
1941 do_pad(buf_p, plen, spaces); /* pre-padding */
1942
1943 if (fld_s.flags & INFO_NEGATIVE) /* leading signs */
1944 addc(buf_p, '-');
1945 else if (fld_s.flags & FLAG_PLUS)
1946 addc(buf_p, '+');
1947 else if (fld_s.flags & FLAG_SPACE)
1948 addc(buf_p, ' ');
1949
1950 if ((fld_s.flags & FLAG_ALT) && fld_s.base == BASE_HEX) { /* hex 0x */
1951 addc(buf_p, '0');
1952 addc(buf_p, fld_s.flags & INFO_UPPERCASE ? 'X' : 'x');
1953 }
1954
1955 if (zlen > 0) /* leading zeros */
1956 do_pad(buf_p, zlen, zeros);
1957
1958 adds(buf_p, ilen, intbuf + ibuf_loc); /* add the integer string */
1959
1960 if (plen > 0 && (fld_s.flags & FLAG_MINUS))
1961 do_pad(buf_p, plen, spaces); /* post-padding */
1962
1963 /* Don't support floating point at this time; it's too complicated */
1964 /* } else if ((fld_s.flags & CONV_MASK) == CONV_FLOAT) { */
1965 /* convert a float */
1966 } else if ((fld_s.flags & CONV_MASK) == CONV_CHAR) {
1967 if (fld_s.width > 0 && !(fld_s.flags & FLAG_MINUS))
1968 do_pad(buf_p, fld_s.width - 1, spaces); /* pre-padding */
1969
1970 addc(buf_p, fld_s.value.v_int); /* add the character */
1971
1972 if (fld_s.width > 0 && (fld_s.flags & FLAG_MINUS))
1973 do_pad(buf_p, fld_s.width - 1, spaces); /* post-padding */
1974 } else if ((fld_s.flags & CONV_MASK) == CONV_STRING ||
1975 fld_s.value.v_ptr == 0) { /* spaces or null pointers */
1976 int slen, plen;
1977 char *str = (char*) fld_s.value.v_ptr;
1978
1979 if (!str) /* NULL pointers print "(null)" */
1980 str = "(null)";
1981
1982 slen = my_strnlen(str, fld_s.prec); /* str lengths and pad lengths */
1983 plen = (fld_s.width - slen <= 0 ? 0 : fld_s.width - slen);
1984
1985 if (plen > 0 && !(fld_s.flags & FLAG_MINUS))
1986 do_pad(buf_p, plen, spaces); /* pre-padding */
1987
1988 adds(buf_p, slen, str); /* add the string */
1989
1990 if (plen > 0 && (fld_s.flags & FLAG_MINUS))
1991 do_pad(buf_p, plen, spaces); /* post-padding */
1992 } else if ((fld_s.flags & CONV_MASK) == CONV_VARARGS) {
1993 struct BufData buf_s = BUFDATA_INIT;
1994 struct VarData *vdata = (struct VarData*) fld_s.value.v_ptr;
1995 int plen, tlen;
1996
1997 buf_s.buf = buf_p->buf + buf_p->buf_loc;
1998 buf_s.buf_size = buf_p->buf_size - buf_p->buf_loc;
1999 buf_s.limit = fld_s.prec;
2000
2001 doprintf(dest, &buf_s, vdata->vd_format, vdata->vd_args);
2002
2003 plen = (fld_s.width - buf_s.buf_loc <= 0 ? 0 :
2004 fld_s.width - buf_s.buf_loc);
2005
2006 if (plen > 0) {
2007 if (fld_s.flags & FLAG_MINUS) { /* left aligned... */
2008 buf_p->buf_loc += buf_s.buf_loc; /* remember the modifications */
2009 buf_p->buf_overflow += buf_s.buf_overflow;
2010
2011 do_pad(buf_p, plen, spaces); /* and do the post-padding */
2012 } else { /* right aligned... */
2013 /* Ok, first, see if we'll have *anything* left after padding */
2014 if (plen > buf_s.buf_size) {
2015 /* nope, good, this is easy: everything overflowed buffer */
2016 do_pad(buf_p, plen, spaces);
2017
2018 buf_s.buf_overflow += buf_s.buf_loc; /* update buf counts */
2019 buf_s.buf_loc = 0;
2020 buf_p->buf_overflow += buf_s.buf_overflow;
2021 } else {
2022 /* first figure out how much we're going to save */
2023 tlen = SNP_MIN(buf_s.buf_loc, buf_s.buf_size - plen);
2024
2025 memmove(buf_s.buf + plen, buf_s.buf, tlen); /* save it... */
2026 do_pad(buf_p, plen, spaces); /* add spaces... */
2027
2028 buf_s.buf_overflow += buf_s.buf_loc - tlen; /* update buf counts */
2029 buf_s.buf_loc = tlen;
2030 buf_p->buf_overflow += buf_s.buf_overflow;
2031 buf_p->buf_loc += buf_s.buf_loc;
2032 }
2033 }
2034 } else {
2035 buf_p->buf_loc += buf_s.buf_loc; /* no padding, but remember mods */
2036 buf_p->buf_overflow += buf_s.buf_overflow;
2037 }
2038
2039 vdata->vd_chars = buf_s.buf_loc; /* return relevant data */
2040 vdata->vd_overflow = SNP_MAX(buf_s.buf_overflow, buf_s.overflow);
2041 } else if ((fld_s.flags & CONV_MASK) == CONV_CLIENT) {
2042 struct Client *cptr = (struct Client*) fld_s.value.v_ptr;
2043 const char *str1 = 0, *str2 = 0, *str3 = 0;
2044 int slen1 = 0, slen2 = 0, slen3 = 0, elen = 0, plen = 0;
2045
2046 /* &me is used if it's not a definite server */
2047 if (dest && (IsServer(dest) || IsMe(dest))) {
2048 if (IsServer(cptr) || IsMe(cptr))
2049 str1 = cli_yxx(cptr);
2050 else {
2051 str1 = cli_yxx(cli_user(cptr)->server);
2052 str2 = cli_yxx(cptr);
2053 }
2054 fld_s.flags &= ~(FLAG_ALT | FLAG_COLON);
2055 } else {
2056 str1 = *cli_name(cptr) ? cli_name(cptr) : "*";
2057 if (!IsServer(cptr) && !IsMe(cptr) && fld_s.flags & FLAG_ALT) {
2058 assert(0 != cli_user(cptr));
2059 assert(0 != *(cli_name(cptr)));
2060 str2 = cli_user(cptr)->username;
2061 str3 = cli_user(cptr)->host;
2062 } else
2063 fld_s.flags &= ~FLAG_ALT;
2064 }
2065
2066 if (fld_s.flags & FLAG_COLON)
2067 elen++; /* account for : */
2068
2069 slen1 = my_strnlen(str1, fld_s.prec < 0 ? -1 : fld_s.prec - elen);
2070 if (fld_s.flags & FLAG_ALT)
2071 elen++; /* account for ! */
2072 if (str2 && (fld_s.prec < 0 || fld_s.prec - (slen1 + elen) > 0))
2073 slen2 = my_strnlen(str2, fld_s.prec < 0 ? -1 : fld_s.prec -
2074 (slen1 + elen));
2075 if (fld_s.flags & FLAG_ALT)
2076 elen++; /* account for @ */
2077 if (str3 && (fld_s.prec < 0 || fld_s.prec - (slen1 + slen2 + elen) > 0))
2078 slen3 = my_strnlen(str3, fld_s.prec < 0 ? -1 : fld_s.prec -
2079 (slen1 + slen2 + elen));
2080 plen = (fld_s.width - (slen1 + slen2 + slen3 + elen) <= 0 ? 0 :
2081 fld_s.width - (slen1 + slen2 + slen3 + elen));
2082
2083 if (plen > 0 && !(fld_s.flags & FLAG_MINUS))
2084 do_pad(buf_p, plen, spaces); /* pre-padding */
2085
2086 if (fld_s.flags & FLAG_COLON)
2087 addc(buf_p, ':');
2088 adds(buf_p, slen1, str1);
2089 if (fld_s.flags & FLAG_ALT)
2090 addc(buf_p, '!');
2091 if (str2)
2092 adds(buf_p, slen2, str2);
2093 if (fld_s.flags & FLAG_ALT)
2094 addc(buf_p, '@');
2095 if (str3)
2096 adds(buf_p, slen3, str3);
2097
2098 if (plen > 0 && (fld_s.flags & FLAG_MINUS))
2099 do_pad(buf_p, plen, spaces); /* post-padding */
2100 } else if ((fld_s.flags & CONV_MASK) == CONV_CHANNEL) {
2101 struct Channel *chan = (struct Channel *)fld_s.value.v_ptr;
2102 char *str = chan->chname;
2103 int slen, plen;
2104
2105 slen = my_strnlen(str, fld_s.prec); /* str lengths and pad lengths */
2106 plen = (fld_s.width - slen <= 0 ? 0 : fld_s.width - slen);
2107
2108 if (plen > 0 && !(fld_s.flags & FLAG_MINUS))
2109 do_pad(buf_p, plen, spaces); /* pre-padding */
2110
2111 adds(buf_p, slen, str); /* add the string */
2112
2113 if (plen > 0 && (fld_s.flags & FLAG_MINUS))
2114 do_pad(buf_p, plen, spaces); /* post-padding */
2115 }
2116 } /* for (; *fmt; fmt++) { */
2117 }
2118
2119 /* ircd_snprintf() has a big Doxygen comment in the header file. */
2120 int
2121 ircd_snprintf(struct Client *dest, char *buf, size_t buf_len,
2122 const char *format, ...)
2123 {
2124 struct BufData buf_s = BUFDATA_INIT;
2125 va_list args;
2126
2127 if (!format)
2128 return 0;
2129
2130 buf_s.buf = buf; /* initialize buffer settings */
2131 buf_s.buf_size = buf_len - 1;
2132 buf_s.limit = -1;
2133
2134 va_start(args, format);
2135 doprintf(dest, &buf_s, format, args); /* fill the buffer */
2136 va_end(args);
2137
2138 buf_s.buf[buf_s.buf_loc] = '\0'; /* terminate buffer */
2139
2140 return TOTAL(&buf_s);
2141 }
2142
2143 /** Like ircd_snprintf() but with a va_list argument list.
2144 * @param[in] dest Client receiving of message.
2145 * @param[out] buf Output buffer for formatted message.
2146 * @param[in] buf_len Number of bytes that can be written to \a buf.
2147 * @param[in] format Format string for message.
2148 * @param[in] args Variable-length argument list for format string.
2149 * @return Number of bytes that would be written to \a buf without truncation.
2150 */
2151 int
2152 ircd_vsnprintf(struct Client *dest, char *buf, size_t buf_len,
2153 const char *format, va_list args)
2154 {
2155 struct BufData buf_s = BUFDATA_INIT;
2156
2157 if (!format)
2158 return 0;
2159
2160 buf_s.buf = buf; /* initialize buffer settings */
2161 buf_s.buf_size = buf_len - 1;
2162 buf_s.limit = -1;
2163
2164 doprintf(dest, &buf_s, format, args); /* fill the buffer */
2165
2166 buf_s.buf[buf_s.buf_loc] = '\0'; /* terminate buffer */
2167
2168 return TOTAL(&buf_s);
2169 }