Annotation of OpenXM/src/kan96xx/Kan/scanner.c, Revision 1.10
1.10 ! takayama 1: /*$OpenXM: OpenXM/src/kan96xx/Kan/scanner.c,v 1.9 2005/07/18 10:55:16 takayama Exp $*/
1.1 maekawa 2: /* scanner.c (SM StackMachine) */
3: /* export: struct tokens getokenSM(actionType kind,char *str);
4: scanner.c is used to get tokens from streams.
5: files: none
6: */
7: #include <stdio.h>
1.8 ohara 8: #include <stdlib.h>
9: #include <string.h>
1.1 maekawa 10: #include "datatype.h"
11: #include "stackm.h"
12: struct tokens lookupTokens(struct tokens t);
13: int isLiteral(char *s);
14: struct object lookupLiteralString(char *s);
15: char *getLOAD_SM1_PATH();
16: /**************** defined in stackm.h ****************************
17: typedef enum {INIT,GET,PUT,OPEN} actionType;
18:
19: struct tokens{
20: char *token;
21: int kind;
22: };
23:
24:
25: #define ID 2
26: #define DOLLAR 3 strings enclosed by dollar sign
27: #define EXECUTABLE_STRING 4 strings enclosed by {}
28: #define EXECUTABLE_ARRAY 8 Don't set it in this file.
29: ******************************************************************/
30:
31:
32: /******* declaration-part of lexical analizer ********************/
33: /* #define mygetchar() getSM() */
34: /* to use getSM() ( input from StringSM ),
35: setup StringSM;
36: getokenSM(INIT);
37: */
38: /* to use getchar(),
39: getokenSM(INIT);
40: */
41:
42:
43:
1.3 takayama 44: FILE *BaseFp = NULL; /* Initialized to stdin in stackmachine_init().
45: file pointer of the first file. */
1.1 maekawa 46:
47: int EchoInScanner = 0; /* echo in scanner */
48:
49: #define BUF0LIMIT 20000
50: static char *StringSM;
51: static int StrpSM = 0;
52: static char BufSMorg[BUF0LIMIT];
53: static char *BufSM = BufSMorg;
54: static int Buf0limit = BUF0LIMIT;
55: static int ExistSM = 0;
56: static int TypeSM = ID;
57:
58: #define FILESTACK_LIMIT 10
59: static FILE * Cfp; /* current input file pointer */
60: static FILE * FileStack[FILESTACK_LIMIT];
61: static int FileStackP = 0;
62: /**************** end of declaration part of lexical analizer ******/
63:
64: static int getSM();
65: static putSM();
66: static struct tokens flushSM();
67: static isSpaceSM();
68: static isDollarSM();
69: static isBraceSM();
70: static isKakkoSM();
71: static isSymbolSM();
72: static mygetchar();
73: static myungetchar();
74:
1.9 takayama 75: int ScannerWhich = 0;
76: unsigned char ScannerBuf[SCANNERBUF_SIZE];
77: int ScannerPt = 0;
1.1 maekawa 78:
79: /*
80: static mygetchar()
81: {
1.9 takayama 82:
1.1 maekawa 83: return( getc(Cfp) );
84: }
85: */
86:
87: static mygetchar()
88: { int c;
1.9 takayama 89: c = getc(Cfp);
90: if (c > 0) { /* ungetchar is ignored */
91: ScannerPt++; if (ScannerPt >= SCANNERBUF_SIZE) ScannerPt = 0;
92: ScannerBuf[ScannerPt] = c;
93: }
1.4 takayama 94: if (EchoInScanner) {
95: if (c==EOF) {
1.10 ! takayama 96: printf("\n%% EOF of file %p\n",Cfp);
1.4 takayama 97: }else{
98: printf("%c",c);
99: }
100: return( c );
101: }else{
1.9 takayama 102: return( c );
1.4 takayama 103: }
1.1 maekawa 104: }
105:
106:
107: static myungetchar(c)
1.4 takayama 108: int c;
1.1 maekawa 109: {
110: return( ungetc(c,Cfp) );
111: }
112:
113: /**************** code part of lexical analizer ********************/
114: static int getSM()
1.4 takayama 115: /* get a letter from StringSM */
1.1 maekawa 116: {
117: int c;
1.6 takayama 118:
119: if ((StrpSM > 0) && (StringSM[StrpSM] == ',') && (StringSM[StrpSM-1] == ',')) { int i;
120: fprintf(stderr,"Warning: ,, is found.");
121: for (i=(StrpSM-30>0?StrpSM-30:0); i<=StrpSM; i++) {
122: fprintf(stderr,"%c",StringSM[i]);
123: }
124: fprintf(stderr,"\n");
125: }
126:
1.1 maekawa 127: c = StringSM[StrpSM++];
128: if (c == '\0') {
129: StrpSM--;return(EOF);
130: } else return(c);
131: }
132:
133: static putSM(c)
1.4 takayama 134: int c;
135: /* put a letter on BufSM */
1.1 maekawa 136: {
137: char *new; int i;
138: BufSM[ExistSM++] = ((c=='\n')? ' ' : c);
139: if (ExistSM >= Buf0limit-1) {
140: new = (char *) sGC_malloc(sizeof(char *)*Buf0limit*2) ;
141: if (new == (char *)NULL) {
142: fprintf(stderr,"No more memory in parserpass0.c\n");
143: exit(18);
144: }
145: fprintf(stderr,"\nSystem Message: Increasing BufSM to %d in scanner.c\n",Buf0limit*2);
146: for (i=0; i<Buf0limit; i++) {
147: new[i] = BufSM[i];
148: }
149: BufSM = new; Buf0limit *= 2;
150: }
151: }
152:
153: static struct tokens flushSM()
154: {
155: char *token;
156: struct tokens r;
157: if (ExistSM<=0) {
158: fprintf(stderr,"\n flushSM() is called without data. Don't use the empty string $$. \n");
159: r.token = (char *)NULL; r.kind = -10; /* -1 ==> -10 */
160: return(r);
161: }
162: BufSM[ExistSM] = '\0';
163: ExistSM = 0;
164: token = (char *)sGC_malloc((strlen(BufSM)+1)*sizeof(char));
165: strcpy(token,BufSM);
166: r.token = token;
167: r.kind = TypeSM;
1.7 takayama 168: r.tflag = 0;
1.1 maekawa 169: if (r.kind == ID) {
170: if (isLiteral(r.token)) {
171: r.object = lookupLiteralString(r.token);
172: }else{
173: r = lookupTokens(r); /* Compute hashing values */
174: }
175: }
176: return(r);
177: }
178:
179: static isSpaceSM(c)
1.4 takayama 180: int c;
1.1 maekawa 181: {
1.5 takayama 182: if (((c <= ' ') || c == ',') && (c!= EOF)) return(1);
1.1 maekawa 183: else return(0);
184: }
185:
186: static isDollarSM(c)
1.4 takayama 187: int c;
1.1 maekawa 188: {
189: if (c == '$') return(1);
190: else return(0);
191: }
192:
193: static isBraceSM(c)
1.4 takayama 194: int c;
1.1 maekawa 195: {
196: if (c == '{') return(1);
197: else return(0);
198: }
199:
200: static isKakkoSM(c)
1.4 takayama 201: int c;
1.1 maekawa 202: {
203: if (c == '(') return(1);
204: else return(0);
205: }
206:
207: static isSymbolSM(c)
1.4 takayama 208: int c;
1.1 maekawa 209: {
210: if ((c == '{') ||
211: (c == '}') ||
212: (c == '[') ||
213: (c == ']') ||
214: (c == '(') ||
215: (c == ')'))
216: return(1);
217: else return(0);
218: }
219:
220: struct tokens getokenSM(kind,str)
1.4 takayama 221: actionType kind;
222: char *str;
1.1 maekawa 223: {
224: static int c;
225: static struct tokens rnull;
226: int level;
227: char fname[1024];
228:
229: if (kind == INIT) {
1.9 takayama 230: ScannerWhich = 2;
231: ScannerPt = 0;
232: ScannerBuf[0] = 0;
233:
1.1 maekawa 234: StrpSM = 0;
235: ExistSM = 0;
236:
237: Cfp = BaseFp; /* set the file name to BaseFp */
238: FileStackP = 0; /* Clear the file stack */
239:
240: myungetchar('\n'); /* dummy */
241: c = mygetchar(); /* Notice that you need at least on input to return
1.4 takayama 242: from the getokenSM(INIT); ^^^^^^^^*/
1.1 maekawa 243: rnull.token = (char *)NULL; rnull.kind = -1;
244: return(rnull);
245: }
246:
247: if (kind == OPEN) {
248: rnull.token = (char *)NULL; rnull.kind = -2;
249: /* -2: suceeded, -3: fail */
250: myungetchar(c);
251: FileStack[FileStackP++] = Cfp; /* push the current file */
252: if (FileStackP >= FILESTACK_LIMIT) {
253: fprintf(stderr,"\nError: I cannot open more than %d files.\n",FILESTACK_LIMIT);
254: FileStackP--;
255: c = mygetchar();
256: rnull.kind = -3;
257: return(rnull); /* error */
258: }else {
259: Cfp = fopen(str,"r");
260: if (EchoInScanner)
1.4 takayama 261: printf("\n%% I open the file %s.\n",str);
1.1 maekawa 262: if (Cfp == (FILE *)NULL) {
263:
1.4 takayama 264: strcpy(fname,getLOAD_SM1_PATH());
265: strcat(fname,str);
266: Cfp = fopen(fname,"r");
267: if (Cfp == (FILE *)NULL) {
268: strcpy(fname,LOAD_SM1_PATH);
269: strcat(fname,str);
270: Cfp = fopen(fname,"r");
271: if (Cfp == (FILE *)NULL) {
272: fprintf(stderr,"Warning: Cannot open the file <<%s>> for loading in the current directory nor the library directories %s and %s.\n",str,getLOAD_SM1_PATH(),LOAD_SM1_PATH);
273:
274: Cfp = FileStack[--FileStackP];
275: fprintf(stderr,"\nWarning: I could not open the file %s\n",str);
276: c = mygetchar();
277: rnull.kind = -3;
278: return(rnull); /* error */
279: }else{
280: c = mygetchar(); /* input from the new file */
281: return(rnull);
282: }
283: }else{
284: c = mygetchar(); /* input from the new file */
285: return(rnull);
286: }
1.1 maekawa 287: }else{
1.4 takayama 288: c = mygetchar(); /* input from the new file */
289: return(rnull);
1.1 maekawa 290: }
291: }
292: }
293:
294: for (;;) {
295: TypeSM = ID;
296: if (c == EOF) {
297: if (FileStackP <= 0) {
1.4 takayama 298: if (ExistSM) return(flushSM());
299: else return(rnull);
1.1 maekawa 300: }else { /* return to the previous file */
1.4 takayama 301: fclose(Cfp); /* close the file */
302: Cfp = FileStack[--FileStackP];
303: c = mygetchar(Cfp);
1.1 maekawa 304: }
305: } else if (isSpaceSM(c)) {
306: if (ExistSM) {
1.4 takayama 307: c = mygetchar(); return(flushSM());
1.1 maekawa 308: }else {
1.4 takayama 309: while (isSpaceSM(c=mygetchar())) ;
1.1 maekawa 310: }
311: } else if (isDollarSM(c)) { /* output contents in dollar signs. */
312: if (ExistSM) return(flushSM());
313: else {
1.4 takayama 314: c = mygetchar();
315: while ((c != EOF) && (c != '$')) {
316: putSM(c);
317: c = mygetchar();
318: }
319: if (c=='$') c=mygetchar();
320: TypeSM = DOLLAR;
321: return(flushSM());
1.1 maekawa 322: }
323: } else if (isBraceSM(c)) { /* output contents in { } */
324: /* { { } } */
325: level = 0;
326: if (ExistSM) return(flushSM());
327: else {
1.4 takayama 328: c = mygetchar();
329: while (1) {
330: if (c == '%') { /* skip the comment in the brace. */
331: while (((c=mygetchar()) != '\n') && (c != EOF)) ;
332: }
333: if (c == EOF) break;
334: if ((c == '}') && (level <= 0)) break;
335: if ( c == '{') ++level;
336: if ( c == '}') --level;
337: putSM(c);
338: c = mygetchar();
339: }
340: if (c=='}') c=mygetchar();
341: TypeSM = EXECUTABLE_STRING;
342: return(flushSM());
1.1 maekawa 343: }
344: } else if (isKakkoSM(c)) { /* output contents in ( ) */
345: level = 0;
346: if (ExistSM) return(flushSM());
347: else {
1.4 takayama 348: c = mygetchar();
349: while (1) {
350: if (c == EOF) break;
351: if (c == '\\') { /* e.g. \( */
352: putSM(c);
353: c = mygetchar();
354: if (c == EOF) break;
355: }else{
356: if ((c == ')') && (level <= 0)) break;
357: if ( c == '(') ++level;
358: if ( c == ')') --level;
359: }
360: putSM(c);
361: c = mygetchar();
362: }
363: if (c==')') c=mygetchar();
364: TypeSM = DOLLAR;
365: return(flushSM());
1.1 maekawa 366: }
367: } else if (c=='%') { /* comment */
368: while (((c=mygetchar()) != '\n') && (c != EOF)) ;
369: if(ExistSM) return(flushSM());
370: } else if (isSymbolSM(c)) { /* symbols. {,} etc */
371: if(ExistSM) return(flushSM());
372: else {
1.4 takayama 373: putSM(c);
374: c = mygetchar();
375: return(flushSM());
1.1 maekawa 376: }
377: } else { /* identifier */
378: putSM(c);
379: c =mygetchar();
380: while ((!isDollarSM(c)) &&
1.4 takayama 381: (!isSpaceSM(c)) &&
382: (!isSymbolSM(c)) &&
383: (c != EOF)) {
384: putSM(c);
385: c = mygetchar();
1.1 maekawa 386: }
387: return(flushSM());
388: }
389: }
390: }
391:
392: /*********** end of code part of lexical analizer ********************/
393:
394: /*
395: main() {
396: char input[1000];
397: struct tokens r;
398:
399: getokenSM(INIT);
400: r = getokenSM(GET);
401: while (r.token != (char *)NULL) {
402: printf("%s %d\n",r.token,r.kind);
403: r =getokenSM(GET);
404: }
405:
406: }
407: */
408:
409: /*
410: gets(input);
411: StringSM = (char *)sGC_malloc((strlen(input)+2)*sizeof(char));
412: strcpy(StringSM,input);
413: getokenSM(INIT);
414: */
415:
416: char *getLOAD_SM1_PATH() {
417: char *p;
418: char *p2;
1.8 ohara 419: char *getenv(const char *s);
1.1 maekawa 420: p = getenv("LOAD_SM1_PATH");
421: if (p == NULL) {
1.2 takayama 422: p = getenv("OpenXM_HOME");
423: if (p == NULL) {
424: return("/usr/local/lib/sm1/");
425: }else{
426: if (strlen(p) == 0) return(p);
427: p2 = (char *) sGC_malloc(sizeof(char)*(strlen(p)+strlen("/lib/sm1/")+3));
428: if (p2 == NULL) { fprintf(stderr,"No more memory.\n"); exit(10); }
429: if (p[strlen(p)-1] != '/') {
1.4 takayama 430: strcpy(p2,p); strcat(p2,"/lib/sm1/");
1.2 takayama 431: }else{
1.4 takayama 432: strcpy(p2,p); strcat(p2,"lib/sm1/");
1.2 takayama 433: }
434: return(p2);
435: }
1.1 maekawa 436: }else{
437: if (strlen(p) == 0) return(p);
438: if (p[strlen(p)-1] == '/') return(p);
439: /* Add / */
440: p2 = (char *) sGC_malloc(sizeof(char)*(strlen(p)+3));
441: if (p2 == NULL) { fprintf(stderr,"No more memory.\n"); exit(10); }
442: strcpy(p2,p); strcat(p2,"/");
443: return(p2);
444: }
1.9 takayama 445: }
446:
447: char *traceShowScannerBuf() {
448: char *s;
449: int i,k;
450: s = NULL;
451: /*
452: printf("ScannerPt=%d\n",ScannerPt);
453: for (i=0; i<SCANNERBUF_SIZE; i++) {
454: printf("%x ",(int) (ScannerBuf[i]));
455: }
456: printf("\n"); fflush(NULL); sleep(10);
457: */
458: if ((ScannerPt == 0) && (ScannerBuf[0] == 0)) {
459: s = sGC_malloc(1); s[0] = 0;
460: return s;
461: }
462: if ((ScannerPt > 0) && (ScannerBuf[0] == 0)) {
463: s = sGC_malloc(ScannerPt+1);
464: for (i=1; i<=ScannerPt; i++) {
465: s[i-1] = ScannerBuf[i]; s[i] = 0;
466: }
467: return s;
468: }
469: if (ScannerBuf[0] != 0) {
470: s = sGC_malloc(SCANNERBUF_SIZE+1);
471: k = ScannerPt+1;
472: if (k >= SCANNERBUF_SIZE) k = 0;
473: for (i=0; i<SCANNERBUF_SIZE; i++) {
474: s[i] = ScannerBuf[k]; s[i+1] = 0;
475: k++; if (k >= SCANNERBUF_SIZE) k = 0;
476: }
477: return s;
478: }
479: return s;
1.1 maekawa 480: }
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>