4 typedef struct PCB /* Control block controlling specification parse */
6 char *base; /* start of specification */
7 char *current; /* current parse point */
8 long last; /* last Rune returned */
9 long final; /* final Rune in a span */
12 uchar bits[] = { 1, 2, 4, 8, 16, 32, 64, 128 };
14 #define SETBIT(a, c) ((a)[(c)/8] |= bits[(c)&07])
15 #define CLEARBIT(a,c) ((a)[(c)/8] &= ~bits[(c)&07])
16 #define BITSET(a,c) ((a)[(c)/8] & bits[(c)&07])
18 #define MAXRUNE 0xFFFF
20 uchar f[(MAXRUNE+1)/8];
21 uchar t[(MAXRUNE+1)/8];
31 void complement(void);
36 char *getrune(char*, Rune*);
37 void Pinit(Pcb*, char*);
39 int readrune(int, long*);
41 void writerune(int, Rune);
46 fprint(2, "usage: %s [-cds] [string1 [string2]]\n", argv0);
51 main(int argc, char **argv)
54 case 's': sflag++; break;
55 case 'd': dflag++; break;
56 case 'c': cflag++; break;
60 Pinit(&pfrom, argv[0]);
66 if ((sflag && argc != 2) || (!sflag && argc != 1))
85 memset((char *) f, 0xff, sizeof f);
86 while ((c = canon(&pfrom)) >= 0)
89 while ((c = canon(&pfrom)) >= 0)
93 while ((c = canon(&pto)) >= 0)
98 while (readrune(0, &c) > 0) {
99 if(!BITSET(f, c) && (c != last || !BITSET(t,c))) {
101 writerune(1, (Rune) c);
112 long from, to, lastc, high;
116 while ((from = canon(&pfrom)) >= 0) {
117 if (from > high) high = from;
120 while ((to = canon(&pto)) > 0) {
121 if (to > high) high = to;
125 if ((p = (Rune *) malloc((high+1)*sizeof(Rune))) == 0)
126 sysfatal("no memory");
127 for (i = 0; i <= high; i++){
129 if ((to = canon(&pto)) < 0)
138 while (readrune(0, &from) > 0) {
143 if (from != lastc || !BITSET(t,from)) {
145 writerune(1, (Rune) from);
150 while (readrune(0, &from) > 0){
155 writerune(1, (Rune) from);
166 long from, to, lastc, high;
170 while ((from = canon(&pfrom)) >= 0)
171 if (from > high) high = from;
173 if ((p = (Rune *) malloc((high+1)*sizeof(Rune))) == 0)
174 sysfatal("no memory");
175 for (i = 0; i <= high; i++)
177 while ((from = canon(&pfrom)) >= 0) {
178 if ((to = canon(&pto)) < 0)
181 if (BITSET(f,from) && p[from] != to)
182 sysfatal("ambiguous translation");
187 while ((to = canon(&pto)) >= 0) {
192 while (readrune(0, &from) > 0) {
195 if (from != lastc || !BITSET(t,from)) {
197 writerune(1, (Rune) from);
202 while (readrune(0, &from) > 0) {
205 writerune(1, (Rune) from);
212 readrune(int fd, long *rp)
217 static char buf[4096];
224 memcpy(buf, buf+j, n-j);
226 n = read(fd, &buf[i], sizeof(buf)-i);
228 sysfatal("read error: %r");
235 if (fullrune(&buf[j], i-j))
238 chartorune(&r, &buf[j]);
244 writerune(int fd, Rune r)
251 n = runetochar(buf, (Rune*)&r);
252 if (wptr+n >= wbuf+sizeof(wbuf))
254 memcpy(wptr, buf, n);
261 if (wptr && wptr > wbuf)
262 if (write(fd, wbuf, wptr-wbuf) != wptr-wbuf)
263 sysfatal("write error: %r");
268 getrune(char *s, Rune *rp)
274 s += chartorune(rp, s);
275 if((r = *rp) == '\\' && *s){
279 for (i = 0; i < 4; i++) {
281 s += chartorune(&r, s);
282 if ('0' <= r && r <= '9')
284 else if ('a' <= r && r <= 'f')
285 n = 16*n + r - 'a' + 10;
286 else if ('A' <= r && r <= 'F')
287 n = 16*n + r - 'A' + 10;
296 for(i = 0; i < 3; i++) {
298 s += chartorune(&r, s);
299 if('0' <= r && r <= '7')
312 sysfatal("character > 0377");
325 if (p->last < p->final)
329 if (*p->current == '\0')
331 if(*p->current == '-' && p->last >= 0 && p->current[1]){
332 p->current = getrune(p->current+1, &r);
334 sysfatal("invalid range specification");
340 p->current = getrune(p->current, &r);
346 Pinit(Pcb *p, char *cp)
348 p->current = p->base = cp;
349 p->last = p->final = -1;
354 p->current = p->base;
355 p->last = p->final = -1;