tune.c (6280B)
1 #include <u.h> 2 #include <libc.h> 3 #include <bio.h> 4 #include "hdr.h" 5 #include "conv.h" 6 7 typedef struct Tmap Tmap; 8 struct Tmap 9 { 10 Rune u; 11 Rune t; 12 }; 13 14 static Tmap t1[] = 15 { 16 {0x0b85/*அ*/, 0xe201/**/}, 17 {0x0b86/*ஆ*/, 0xe202/**/}, 18 {0x0b87/*இ*/, 0xe203/**/}, 19 {0x0b88/*ஈ*/, 0xe204/**/}, 20 {0x0b89/*உ*/, 0xe205/**/}, 21 {0x0b8a/*ஊ*/, 0xe206/**/}, 22 {0x0b8e/*எ*/, 0xe207/**/}, 23 {0x0b8f/*ஏ*/, 0xe208/**/}, 24 {0x0b90/*ஐ*/, 0xe209/**/}, 25 {0x0b92/*ஒ*/, 0xe20a/**/}, 26 {0x0b93/*ஓ*/, 0xe20b/**/}, 27 {0x0b94/*ஔ*/, 0xe20c/**/}, 28 {0x0b83/*ஃ*/, 0xe20d/**/} 29 }; 30 31 static Rune t2[] = 32 { 33 0x0bcd/*்*/, 34 0x0bcd/*்*/, // filler 35 0x0bbe/*ா*/, 36 0x0bbf/*ி*/, 37 0x0bc0/*ீ*/, 38 0x0bc1/*ு*/, 39 0x0bc2/*ூ*/, 40 0x0bc6/*ெ*/, 41 0x0bc7/*ே*/, 42 0x0bc8/*ை*/, 43 0x0bca/*ொ*/, 44 0x0bcb/*ோ*/, 45 0x0bcc/*ௌ*/ 46 }; 47 48 static Tmap t3[] = 49 { 50 {0x0b95/*க*/, 0xe211/**/}, 51 {0x0b99/*ங*/, 0xe221/**/}, 52 {0x0b9a/*ச*/, 0xe231/**/}, 53 {0x0b9c/*ஜ*/, 0xe331/**/}, 54 {0x0b9e/*ஞ*/, 0xe241/**/}, 55 {0x0b9f/*ட*/, 0xe251/**/}, 56 {0x0ba3/*ண*/, 0xe261/**/}, 57 {0x0ba4/*த*/, 0xe271/**/}, 58 {0x0ba8/*ந*/, 0xe281/**/}, 59 {0x0ba9/*ன*/, 0xe321/**/}, 60 {0x0baa/*ப*/, 0xe291/**/}, 61 {0x0bae/*ம*/, 0xe2a1/**/}, 62 {0x0baf/*ய*/, 0xe2b1/**/}, 63 {0x0bb0/*ர*/, 0xe2c1/**/}, 64 {0x0bb1/*ற*/, 0xe311/**/}, 65 {0x0bb2/*ல*/, 0xe2d1/**/}, 66 {0x0bb3/*ள*/, 0xe301/**/}, 67 {0x0bb4/*ழ*/, 0xe2f1/**/}, 68 {0x0bb5/*வ*/, 0xe2e1/**/}, 69 {0x0bb6/*ஶ*/, 0xe341/**/}, 70 {0x0bb7/*ஷ*/, 0xe351/**/}, 71 {0x0bb8/*ஸ*/, 0xe361/**/}, 72 {0x0bb9/*ஹ*/, 0xe371/**/} 73 }; 74 75 static Rune 76 findbytune(Tmap *tab, int size, Rune t) 77 { 78 int i; 79 80 for(i = 0; i < size; i++) 81 if(tab[i].t == t) 82 return tab[i].u; 83 return Runeerror; 84 } 85 86 static Rune 87 findbyuni(Tmap *tab, int size, Rune u) 88 { 89 int i; 90 91 for(i = 0; i < size; i++) 92 if(tab[i].u == u) 93 return tab[i].t; 94 return Runeerror; 95 } 96 97 static int 98 findindex(Rune *rstr, int size, Rune r) 99 { 100 int i; 101 102 for(i = 0; i < size; i++) 103 if(rstr[i] == r) 104 return i; 105 return -1; 106 } 107 108 void 109 tune_in(int fd, long *x, struct convert *out) 110 { 111 Biobuf b; 112 Rune rbuf[N]; 113 Rune *r, *er, tr; 114 int c, i; 115 116 USED(x); 117 r = rbuf; 118 er = rbuf+N-3; 119 Binit(&b, fd, OREAD); 120 while((c = Bgetrune(&b)) != Beof){ 121 ninput += b.runesize; 122 if(r >= er){ 123 OUT(out, rbuf, r-rbuf); 124 r = rbuf; 125 } 126 if(c>=0xe210/**/ && c <= 0xe38c/**/ && (i = c%16) < nelem(t2)){ 127 if(c >= 0xe380/**/){ 128 *r++ = 0x0b95/*க*/; 129 *r++ = 0x0bcd/*்*/; 130 *r++ = 0x0bb7/*ஷ*/; 131 }else 132 *r++ = findbytune(t3, nelem(t3), c-i+1); 133 if(i != 1) 134 *r++ = t2[i]; 135 }else if((tr = findbytune(t1, nelem(t1), c)) != Runeerror) 136 *r++ = tr; 137 else switch(c){ 138 case 0xe3d0/**/: 139 *r++ = 0x0ba3/*ண*/; *r++ = 0x0bbe/*ா*/; 140 break; 141 case 0xe3d1/**/: 142 *r++ = 0x0bb1/*ற*/; *r++ = 0x0bbe/*ா*/; 143 break; 144 case 0xe3d2/**/: 145 *r++ = 0x0ba9/*ன*/; *r++ = 0x0bbe/*ா*/; 146 break; 147 case 0xe3d4/**/: 148 *r++ = 0x0ba3/*ண*/; *r++ = 0x0bc8/*ை*/; 149 break; 150 case 0xe3d5/**/: 151 *r++ = 0x0bb2/*ல*/; *r++ = 0x0bc8/*ை*/; 152 break; 153 case 0xe3d6/**/: 154 *r++ = 0x0bb3/*ள*/; *r++ = 0x0bc8/*ை*/; 155 break; 156 case 0xe3d7/**/: 157 *r++ = 0x0ba9/*ன*/; *r++ = 0x0bc8/*ை*/; 158 break; 159 case 0xe38d/**/: 160 *r++ = 0x0bb6/*ஶ*/; *r++ = 0x0bcd/*்*/; *r++ = 0x0bb0/*ர*/; *r++ = 0x0bc0/*ீ*/; 161 break; 162 default: 163 if(c >= 0xe200 && c <= 0xe3ff){ 164 if(squawk) 165 EPR "%s: rune 0x%x not in output cs\n", argv0, c); 166 nerrors++; 167 if(clean) 168 break; 169 c = BADMAP; 170 } 171 *r++ = c; 172 break; 173 } 174 } 175 if(r > rbuf) 176 OUT(out, rbuf, r-rbuf); 177 OUT(out, rbuf, 0); 178 } 179 180 void 181 tune_out(Rune *r, int n, long *x) 182 { 183 static int state = 0; 184 static Rune lastr; 185 Rune *er, tr, rr; 186 char *p; 187 int i; 188 189 USED(x); 190 nrunes += n; 191 er = r+n; 192 for(p = obuf; r < er; r++){ 193 switch(state){ 194 case 0: 195 case0: 196 if((tr = findbyuni(t3, nelem(t3), *r)) != Runeerror){ 197 lastr = tr; 198 state = 1; 199 }else if(*r == 0x0b92/*ஒ*/){ 200 lastr = 0xe20a/**/; 201 state = 3; 202 }else if((tr = findbyuni(t1, nelem(t1), *r)) != Runeerror) 203 p += runetochar(p, &tr); 204 else 205 p += runetochar(p, r); 206 break; 207 case 1: 208 case1: 209 if((i = findindex(t2, nelem(t2), *r)) != -1){ 210 if(lastr && lastr != Runeerror) 211 lastr += i-1; 212 if(*r ==0x0bc6/*ெ*/) 213 state = 5; 214 else if(*r ==0x0bc7/*ே*/) 215 state = 4; 216 else if(lastr == 0xe210/**/) 217 state = 2; 218 else if(lastr == 0xe340/**/) 219 state = 6; 220 else{ 221 if(lastr) 222 p += runetochar(p, &lastr); 223 state = 0; 224 } 225 }else if(lastr && lastr != Runeerror && (*r == 0x00b2/*²*/ || *r == 0x00b3/*³*/ || *r == 0x2074/*⁴*/)){ 226 if(squawk) 227 EPR "%s: character <U+%.4X, U+%.4X> not in output cs\n", argv0, lastr, *r); 228 lastr = clean ? 0 : Runeerror; 229 nerrors++; 230 }else{ 231 if(lastr) 232 p += runetochar(p, &lastr); 233 state = 0; 234 goto case0; 235 } 236 break; 237 case 2: 238 if(*r == 0x0bb7/*ஷ*/){ 239 lastr = 0xe381/**/; 240 state = 1; 241 break; 242 } 243 p += runetochar(p, &lastr); 244 state = 0; 245 goto case0; 246 case 3: 247 state = 0; 248 if(*r == 0x0bd7/*ௗ*/){ 249 rr = 0xe20c/**/; 250 p += runetochar(p, &rr); 251 break; 252 } 253 p += runetochar(p, &lastr); 254 goto case0; 255 case 4: 256 state = 0; 257 if(*r == 0x0bbe/*ா*/){ 258 if(lastr){ 259 if(lastr != Runeerror) 260 lastr += 3; 261 p += runetochar(p, &lastr); 262 } 263 break; 264 } 265 if(lastr) 266 p += runetochar(p, &lastr); 267 goto case0; 268 case 5: 269 state = 0; 270 if(*r == 0x0bbe/*ா*/ || *r == 0x0bd7/*ௗ*/){ 271 if(lastr){ 272 if(lastr != Runeerror) 273 lastr += *r == 0x0bbe/*ா*/ ? 3 : 5; 274 p += runetochar(p, &lastr); 275 } 276 break; 277 } 278 if(lastr) 279 p += runetochar(p, &lastr); 280 goto case0; 281 case 6: 282 if(*r == 0x0bb0/*ர*/){ 283 state = 7; 284 break; 285 } 286 p += runetochar(p, &lastr); 287 state = 0; 288 goto case0; 289 case 7: 290 if(*r == 0x0bc0/*ீ*/){ 291 rr = 0xe38d/**/; 292 p += runetochar(p, &rr); 293 state = 0; 294 break; 295 } 296 p += runetochar(p, &lastr); 297 lastr = 0xe2c1/**/; 298 state = 1; 299 goto case1; 300 } 301 } 302 if(n == 0 && state != 0){ 303 if(lastr) 304 p += runetochar(p, &lastr); 305 state = 0; 306 } 307 noutput += p-obuf; 308 write(1, obuf, p-obuf); 309 }