added demo of signal/uid handling feature
[tridge/junkcode.git] / unicode_map.c
1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <sys/time.h>
4
5 #define smb_ucs2_t unsigned short
6
7 typedef struct {
8         smb_ucs2_t lower;
9         smb_ucs2_t upper;
10         unsigned char flags;
11 } smb_unicode_table_t;
12
13 #define UNI_UPPER    0x1
14 #define UNI_LOWER    0x2
15 #define UNI_DIGIT    0x4
16 #define UNI_XDIGIT   0x8
17 #define UNI_SPACE    0x10
18
19 static smb_unicode_table_t map_table[] = {
20 #include "unicode_map_table.h"
21 };
22
23
24 struct map_range {
25         unsigned short start;
26         unsigned short end;
27         signed short lower_ofs;
28         signed short upper_ofs;
29         unsigned char flags;
30 };
31
32 static struct map_range range[0x10000];
33 static int map_range_size;
34
35 static unsigned short map_range_find(smb_ucs2_t val)
36 {
37         unsigned low = 0, high = map_range_size-1;
38         unsigned t;
39
40         while (low != high) {
41                 t = (1+low+high)>>1;
42                 if (range[t].start > val) {
43                         high = t-1;
44                 } else {
45                         low = t;
46                 }
47         }
48
49         return low;
50 }
51
52 #define map_range_flags(val) (range[map_range_find(val)].flags)
53 #define map_range_lower(val) (range[map_range_find(val)].lower_ofs+(val))
54 #define map_range_upper(val) (range[map_range_find(val)].upper_ofs+(val))
55
56 static void build_map_range(void)
57 {
58         int i, n;
59
60         n = 0;
61         range[n].start = 0;
62         range[n].lower_ofs = map_table[0].lower;
63         range[n].upper_ofs = map_table[0].upper;
64         range[n].flags =     map_table[0].flags;
65
66         for (i=1;i<0x10000;i++) {
67                 if (range[n].lower_ofs + i == map_table[i].lower &&
68                     range[n].upper_ofs + i == map_table[i].upper &&
69                     range[n].flags         == map_table[i].flags) continue;
70
71                 range[n].end = i-1;
72                 n++;
73                 range[n].start = i;
74                 range[n].lower_ofs = map_table[i].lower - i;
75                 range[n].upper_ofs = map_table[i].upper - i;
76                 range[n].flags =     map_table[i].flags;
77         }
78         range[n].end = i-1;
79         map_range_size = n+1;
80         printf("map_range_size = %d\n", map_range_size);
81 }
82
83
84 static void test_map_range(void)
85 {
86         int i;
87
88         for (i=0;i<0x10000;i++) {
89                 smb_ucs2_t v = (smb_ucs2_t)i;
90                 if (map_range_flags(v) != map_table[v].flags) {
91                         printf("flags failed at %d\n", i);
92                         break;
93                 }
94                 if (map_range_upper(v) != map_table[v].upper) {
95                         printf("upper failed at %d\n", i);
96                         break;
97                 }
98                 if (map_range_lower(v) != map_table[v].lower) {
99                         printf("lower failed at %d\n", i);
100                         break;
101                 }
102         }
103         
104 }
105
106
107 static struct timeval tp1,tp2;
108
109 static void start_timer()
110 {
111         gettimeofday(&tp1,NULL);
112 }
113
114 static double end_timer()
115 {
116         gettimeofday(&tp2,NULL);
117         return((tp2.tv_sec - tp1.tv_sec) + 
118                (tp2.tv_usec - tp1.tv_usec)*1.0e-6);
119 }
120
121 static void speed_test(void)
122 {
123         #define TEST_SIZE (1000*1000)
124         smb_ucs2_t testbuf[TEST_SIZE];
125         int i;
126         unsigned sum;
127
128         srandom(time(NULL));
129
130         for (i=0;i<TEST_SIZE;i++) {
131                 testbuf[i] = random();
132         }
133
134         sum = 0;
135
136         for (i=0;i<TEST_SIZE;i++) {
137                 smb_ucs2_t v = testbuf[i];
138                 sum += map_table[v].flags;
139         }       
140         start_timer();
141         for (i=0;i<TEST_SIZE;i++) {
142                 smb_ucs2_t v = testbuf[i];
143                 sum += map_table[v].flags;
144         }       
145         printf("table took %g secs (sum=%d)\n", end_timer(), sum);
146
147         sum = 0;
148
149         for (i=0;i<TEST_SIZE;i++) {
150                 smb_ucs2_t v = testbuf[i];
151                 sum += map_range_flags(v);
152         }       
153         start_timer();
154         for (i=0;i<TEST_SIZE;i++) {
155                 smb_ucs2_t v = testbuf[i];
156                 sum += map_range_flags(v);
157         }       
158         printf("range took %g secs (sum=%d)\n", end_timer(), sum);
159 }
160
161 main()
162 {
163         build_map_range();
164         test_map_range();
165         speed_test();
166 }