1 /* # skkinput (Simple Kana-Kanji Input)
2 *
3 * This file is part of skkinput.
4 * Copyright (C) 2002
5 * Takashi SAKAMOTO (PXG01715@nifty.ne.jp)
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2, or (at your option)
10 * any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with skkinput; see the file COPYING. If not, write to
19 * the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21 #include "local.h"
22 #include <stdio.h>
23 #include <stdlib.h>
24 #include <assert.h>
25 #include "lispmgrp.h"
26 #include "varbuffer.h"
27 #include "kfile.h"
28 #undef DEBUG
29
30 /* ���������*/
31 enum {
32 MAX_UNGETC_BUF = (16),
33 } ;
34
35 struct tagTLispParser ;
36 struct tagTLispEntity ;
37 struct tagTLispManager ;
38
39 /* �������*/
40 typedef TLispEntity* (*LISPPARSEFUNC)(TLispManager*, struct tagTLispParser*) ;
41
42 typedef struct tagTLispParser {
43 union {
44 struct {
45 KFILE* m_pFile ;
46 Char m_achBuf [MAX_UNGETC_BUF] ;
47 int m_iBufUsage ;
48 } m_file ;
49 struct {
50 const Char* m_pStringTop ;
51 const Char* m_pHead ;
52 int m_iRest ;
53 } m_string ;
54 struct {
55 const char* m_pStringTop ;
56 const char* m_pHead ;
57 int m_iRest ;
58 } m_stringA ;
59 } m_src ;
60
61 LISPPARSEFUNC m_pNextStateFunc ;
62 Char (*m_pGetChar)(struct tagTLispParser*) ;
63 int (*m_pUngetChar)(struct tagTLispParser*, Char) ;
64 } TLispParser ;
65
66 typedef struct tagTLispParserTbl {
67 Char m_cc ;
68 TLispEntity* (*m_pFunc)(TLispManager*, struct tagTLispParser*) ;
69 } TLispParserTbl ;
70
71 /* �ץ�ȥ����������*/
72 static Boolean lispParser_checkNextState (TLispParser*) ;
73 static TLispEntity* lispParser_parseSymbol (TLispManager*, TLispParser*) ;
74 static TLispEntity* lispParser_parseString (TLispManager*, TLispParser*) ;
75 static TLispEntity* lispParser_parseQuote (TLispManager*, TLispParser*) ;
76 /*static TLispEntity* lispParser_parseBackquote (TLispManager*, TLispParser*) ;*/
77 static TLispEntity* lispParser_parseList (TLispManager*, TLispParser*) ;
78 static TLispEntity* lispParser_parseInteger (TLispManager*, TLispParser*) ;
79 static TLispEntity* lispParser_parseChar (TLispManager*, TLispParser*) ;
80 static TLispEntity* lispParser_parseComment (TLispManager*, TLispParser*) ;
81 static TLispEntity* lispParser_parseArray (TLispManager*, TLispParser*) ;
82
83 static TLispEntity* lispParser_parseQuoteCommon (TLispManager*, TLispParser*, const Char*, int) ;
84 static Char lispParser_SkipSpace (TLispParser*) ;
85 static Char lispParser_GetStringChar (TLispParser*) ;
86 static int lispParser_UngetStringChar (TLispParser*, Char) ;
87 static Char lispParser_GetStringCharA (TLispParser*) ;
88 static int lispParser_UngetStringCharA (TLispParser*, Char) ;
89 static Char lispParser_GetFileChar (TLispParser*) ;
90 static int lispParser_UngetFileChar (TLispParser*, Char) ;
91 static Boolean lispParser_readBackslashedChar (TLispParser*, Char*) ;
92
93 /* �����Х�ؿ���*/
94
95 TLispEntity*
lispMgr_ParseString(register TLispManager * pLispMgr,register const Char * pString,register int iLength,register int * pnLastIndex)96 lispMgr_ParseString (
97 register TLispManager* pLispMgr,
98 register const Char* pString,
99 register int iLength,
100 register int* pnLastIndex)
101 {
102 TLispParser parser ;
103 TLispEntity* pRetvalue ;
104 LISPPARSEFUNC pNextStateFunc ;
105
106 /*
107 * �ǥե���Ȥ��֤��͡�
108 */
109 pRetvalue = NULL ;
110
111 /*
112 * �ƤӽФ���¦�˱ƶ���̵���褦�ˡ��ݥ��ڤӿ��ͤԡ����롣
113 */
114 parser.m_src.m_string.m_pStringTop = pString ;
115 parser.m_src.m_string.m_pHead = pString ;
116 parser.m_src.m_string.m_iRest = iLength ;
117 parser.m_pGetChar = lispParser_GetStringChar ;
118 parser.m_pUngetChar = lispParser_UngetStringChar ;
119 parser.m_pNextStateFunc = NULL ;
120
121 for ( ; ; ) {
122 if (!lispParser_checkNextState (&parser))
123 break ;
124 pNextStateFunc = parser.m_pNextStateFunc ;
125 if (parser.m_pNextStateFunc == lispParser_parseComment) {
126 (void)(pNextStateFunc)(pLispMgr, &parser) ;
127 } else {
128 pRetvalue = (pNextStateFunc)(pLispMgr, &parser) ;
129 if (pRetvalue == NULL)
130 break ;
131 }
132 }
133 /* ����ޤ��ɤ߹���������֤���*/
134 if (pnLastIndex != NULL)
135 *pnLastIndex = parser.m_src.m_string.m_pHead - parser.m_src.m_string.m_pStringTop ;
136 return pRetvalue ;
137 }
138
139 TLispEntity*
lispMgr_ParseStringA(register TLispManager * pLispMgr,register const char * pString,register int iLength,register int * pnLastIndex)140 lispMgr_ParseStringA (
141 register TLispManager* pLispMgr,
142 register const char* pString,
143 register int iLength,
144 register int* pnLastIndex)
145 {
146 TLispParser parser ;
147 TLispEntity* pRetvalue ;
148 LISPPARSEFUNC pNextStateFunc ;
149
150 /*
151 * �ǥե���Ȥ��֤��͡�
152 */
153 pRetvalue = NULL ;
154
155 /*
156 * �ƤӽФ���¦�˱ƶ���̵���褦�ˡ��ݥ��ڤӿ��ͤԡ����롣
157 */
158 parser.m_src.m_stringA.m_pStringTop = pString ;
159 parser.m_src.m_stringA.m_pHead = pString ;
160 parser.m_src.m_stringA.m_iRest = iLength ;
161 parser.m_pGetChar = lispParser_GetStringCharA ;
162 parser.m_pUngetChar = lispParser_UngetStringCharA ;
163 parser.m_pNextStateFunc = NULL ;
164
165 for ( ; ; ) {
166 if (!lispParser_checkNextState (&parser))
167 break ;
168 pNextStateFunc = parser.m_pNextStateFunc ;
169 if (parser.m_pNextStateFunc == lispParser_parseComment) {
170 (void)(pNextStateFunc)(pLispMgr, &parser) ;
171 } else {
172 pRetvalue = (pNextStateFunc)(pLispMgr, &parser) ;
173 if (pRetvalue == NULL)
174 break ;
175 }
176 }
177 /* ����ޤ��ɤ߹���������֤���*/
178 if (pnLastIndex != NULL)
179 *pnLastIndex = parser.m_src.m_stringA.m_pHead - parser.m_src.m_stringA.m_pStringTop ;
180 return pRetvalue ;
181 }
182
183 /*
184 *[��ǽ]
185 * �ե����뤫�� lisp ̿����ɤ߹���� entity ����Ѵ����롣
186 */
187 #if defined (WIN32)
188 TLispEntity*
lispMgr_ParseFile(register TLispManager * pLispMgr,register LPCWSTR pFileName)189 lispMgr_ParseFile (
190 register TLispManager* pLispMgr,
191 register LPCWSTR pFileName)
192 #else
193 TLispEntity*
194 lispMgr_ParseFile (
195 register TLispManager* pLispMgr,
196 register const char* pFileName)
197 #endif
198 {
199 KFILE kfile ;
200 TLispParser parser ;
201 TLispEntity* pEntity ;
202 TLispEntity* pRetvalue ;
203 LISPPARSEFUNC pNextStateFunc ;
204 TVarbuffer vbEntity ;
205 TVarbuffer vbufTmpFileName ;
206 int nEntity ;
207
208 assert (pLispMgr != NULL) ;
209 assert (pFileName != NULL) ;
210
211 if (TFAILED (TVarbuffer_Initialize (&vbEntity, sizeof (TLispEntity *))) ||
212 TFAILED (TVarbuffer_Initialize (&vbufTmpFileName, sizeof (char))))
213 return NULL ;
214
215 pRetvalue = NULL ;
216 if (!KFile_Open (&kfile, pFileName, KCODING_SYSTEM_UNKNOWN/*KCODING_SYSTEM_EUCJP*/)) {
217 register int nFileName = strlen (pFileName) ;
218 if (TFAILED (TVarbuffer_Add (&vbufTmpFileName, pFileName, nFileName)) ||
219 TFAILED (TVarbuffer_Add (&vbufTmpFileName, ".el", 4))) /* include NUL */
220 goto exit_func ;
221 pFileName = TVarbuffer_GetBuffer (&vbufTmpFileName) ;
222 if (!KFile_Open (&kfile, pFileName, KCODING_SYSTEM_UNKNOWN/*KCODING_SYSTEM_EUCJP*/))
223 goto exit_func ;
224 }
225 KFile_Rewind (&kfile) ;
226
227 parser.m_src.m_file.m_pFile = &kfile ;
228 parser.m_src.m_file.m_iBufUsage = 0 ;
229 parser.m_pGetChar = lispParser_GetFileChar ;
230 parser.m_pUngetChar = lispParser_UngetFileChar ;
231 parser.m_pNextStateFunc = NULL ;
232
233 for ( ; ; ) {
234 if (!lispParser_checkNextState (&parser))
235 break ;
236 pNextStateFunc = parser.m_pNextStateFunc ;
237 if (pNextStateFunc == lispParser_parseComment) {
238 (void)(pNextStateFunc)(pLispMgr, &parser) ;
239 } else {
240 pEntity = (pNextStateFunc)(pLispMgr, &parser) ;
241 if (pEntity == NULL)
242 break ;
243 TVarbuffer_Add (&vbEntity, &pEntity, 1) ;
244 }
245 }
246 KFile_Close (&kfile) ;
247
248 nEntity = TVarbuffer_GetUsage (&vbEntity) ;
249 if (nEntity > 0) {
250 TLispEntity** ppTop ;
251 TLispEntity** ppEntity ;
252 TLispEntity* pNil ;
253 TLispEntity* pLastElm ;
254 TLispEntity* pListTop ;
255 int i ;
256
257 ppTop = (TLispEntity **)TVarbuffer_GetBuffer (&vbEntity) ;
258 assert (ppTop != NULL) ;
259 (void) lispMgr_CreateNil (pLispMgr, &pNil) ;
260 if (TFAILED (lispMgr_CreateConscell (pLispMgr, *ppTop, pNil, &pLastElm))) {
261 ppEntity = ppTop ;
262 for (i = 0 ; i < nEntity ; i ++)
263 lispEntity_Release (pLispMgr, *ppEntity ++) ;
264 } else {
265 TLispEntity* pCdr ;
266
267 pListTop = pLastElm ;
268 lispEntity_AddRef (pLispMgr, pListTop) ;
269 lispEntity_Release (pLispMgr, *ppTop) ;
270
271 ppEntity = ppTop + 1 ;
272 for (i = 1 ; i < nEntity ; i ++) {
273 if (TFAILED (lispMgr_CreateConscell (pLispMgr, *ppEntity, pNil, &pCdr)))
274 break ;
275 lispEntity_SetCdr (pLispMgr, pLastElm, pCdr) ;
276 lispEntity_Release (pLispMgr, *ppEntity) ;
277 ppEntity ++ ;
278 pLastElm = pCdr ;
279 }
280 if (i < nEntity) {
281 while (i < nEntity) {
282 lispEntity_Release (pLispMgr, *ppEntity ++) ;
283 i ++ ;
284 }
285 lispEntity_Release (pLispMgr, pListTop) ;
286 pRetvalue = NULL;
287 } else {
288 pRetvalue = pListTop ;
289 }
290 }
291 } else {
292 pRetvalue = NULL ;
293 }
294 exit_func:
295 TVarbuffer_Uninitialize (&vbEntity) ;
296 TVarbuffer_Uninitialize (&vbufTmpFileName) ;
297 return pRetvalue ;
298 }
299
300 /*========================================================================
301 * �ɽ�ؿ���
302 *========================================================================*/
303
304 Boolean
lispParser_checkNextState(register TLispParser * pParser)305 lispParser_checkNextState (
306 register TLispParser* pParser)
307 {
308 static TLispParserTbl saTable [] = {
309 { 0x22, lispParser_parseString, },
310 { 0x27, lispParser_parseQuote, },
311 { 0x28, lispParser_parseList, },
312 { 0x3B, lispParser_parseComment, },
313 { 0x5B, lispParser_parseArray, },
314 /*{ 0x60, lispParser_parseBackquote, },*/
315 { '.', NULL, /*lispParser_parseInteger,*/ },
316 { ']', NULL, },
317 { ')', NULL, },
318 } ;
319 register TLispParserTbl* ptr ;
320 register int i ;
321 register Char cc ;
322
323 assert (pParser != NULL) ;
324
325 /* ������ɤ����Ф���*/
326 if ((cc = lispParser_SkipSpace (pParser)) == EOF)
327 return False ;
328
329 /* Ƚ�̤˻Ȥä���ʸ�����᤹ɬ�פ����롣*/
330 (pParser->m_pUngetChar)(pParser, cc) ;
331
332 ptr = saTable ;
333 for (i = 0 ; i < NELEMENTS (saTable) ; i ++, ptr ++)
334 if (cc == ptr->m_cc)
335 goto found ;
336
337 if (!Char_DifferenceAscii (cc, '?')) {
338 pParser->m_pNextStateFunc = lispParser_parseChar ;
339 } else if (Char_IsDigitNum (cc)) {
340 pParser->m_pNextStateFunc = lispParser_parseInteger ;
341 } else {
342 pParser->m_pNextStateFunc = lispParser_parseSymbol ;
343 }
344 return True ;
345
346 found:
347 pParser->m_pNextStateFunc = ptr->m_pFunc ;
348 return (ptr->m_pFunc != NULL)? True : False ;
349 }
350
351 /*
352 * ³��ʸ����� SYMBOL �Ǥ��롣
353 */
354 TLispEntity*
lispParser_parseSymbol(register TLispManager * pLispMgr,register TLispParser * pParser)355 lispParser_parseSymbol (
356 register TLispManager* pLispMgr,
357 register TLispParser* pParser)
358 {
359 TVarbuffer vbAtomName ;
360 Char cc ;
361 TLispEntity* pRetvalue ;
362 const Char* pSymName ;
363 int nSymName ;
364
365 assert (pLispMgr != NULL) ;
366 assert (pParser != NULL) ;
367
368 pRetvalue = NULL ;
369
370 #if defined (DEBUG)
371 fprintf (stderr, "[Enter] _parseSymbol ()\n") ;
372 #endif
373 TVarbuffer_Initialize (&vbAtomName, sizeof (Char)) ;
374
375 for ( ; ; ) {
376 cc = (pParser->m_pGetChar)(pParser) ;
377 if (cc == EOF)
378 break ;
379 if (!Char_DifferenceAscii (cc, ' ') ||
380 !Char_DifferenceAscii (cc, '\t') ||
381 !Char_DifferenceAscii (cc, '\n') ||
382 !Char_DifferenceAscii (cc, '\r') ||
383 !Char_DifferenceAscii (cc, ';') ||
384 !Char_DifferenceAscii (cc, ')') ||
385 !Char_DifferenceAscii (cc, ']') ||
386 !Char_DifferenceAscii (cc, '(') ||
387 !Char_DifferenceAscii (cc, '['))
388 break ;
389 TVarbuffer_Add (&vbAtomName, &cc, 1) ;
390 }
391 if (cc != EOF)
392 (pParser->m_pUngetChar)(pParser, cc) ;
393
394 pSymName = TVarbuffer_GetBuffer (&vbAtomName) ;
395 nSymName = TVarbuffer_GetUsage (&vbAtomName) ;
396 if (TFAILED (lispMgr_InternSymbol (pLispMgr, pSymName, nSymName, &pRetvalue))) {
397 #if defined (DEBUG)
398 fprintf (stderr, "[FAILE] InternSymbol ()\n") ;
399 #endif
400 TVarbuffer_Uninitialize (&vbAtomName) ;
401 return NULL ;
402 }
403 lispEntity_AddRef (pLispMgr, pRetvalue) ;
404 TVarbuffer_Uninitialize (&vbAtomName) ;
405
406 #if defined (DEBUG)
407 fprintf (stderr, "[Leave] _parseSymbol ()\n") ;
408 lispEntity_Print (pLispMgr, pRetvalue) ;
409 fprintf (stderr, "\n") ;
410 fflush (stderr) ;
411 #endif
412 return pRetvalue ;
413 }
414
415 /*
416 * ³��ʸ����� STRING �Ǥ��롣
417 */
418 TLispEntity*
lispParser_parseString(register TLispManager * pLispMgr,register TLispParser * pParser)419 lispParser_parseString (
420 register TLispManager* pLispMgr,
421 register TLispParser* pParser)
422 {
423 TVarbuffer vbString ;
424 Char cc ;
425 TLispEntity* pRetvalue ;
426
427 assert (pLispMgr != NULL) ;
428 assert (pParser != NULL) ;
429
430 pRetvalue = NULL ;
431
432 /*
433 * ������ʸ����ʤΤ���
434 */
435 cc = (pParser->m_pGetChar)(pParser) ;
436 if (cc != 0x22) {
437 (pParser->m_pUngetChar)(pParser, cc) ;
438 return NULL ;
439 }
440
441 #if defined (DEBUG)
442 fprintf (stderr, "[Enter] _parseString ()\n") ;
443 #endif
444 TVarbuffer_Initialize (&vbString, sizeof (Char)) ;
445
446 /*
447 * ��������ʸ���ϡ�
448 */
449 for ( ; ; ) {
450 cc = (pParser->m_pGetChar)(pParser) ;
451 switch (cc) {
452 case EOF:
453 case 0x22:
454 goto exit_loop ;
455 case '\\': /* backquote */
456 if (TFAILED (lispParser_readBackslashedChar (pParser, &cc)))
457 goto exit_error ;
458 break ;
459 default:
460 break ;
461 }
462 TVarbuffer_Add (&vbString, &cc, 1) ;
463 }
464 exit_loop:
465
466 /*
467 * ʸ����Ȥ��ƽ�ü����Ƥ���Τ���
468 */
469 if (cc == 0x22) {
470 const Char* pString ;
471 int nString ;
472
473 pString = TVarbuffer_GetBuffer (&vbString) ;
474 nString = TVarbuffer_GetUsage (&vbString) ;
475 if (TFAILED (lispMgr_CreateString (pLispMgr, pString, nString, &pRetvalue))) {
476 pRetvalue = NULL ;
477 } else {
478 lispEntity_AddRef (pLispMgr, pRetvalue) ;
479 }
480 }
481 exit_error:
482 TVarbuffer_Uninitialize (&vbString) ;
483
484 return pRetvalue ;
485 }
486
487 Boolean
lispParser_readBackslashedChar(register TLispParser * pParser,register Char * pchRetval)488 lispParser_readBackslashedChar (
489 register TLispParser* pParser,
490 register Char* pchRetval)
491 {
492 Char cc ;
493 Char chRet ;
494 unsigned long uAndMask, uOrMask ;
495
496 /* ���λ����� '\\' ���ɤ߽��������ξ��֤ˤ��롣*/
497 cc = (pParser->m_pGetChar)(pParser) ;
498 switch (cc) {
499 case 'C':
500 uAndMask = 0x1F ;
501 uOrMask = 0 ;
502 goto meta_control_common ;
503 case 'M':
504 uAndMask = 0x7F ;
505 uOrMask = 0x80 ;
506 meta_control_common:
507 cc = (pParser->m_pGetChar)(pParser) ;
508 if (cc != '-')
509 return False ;
510 cc = (pParser->m_pGetChar)(pParser) ;
511 if (cc == '\\') {
512 if (TFAILED (lispParser_readBackslashedChar (pParser, &cc)))
513 return False ;
514 }
515 *pchRetval = (cc & uAndMask) | uOrMask ;
516 break ;
517
518 case 't':
519 *pchRetval = Char_Make (KCHARSET_ASCII, '\t') ;
520 break ;
521
522 case 'n':
523 *pchRetval = Char_Make (KCHARSET_ASCII, '\n') ;
524 break ;
525
526 case 'r':
527 *pchRetval = Char_Make (KCHARSET_ASCII, '\r') ;
528 break ;
529
530 case 'x':
531 chRet = 0 ;
532 for ( ; ; ) {
533 cc = (pParser->m_pGetChar)(pParser) ;
534 if ('0' <= cc && cc <= '9') {
535 chRet = chRet * 0x10 + (cc - '0') ;
536 } else if ('a' <= cc && cc <= 'f') {
537 chRet = chRet * 0x10 + (cc - 'a' + 10) ;
538 } else if ('A' <= cc && cc <= 'F') {
539 chRet = chRet * 0x10 + (cc - 'A' + 10) ;
540 } else {
541 (pParser->m_pUngetChar)(pParser, cc) ;
542 break ;
543 }
544 }
545 *pchRetval = Char_Make (KCHARSET_ASCII, chRet) ;
546 break ;
547
548 default:
549 if ('0' <= cc && cc <= '7') {
550 register int i ;
551 chRet = cc - '0' ;
552 for (i = 0 ; i < 2 ; i ++) {
553 cc = (pParser->m_pGetChar)(pParser) ;
554 if (cc < '0' || cc > '7') {
555 (pParser->m_pUngetChar)(pParser, cc) ;
556 break ;
557 }
558 chRet = chRet * 8 + (cc - '0') ;
559 }
560 *pchRetval = Char_Make (KCHARSET_ASCII, chRet) ;
561 break ;
562 }
563 *pchRetval = cc ;
564 break ;
565 }
566 return True ;
567 }
568
569 /*
570 *
571 */
572 TLispEntity*
lispParser_parseQuote(register TLispManager * pLispMgr,register TLispParser * pParser)573 lispParser_parseQuote (
574 register TLispManager* pLispMgr,
575 register TLispParser* pParser)
576 {
577 static const Char achQuote [] = { 'q', 'u', 'o', 't', 'e', } ;
578 register Char cc ;
579
580 assert (pLispMgr != NULL) ;
581 assert (pParser != NULL) ;
582
583 #if defined (DEBUG)
584 fprintf (stderr, "[Enter] _parseQuote ()\n") ;
585 #endif
586 cc = (pParser->m_pGetChar)(pParser) ;
587 if (cc == EOF)
588 return NULL ;
589 if (cc != 0x27) {
590 (pParser->m_pUngetChar)(pParser, cc) ;
591 return NULL ;
592 }
593 return lispParser_parseQuoteCommon (pLispMgr, pParser, achQuote, NELEMENTS (achQuote)) ;
594 }
595
596 #if 0
597 /*
598 * ����ϼ��ԡ����Ǥ������Υ����ɤ����פǤ���(;_;)
599 */
600 TLispEntity*
601 lispParser_parseBackquote (
602 register TLispManager* pLispMgr,
603 register TLispParser* pParser)
604 {
605 static const Char achQuote [] = { 'b', 'a', 'c', 'k', 'q', 'u', 'o', 't', 'e', } ;
606 register Char cc ;
607
608 assert (pLispMgr != NULL) ;
609 assert (pParser != NULL) ;
610
611 cc = (pParser->m_pGetChar)(pParser) ;
612 if (cc == EOF)
613 return NULL ;
614 if (cc != 0x60) {
615 (pParser->m_pUngetChar)(pParser, cc) ;
616 return NULL ;
617 }
618 return lispParser_parseQuoteCommon (pLispMgr, pParser, achQuote, NELEMENTS (achQuote)) ;
619 }
620 #endif
621
622 TLispEntity*
lispParser_parseQuoteCommon(register TLispManager * pLispMgr,register TLispParser * pParser,register const Char * strSymbol,register int nSymbol)623 lispParser_parseQuoteCommon (
624 register TLispManager* pLispMgr,
625 register TLispParser* pParser,
626 register const Char* strSymbol,
627 register int nSymbol)
628 {
629 register LISPPARSEFUNC pNextStateFunc ;
630 register LISPPARSEFUNC pOrgNextStateFunc ;
631 TLispEntity* pEntQuote ;
632 TLispEntity* pEntArg ;
633 TLispEntity* pRetvalue ;
634 TLispEntity* apEntities [2] ;
635
636 if (TFAILED (lispMgr_InternSymbol (pLispMgr, strSymbol, nSymbol, &pEntQuote)))
637 return NULL ;
638
639 lispEntity_AddRef (pLispMgr, pEntQuote) ;
640 apEntities [0] = pEntQuote ;
641 pEntArg = NULL ;
642
643 pOrgNextStateFunc = pParser->m_pNextStateFunc ;
644 for ( ; ; ) {
645 if (!lispParser_checkNextState (pParser))
646 break ;
647 pNextStateFunc = pParser->m_pNextStateFunc ;
648 pEntArg = (pNextStateFunc)(pLispMgr, pParser) ;
649 if (pNextStateFunc != lispParser_parseComment)
650 break ;
651 }
652 pParser->m_pNextStateFunc = pOrgNextStateFunc ;
653
654 if (pEntArg == NULL) {
655 lispEntity_Release (pLispMgr, pEntQuote) ;
656 return NULL ;
657 }
658 apEntities [1] = pEntArg ;
659 if (TFAILED (lispMgr_CreateList (pLispMgr, apEntities, 2, &pRetvalue))) {
660 lispEntity_Release (pLispMgr, pEntQuote) ;
661 lispEntity_Release (pLispMgr, pEntArg) ;
662 return NULL ;
663 }
664 lispEntity_AddRef (pLispMgr, pRetvalue) ;
665 lispEntity_Release (pLispMgr, pEntQuote) ;
666 lispEntity_Release (pLispMgr, pEntArg) ;
667 return pRetvalue ;
668 }
669
670 TLispEntity*
lispParser_parseInteger(register TLispManager * pLispMgr,register TLispParser * pParser)671 lispParser_parseInteger (
672 register TLispManager* pLispMgr,
673 register TLispParser* pParser)
674 {
675 TVarbuffer vbufSymbol ; /* integer �� symbol ���ޤ�ʬ����ʤ���*/
676 TLispEntity* pRetvalue ;
677 Char cc ;
678 int iNumber = 0 ;
679 int iSign = +1 ;
680 Boolean fNotInteger = False ;
681
682 assert (pLispMgr != NULL) ;
683 assert (pParser != NULL) ;
684
685 #if defined (DEBUG)
686 fprintf (stderr, "[Enter] _parseInteger ()\n") ;
687 #endif
688 pRetvalue = NULL ;
689 cc = (pParser->m_pGetChar)(pParser) ;
690 if (cc == EOF)
691 return NULL ;
692 if (TFAILED (TVarbuffer_Initialize (&vbufSymbol, sizeof (Char))))
693 return NULL ;
694
695 if (cc != '.') {
696 if (!Char_IsDigitNum (cc) && cc != '-' && cc != '+') {
697 (pParser->m_pUngetChar) (pParser, cc) ;
698 return NULL ;
699 }
700 TVarbuffer_Add (&vbufSymbol, &cc, 1) ;
701 if (!Char_DifferenceAscii (cc, '+') || !Char_DifferenceAscii (cc, '-')) {
702 iSign = (!Char_DifferenceAscii (cc, '-'))? -1 : +1 ;
703 cc = (pParser->m_pGetChar)(pParser) ;
704 if (Char_DifferenceAscii (cc, '0') < 0 ||
705 Char_DifferenceAscii (cc, '9') > 0) {
706 if (cc != EOF)
707 (pParser->m_pUngetChar) (pParser, cc) ;
708 fNotInteger = True ;
709 goto not_integer ;
710 }
711 TVarbuffer_Add (&vbufSymbol, &cc, 1) ;
712 }
713 while (cc != EOF &&
714 Char_DifferenceAscii (cc, '0') >= 0 &&
715 Char_DifferenceAscii (cc, '9') <= 0) {
716 iNumber = iNumber * 10 + Char_DifferenceAscii (cc, '0') ;
717 cc = (pParser->m_pGetChar)(pParser) ;
718 TVarbuffer_Add (&vbufSymbol, &cc, 1) ;
719 }
720 }
721 /* '.' ����Ƥ���Ȥ������Ȥ���ư����������*/
722 if (!Char_DifferenceAscii (cc, '.')) {
723 double dShift = 0.1 ;
724 double dNumber = (double) iNumber ;
725
726 cc = (pParser->m_pGetChar)(pParser) ;
727 TVarbuffer_Add (&vbufSymbol, &cc, 1) ;
728
729 while (cc != EOF &&
730 Char_DifferenceAscii (cc, '0') >= 0 &&
731 Char_DifferenceAscii (cc, '9') <= 0) {
732 dNumber = dNumber + (double)(Char_DifferenceAscii (cc, '0')) * dShift ;
733 dShift = dShift / 10.0 ;
734 cc = (pParser->m_pGetChar)(pParser) ;
735 TVarbuffer_Add (&vbufSymbol, &cc, 1) ;
736 }
737 if (cc != EOF &&
738 Char_DifferenceAscii (cc, ' ') &&
739 Char_DifferenceAscii (cc, ']') &&
740 Char_DifferenceAscii (cc, '"') &&
741 Char_DifferenceAscii (cc, '\t') &&
742 Char_DifferenceAscii (cc, '\x39') &&
743 Char_DifferenceAscii (cc, '\x29') &&
744 Char_DifferenceAscii (cc, '\n') &&
745 Char_DifferenceAscii (cc, '\r')) {
746 fNotInteger = True ;
747 } else {
748 if (cc != EOF)
749 (pParser->m_pUngetChar) (pParser, cc) ;
750 if (TFAILED (lispMgr_CreateFloat (pLispMgr, (float) (iSign * dNumber), &pRetvalue)))
751 pRetvalue = NULL ;
752 }
753 } else if (cc != EOF &&
754 Char_DifferenceAscii (cc, ' ') &&
755 Char_DifferenceAscii (cc, ']') &&
756 Char_DifferenceAscii (cc, '"') &&
757 Char_DifferenceAscii (cc, '\t') &&
758 Char_DifferenceAscii (cc, '\x39') &&
759 Char_DifferenceAscii (cc, '(') &&
760 Char_DifferenceAscii (cc, ')') &&
761 Char_DifferenceAscii (cc, '[') &&
762 Char_DifferenceAscii (cc, '\n') &&
763 Char_DifferenceAscii (cc, '\r')) {
764 fNotInteger = True ;
765 } else {
766 if (cc != EOF)
767 (pParser->m_pUngetChar) (pParser, cc) ;
768
769 if (TFAILED (lispMgr_CreateInteger (pLispMgr, iSign * iNumber, &pRetvalue)))
770 pRetvalue = NULL ;
771 }
772
773 not_integer:
774 if (fNotInteger) {
775 const Char* pString ;
776 int nLength ;
777
778 for ( ; ; ) {
779 cc = (pParser->m_pGetChar)(pParser) ;
780 if (cc == EOF ||
781 !Char_DifferenceAscii (cc, ' ') ||
782 !Char_DifferenceAscii (cc, '[') ||
783 !Char_DifferenceAscii (cc, ']') ||
784 !Char_DifferenceAscii (cc, '"') ||
785 !Char_DifferenceAscii (cc, '\t') ||
786 !Char_DifferenceAscii (cc, '\x39') ||
787 !Char_DifferenceAscii (cc, '(') ||
788 !Char_DifferenceAscii (cc, ')') ||
789 !Char_DifferenceAscii (cc, '\n') ||
790 !Char_DifferenceAscii (cc, '\r'))
791 break ;
792 TVarbuffer_Add (&vbufSymbol, &cc, 1) ;
793 }
794 if (cc != EOF)
795 (pParser->m_pUngetChar) (pParser, cc) ;
796
797 pString = TVarbuffer_GetBuffer (&vbufSymbol) ;
798 nLength = TVarbuffer_GetUsage (&vbufSymbol) ;
799 if (TFAILED (lispMgr_InternSymbol (pLispMgr, pString, nLength, &pRetvalue))) {
800 pRetvalue = NULL ;
801 }
802 }
803 if (pRetvalue != NULL)
804 lispEntity_AddRef (pLispMgr, pRetvalue) ;
805 TVarbuffer_Uninitialize (&vbufSymbol) ;
806 return pRetvalue ;
807 }
808
809 TLispEntity*
lispParser_parseChar(register TLispManager * pLispMgr,register TLispParser * pParser)810 lispParser_parseChar (
811 register TLispManager* pLispMgr,
812 register TLispParser* pParser)
813 {
814 TLispEntity* pRetvalue ;
815 Char cc ;
816
817 assert (pLispMgr != NULL) ;
818 assert (pParser != NULL) ;
819
820 pRetvalue = NULL ;
821
822 #if defined (DEBUG)
823 fprintf (stderr, "[Enter] _parseChar ()\n") ;
824 #endif
825 cc = (pParser->m_pGetChar)(pParser) ;
826 if (cc == EOF)
827 return NULL ;
828
829 if (Char_DifferenceAscii (cc, '?')) {
830 (pParser->m_pUngetChar) (pParser, cc) ;
831 return NULL ;
832 }
833 cc = (pParser->m_pGetChar)(pParser) ;
834 if (!Char_DifferenceAscii (cc, '\\'))
835 lispParser_readBackslashedChar (pParser, &cc) ;
836 if (cc == EOF)
837 return NULL ;
838 if (TFAILED (lispMgr_CreateInteger (pLispMgr, cc, &pRetvalue)))
839 return NULL ;
840 lispEntity_AddRef (pLispMgr, pRetvalue) ;
841
842 return pRetvalue ;
843 }
844
845 /*
846 *
847 */
848 TLispEntity*
lispParser_parseList(register TLispManager * pLispMgr,register TLispParser * pParser)849 lispParser_parseList (
850 register TLispManager* pLispMgr,
851 register TLispParser* pParser)
852 {
853 TLispEntity* pEntity ;
854 TLispEntity* pCdr ;
855 TLispEntity* pRetvalue ;
856 TVarbuffer vbufEntity ;
857 int iEntity ;
858 Char cc ;
859 LISPPARSEFUNC pNextStateFunc ;
860 LISPPARSEFUNC pOrgNextStateFunc ;
861
862 assert (pLispMgr != NULL) ;
863 assert (pParser != NULL) ;
864
865 #if defined (DEBUG)
866 fprintf (stderr, "[Enter] _parseList ()\n") ;
867 #endif
868 pRetvalue = NULL ;
869
870 cc = (pParser->m_pGetChar)(pParser) ;
871 if (cc == EOF)
872 return NULL ;
873
874 if (Char_DifferenceAscii (cc, '(')) {
875 (pParser->m_pUngetChar)(pParser, cc) ;
876 #if defined (DEBUG)
877 fprintf (stderr, "[ParseList] cc != '('\n") ;
878 #endif
879 return NULL ;
880 }
881
882 if (!TVarbuffer_Initialize (&vbufEntity, sizeof (TLispEntity*)))
883 return NULL ;
884
885 pOrgNextStateFunc = pParser->m_pNextStateFunc ;
886
887 for ( ; ; ) {
888 if (!lispParser_checkNextState (pParser))
889 break ;
890 pNextStateFunc = pParser->m_pNextStateFunc ;
891 pEntity = (pNextStateFunc)(pLispMgr, pParser) ;
892 if (pNextStateFunc == lispParser_parseComment)
893 continue ;
894 if (pEntity == NULL) {
895 #if defined (DEBUG)
896 fprintf (stderr, "(1) [ParseList] pEntity == NULL\n") ;
897 #endif
898 goto exit_parse_list ;
899 }
900 TVarbuffer_Add (&vbufEntity, &pEntity, 1) ;
901 }
902
903 /*cc = (pParser->m_pGetChar)(pParser) ;*/
904 cc = lispParser_SkipSpace (pParser) ;
905 if (cc != EOF && !Char_DifferenceAscii (cc, '.')) {
906 pEntity = NULL ;
907 for ( ; ; ) {
908 if (!lispParser_checkNextState (pParser))
909 break ;
910 pNextStateFunc = pParser->m_pNextStateFunc ;
911 pEntity = (pNextStateFunc)(pLispMgr, pParser) ;
912 if (pNextStateFunc != lispParser_parseComment)
913 break ;
914 }
915 if (pEntity == NULL) {
916 #if defined (DEBUG)
917 fprintf (stderr, "(2) [ParseList] pEntity == NULL\n") ;
918 #endif
919 goto exit_parse_list ;
920 }
921 pCdr = pEntity ;
922 /*cc = (pParser->m_pGetChar)(pParser) ;*/
923 cc = lispParser_SkipSpace (pParser) ;
924 } else {
925 (void) lispMgr_CreateNil (pLispMgr, &pCdr) ;
926 assert (pCdr != NULL) ;
927 lispEntity_AddRef (pLispMgr, pCdr) ;
928 }
929
930 if (cc == EOF || Char_DifferenceAscii (cc, ')')) {
931 #if defined (DEBUG)
932 fprintf (stderr, "[ParseList] cc != ')' %lx\n", cc) ;
933 #endif
934 goto exit_parse_list ;
935 }
936
937 iEntity = TVarbuffer_GetUsage (&vbufEntity) ;
938 if (iEntity < 0) {
939 (void) lispMgr_CreateNil (pLispMgr, &pRetvalue) ;
940 lispEntity_AddRef (pLispMgr, pRetvalue) ;
941 } else if (iEntity == 0) {
942 pRetvalue = pCdr ;
943 } else {
944 TLispEntity** ppTop ;
945 TLispEntity** ppEntity ;
946 TLispEntity* pListTop ;
947 TLispEntity* pNil ;
948 int i ;
949
950 (void) lispMgr_CreateNil (pLispMgr, &pNil) ;
951 ppTop = (TLispEntity **) TVarbuffer_GetBuffer (&vbufEntity) ;
952 if (TFAILED (lispMgr_CreateConscell (pLispMgr, *ppTop, pNil, &pListTop))) {
953 ppEntity = ppTop ;
954 for (i = 0 ; i < iEntity ; i ++)
955 lispEntity_Release (pLispMgr, *ppEntity ++) ;
956 pRetvalue = NULL ;
957 } else {
958 TLispEntity* pLast ;
959 TLispEntity* pElm ;
960
961 lispEntity_AddRef (pLispMgr, pListTop) ;
962 lispEntity_Release (pLispMgr, *ppTop) ;
963 pLast = pListTop ;
964
965 ppEntity = ppTop + 1 ;
966 for (i = 1 ; i < iEntity ; i ++) {
967 if (TFAILED (lispMgr_CreateConscell (pLispMgr, *ppEntity, pNil, &pElm)))
968 break ;
969 lispEntity_SetCdr (pLispMgr, pLast, pElm) ;
970 lispEntity_Release (pLispMgr, *ppEntity) ;
971 ppEntity ++ ;
972 pLast = pElm ;
973 }
974 lispEntity_SetCdr (pLispMgr, pLast, pCdr) ;
975 if (i < iEntity) {
976 while (i < iEntity) {
977 lispEntity_Release (pLispMgr, *ppEntity ++) ;
978 i ++ ;
979 }
980 lispEntity_Release (pLispMgr, pListTop) ;
981 pRetvalue = NULL ;
982 } else {
983 pRetvalue = pListTop ;
984 }
985 }
986 lispEntity_Release (pLispMgr, pCdr) ;
987 }
988
989 exit_parse_list:
990 TVarbuffer_Uninitialize (&vbufEntity) ;
991
992 return pRetvalue ;
993 }
994
995 /*
996 *
997 */
998 TLispEntity*
lispParser_parseComment(register TLispManager * pLispMgr,register TLispParser * pParser)999 lispParser_parseComment (
1000 register TLispManager* pLispMgr,
1001 register TLispParser* pParser)
1002 {
1003 register Char cc ;
1004
1005 assert (pLispMgr != NULL) ;
1006 assert (pParser != NULL) ;
1007
1008 cc = (pParser->m_pGetChar)(pParser) ;
1009 if (cc == EOF)
1010 return NULL ;
1011
1012 if (Char_DifferenceAscii (cc, ';')) {
1013 (pParser->m_pUngetChar)(pParser, cc) ;
1014 return NULL ;
1015 }
1016 #if defined (DEBUG)
1017 fprintf (stderr, "[Enter] _parseComment ()\n") ;
1018 #endif
1019
1020 while (cc != EOF && Char_DifferenceAscii (cc, '\n'))
1021 cc = (pParser->m_pGetChar)(pParser) ;
1022
1023 if (cc != EOF)
1024 (pParser->m_pUngetChar)(pParser, cc) ;
1025
1026 return NULL ;
1027 }
1028
1029 /*
1030 *
1031 */
1032 TLispEntity*
lispParser_parseArray(register TLispManager * pLispMgr,register TLispParser * pParser)1033 lispParser_parseArray (
1034 register TLispManager* pLispMgr,
1035 register TLispParser* pParser)
1036 {
1037 TVarbuffer vbufVector ;
1038 TLispEntity* pEntity ;
1039 TLispEntity* pRetvalue ;
1040 LISPPARSEFUNC pNextStateFunc ;
1041 LISPPARSEFUNC pOrgNextStateFunc ;
1042 Char cc ;
1043 int nElements ;
1044
1045 assert (pLispMgr != NULL) ;
1046 assert (pParser != NULL) ;
1047
1048 pRetvalue = NULL ;
1049
1050 #if defined (DEBUG)
1051 fprintf (stderr, "[Enter] _parseArray ()\n") ;
1052 #endif
1053 /* ��������ȳ����Ƥ��뤫�����å����롣*/
1054 cc = (pParser->m_pGetChar)(pParser) ;
1055 if (cc == EOF)
1056 return NULL ;
1057 if (Char_DifferenceAscii (cc, '[')) {
1058 (pParser->m_pUngetChar)(pParser, cc) ;
1059 return NULL ;
1060 }
1061
1062 if (!TVarbuffer_Initialize (&vbufVector, sizeof (TLispEntity*)))
1063 return NULL ;
1064
1065 pOrgNextStateFunc = pParser->m_pNextStateFunc ;
1066
1067 /* ��������Ǥ���Ф���*/
1068 for ( ; ; ) {
1069 /*
1070 * �����֤�����Τ˼��Ԥ����顢ȴ���롣
1071 * �쳵�˥��顼�Ȥϸ����ʤ���������Ĥ���Ȥ��ˤ� false ��
1072 * ��äƤ���Τǡ�
1073 */
1074 if (!lispParser_checkNextState (pParser))
1075 break ;
1076 pNextStateFunc = pParser->m_pNextStateFunc ;
1077 pEntity = (pNextStateFunc)(pLispMgr, pParser) ;
1078 if (pEntity != NULL) {
1079 if (!TVarbuffer_Add (&vbufVector, &pEntity, 1))
1080 goto exit_parse_array ;
1081 } else {
1082 if (pNextStateFunc != lispParser_parseComment)
1083 goto exit_parse_array ;
1084 }
1085 }
1086
1087 /* ����������Ĥ��Ƥ��뤫�ɤ��������å����롣*/
1088 cc = (pParser->m_pGetChar)(pParser) ;
1089 if (cc == EOF || Char_DifferenceAscii (cc, ']'))
1090 goto exit_parse_array ;
1091
1092 nElements = TVarbuffer_GetUsage (&vbufVector) ;
1093 if (nElements <= 0) {
1094 if (TFAILED (lispMgr_CreateVector (pLispMgr, NULL, 0, &pRetvalue)))
1095 pRetvalue = NULL ;
1096 } else {
1097 TLispEntity** ppElements ;
1098
1099 ppElements = (TLispEntity **)TVarbuffer_GetBuffer (&vbufVector) ;
1100 if (TFAILED (lispMgr_CreateVector (pLispMgr, ppElements, nElements, &pRetvalue)))
1101 pRetvalue = NULL ;
1102 }
1103 if (pRetvalue != NULL)
1104 lispEntity_AddRef (pLispMgr, pRetvalue) ;
1105
1106 exit_parse_array:
1107 nElements = TVarbuffer_GetUsage (&vbufVector) ;
1108 if (nElements > 0) {
1109 TLispEntity** ppElements ;
1110
1111 ppElements = (TLispEntity **)TVarbuffer_GetBuffer (&vbufVector) ;
1112 nElements = TVarbuffer_GetUsage (&vbufVector) ;
1113 /* ���פˤʤä�����ƥ��ƥ���������롣*/
1114 while (nElements > 0) {
1115 lispEntity_Release (pLispMgr, *ppElements ++) ;
1116 nElements -- ;
1117 }
1118 }
1119
1120 pParser->m_pNextStateFunc = pOrgNextStateFunc ;
1121
1122 TVarbuffer_Uninitialize (&vbufVector) ;
1123
1124 return pRetvalue ;
1125 }
1126
1127 Char
lispParser_SkipSpace(register TLispParser * pParser)1128 lispParser_SkipSpace (
1129 register TLispParser* pParser)
1130 {
1131 register Char cc ;
1132
1133 assert (pParser != NULL) ;
1134
1135 for ( ; ; ) {
1136 cc = (pParser->m_pGetChar)(pParser) ;
1137 if (Char_DifferenceAscii (cc, ' ') &&
1138 Char_DifferenceAscii (cc, '\t') &&
1139 Char_DifferenceAscii (cc, '\n') &&
1140 Char_DifferenceAscii (cc, '\f') &&
1141 Char_DifferenceAscii (cc, '\r'))
1142 break ;
1143 }
1144 return cc ;
1145 }
1146
1147 Char
lispParser_GetStringChar(register TLispParser * pParser)1148 lispParser_GetStringChar (
1149 register TLispParser* pParser)
1150 {
1151 register Char cc ;
1152
1153 if (pParser->m_src.m_string.m_iRest <= 0)
1154 return (Char) EOF ;
1155
1156 cc = *pParser->m_src.m_string.m_pHead ++ ;
1157 pParser->m_src.m_string.m_iRest -- ;
1158 return cc ;
1159 }
1160
1161 int
lispParser_UngetStringChar(register TLispParser * pParser,register Char cc)1162 lispParser_UngetStringChar (
1163 register TLispParser* pParser,
1164 register Char cc)
1165 {
1166 if (pParser->m_src.m_string.m_pHead <= pParser->m_src.m_string.m_pStringTop)
1167 return -1 ;
1168
1169 pParser->m_src.m_string.m_pHead -- ;
1170 pParser->m_src.m_string.m_iRest ++ ;
1171 return 0 ;
1172
1173 UNREFERENCED_PARAMETER (cc) ;
1174 }
1175
1176 Char
lispParser_GetStringCharA(register TLispParser * pParser)1177 lispParser_GetStringCharA (
1178 register TLispParser* pParser)
1179 {
1180 register char cc ;
1181
1182 if (pParser->m_src.m_stringA.m_iRest <= 0)
1183 return (Char) EOF ;
1184
1185 cc = *pParser->m_src.m_stringA.m_pHead ++ ;
1186 pParser->m_src.m_stringA.m_iRest -- ;
1187 return Char_MakeAscii (cc) ;
1188 }
1189
1190 int
lispParser_UngetStringCharA(register TLispParser * pParser,register Char cc)1191 lispParser_UngetStringCharA (
1192 register TLispParser* pParser,
1193 register Char cc)
1194 {
1195 if (pParser->m_src.m_stringA.m_pHead <= pParser->m_src.m_stringA.m_pStringTop)
1196 return -1 ;
1197
1198 pParser->m_src.m_stringA.m_pHead -- ;
1199 pParser->m_src.m_stringA.m_iRest ++ ;
1200 return 0 ;
1201
1202 UNREFERENCED_PARAMETER (cc) ;
1203 }
1204
1205 Char
lispParser_GetFileChar(register TLispParser * pParser)1206 lispParser_GetFileChar (
1207 register TLispParser* pParser)
1208 {
1209 register Char cc ;
1210
1211 if (pParser->m_src.m_file.m_iBufUsage > 0) {
1212 cc = pParser->m_src.m_file.m_achBuf [-- pParser->m_src.m_file.m_iBufUsage] ;
1213 } else {
1214 cc = KFile_Getc (pParser->m_src.m_file.m_pFile) ;
1215 }
1216 return cc ;
1217 }
1218
1219 int
lispParser_UngetFileChar(register TLispParser * pParser,register Char cc)1220 lispParser_UngetFileChar (
1221 register TLispParser* pParser,
1222 register Char cc)
1223 {
1224 if (pParser->m_src.m_file.m_iBufUsage < MAX_UNGETC_BUF) {
1225 pParser->m_src.m_file.m_achBuf [pParser->m_src.m_file.m_iBufUsage ++] = cc ;
1226 return 0 ;
1227 }
1228 return -1 ;
1229 }
1230
1231