Subversion Repositories planix.SVN

Rev

Rev 2 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 - 1
#ifdef	PLAN9
2
#include	<u.h>
3
#include	<libc.h>
4
#include	<bio.h>
5
#else
6
#include	<stdio.h>
7
#include	<unistd.h>
8
#include	"plan9.h"
9
#endif
10
#include	"hdr.h"
11
#include	"conv.h"
12
#include	"ksc.h"
13
 
14
/*
15
	contributed by kuro@vodka.Eng.Sun.COM (Teruhiko Kurosaka)
16
*/
17
 
18
/*
19
	a state machine for interpreting shift-ksc.
20
*/
21
 
22
#define	SS2	0x8e
23
#define	SS3	0x8f
24
/*
25
 * Convert EUC in Koran locale to Unicode.
26
 * Only codeset 0 and 1 are used.
27
 */
28
void
29
ukscproc(int c, Rune **r, long input_loc)
30
{
31
	static enum { init, cs1last /*, cs2, cs3first, cs3last*/} state = init;
32
	static int korean646 = 1; /* fixed to 1 for now. */
33
	static int lastc;
34
	int n;
35
	long l;
36
 
37
	switch(state)
38
	{
39
	case init:
40
		if (c < 0){
41
			return;
42
		}else if (c < 128){
43
			if(korean646 && (c=='\\')){
44
				emit(0x20A9);
45
			} else {
46
				emit(c);
47
			}
48
/*		}else if (c==SS2){
49
			state = cs2;
50
		}else if (c==SS3){
51
			state = cs3first;
52
 */		}else{
53
			lastc = c;
54
			state = cs1last;
55
		}
56
		return;
57
 
58
	case cs1last: /* 2nd byte of codeset 1 (KSC 5601) */
59
		if(c < 0){
60
			if(squawk)
61
				EPR "%s: unexpected EOF in %s\n", argv0, file);
62
			c = 0x21 | (lastc&0x80);
63
		}
64
		n = ((lastc&0x7f)-33)*94 + (c&0x7f)-33;
65
 		if((n >= ksc5601max) || ((l = tabksc5601[n]) < 0)){
66
			nerrors++;
67
			if(squawk)
68
				EPR "%s: unknown ksc5601 %d (from 0x%x,0x%x) near byte %ld in %s\n", argv0, n, lastc, c, input_loc, file);
69
			if(!clean)
70
				emit(BADMAP);
71
		} else {
72
			emit(l);
73
		}
74
		state = init;
75
		return;
76
	default:
77
		if(squawk)
78
			EPR "%s: ukscproc: unknown state %d\n",
79
				argv0, init);
80
	}
81
}
82
 
83
void
84
uksc_in(int fd, long *notused, struct convert *out)
85
{
86
	Rune ob[N];
87
	Rune *r, *re;
88
	uchar ibuf[N];
89
	int n, i;
90
	long nin;
91
 
92
	USED(notused);
93
	r = ob;
94
	re = ob+N-3;
95
	nin = 0;
96
	while((n = read(fd, ibuf, sizeof ibuf)) > 0){
97
		for(i = 0; i < n; i++){
98
			ukscproc(ibuf[i], &r, nin++);
99
			if(r >= re){
100
				OUT(out, ob, r-ob);
101
				r = ob;
102
			}
103
		}
104
		if(r > ob){
105
			OUT(out, ob, r-ob);
106
			r = ob;
107
		}
108
	}
109
	ukscproc(-1, &r, nin);
110
	if(r > ob)
111
		OUT(out, ob, r-ob);
112
	OUT(out, ob, 0);
113
}
114
 
115
void
116
uksc_out(Rune *base, int n, long *notused)
117
{
118
	char *p;
119
	int i;
120
	Rune r;
121
	long l;
122
	static int first = 1;
123
 
124
	USED(notused);
125
	if(first){
126
		first = 0;
127
		for(i = 0; i < NRUNE; i++)
128
			tab[i] = -1;
129
		for(i = 0; i < ksc5601max; i++)
130
			if((l = tabksc5601[i]) != -1){
131
				if(l < 0)
132
					tab[-l] = i;
133
				else
134
					tab[l] = i;
135
			}
136
	}
137
	nrunes += n;
138
	p = obuf;
139
	for(i = 0; i < n; i++){
140
		r = base[i];
141
		if(r < 128)
142
			*p++ = r;
143
		else {
144
			if(tab[r] != -1){
145
				*p++ = 0x80 | (tab[r]/94 + 0x21);
146
				*p++ = 0x80 | (tab[r]%94 + 0x21);
147
				continue;
148
			}
149
			if(squawk)
150
				EPR "%s: rune 0x%x not in output cs\n", argv0, r);
151
			nerrors++;
152
			if(clean)
153
				continue;
154
			*p++ = BYTEBADMAP;
155
		}
156
	}
157
	noutput += p-obuf;
158
	if(p > obuf)
159
		write(1, obuf, p-obuf);
160
}
161