CRS.mod 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372
  1. IMPLEMENTATION MODULE CRS;
  2. (* Scanner generated by Coco/R - assuming FileIO library will be available. *)
  3. IMPORT FileIO, Storage;
  4. CONST
  5. noSYMB = 41; (*error token code*)
  6. (* not only for errors but also for not finished states of scanner analysis *)
  7. eof = 32C (* MS-DOS Keyboard eof char *);
  8. EOF = FileIO.EOF;
  9. EOL = FileIO.CR;
  10. CR = FileIO.CR;
  11. LF = FileIO.LF;
  12. Long0 = FileIO.Long0;
  13. Long1 = FileIO.Long1;
  14. BlkSize = 16384;
  15. TYPE
  16. BufBlock = ARRAY [0 .. BlkSize-1] OF CHAR;
  17. Buffer = ARRAY [0 .. 31] OF POINTER TO BufBlock;
  18. StartTable = ARRAY [0 .. 255] OF INTEGER;
  19. GetCH = PROCEDURE (INT32): CHAR;
  20. VAR
  21. lastCh,
  22. ch: CHAR; (*current input character*)
  23. curLine: INTEGER; (*current input line (may be higher than line)*)
  24. lineStart: INT32; (*start position of current line*)
  25. apx: INT32; (*length of appendix (CONTEXT phrase)*)
  26. oldEols: INTEGER; (*number of EOLs in a comment*)
  27. bp, bp0: INT32; (*current position in buf
  28. (bp0: position of current token)*)
  29. LBlkSize: INT32; (*BlkSize*)
  30. inputLen: INT32; (*source file size*)
  31. buf: Buffer; (*source buffer for low-level access*)
  32. start: StartTable; (*start state for every character*)
  33. CurrentCh: GetCH;
  34. PROCEDURE ORDL (n: INT32): CARDINAL;
  35. BEGIN
  36. RETURN FileIO.ORDL(n)
  37. END ORDL;
  38. PROCEDURE Err (nr, line, col: INTEGER; pos: INT32);
  39. BEGIN
  40. INC(errors)
  41. END Err;
  42. PROCEDURE NextCh;
  43. (* Return global variable ch *)
  44. BEGIN
  45. lastCh := ch; INC(bp); ch := CurrentCh(bp);
  46. IF (ch = EOL) OR (ch = FileIO.LF) AND (lastCh # EOL) THEN
  47. INC(curLine); lineStart := bp
  48. END
  49. END NextCh;
  50. PROCEDURE Comment (): BOOLEAN;
  51. VAR
  52. level, startLine: INTEGER;
  53. oldLineStart: INT32;
  54. BEGIN
  55. level := 1; startLine := curLine; oldLineStart := lineStart;
  56. IF (ch = "/") THEN
  57. NextCh;
  58. IF (ch = "*") THEN
  59. NextCh;
  60. LOOP
  61. IF (ch = "*") THEN
  62. NextCh;
  63. IF (ch = "/") THEN
  64. DEC(level); NextCh;
  65. IF level = 0 THEN RETURN TRUE END
  66. END;
  67. ELSIF ch = EOF THEN RETURN FALSE
  68. ELSE NextCh END;
  69. END; (* LOOP *)
  70. ELSE
  71. IF (ch = CR) OR (ch = LF) THEN
  72. DEC(curLine); lineStart := oldLineStart
  73. END;
  74. DEC(bp); ch := lastCh;
  75. END;
  76. END;
  77. IF (ch = "(") THEN
  78. NextCh;
  79. IF (ch = "*") THEN
  80. NextCh;
  81. LOOP
  82. IF (ch = "*") THEN
  83. NextCh;
  84. IF (ch = ")") THEN
  85. DEC(level); NextCh;
  86. IF level = 0 THEN RETURN TRUE END
  87. END;
  88. ELSIF (ch = "(") THEN
  89. NextCh;
  90. IF (ch = "*") THEN INC(level); NextCh END;
  91. ELSIF ch = EOF THEN RETURN FALSE
  92. ELSE NextCh END;
  93. END; (* LOOP *)
  94. ELSE
  95. IF (ch = CR) OR (ch = LF) THEN
  96. DEC(curLine); lineStart := oldLineStart
  97. END;
  98. DEC(bp); ch := lastCh;
  99. END;
  100. END;
  101. RETURN FALSE;
  102. END Comment;
  103. PROCEDURE Get (VAR sym: CARDINAL);
  104. VAR
  105. state: CARDINAL;
  106. PROCEDURE Equal (s: ARRAY OF CHAR): BOOLEAN;
  107. VAR
  108. i: CARDINAL;
  109. q: INT32;
  110. BEGIN
  111. IF nextLen # FileIO.SLENGTH(s) THEN RETURN FALSE END;
  112. i := 1; q := bp0; INC(q);
  113. WHILE i < nextLen DO
  114. IF CurrentCh(q) # s[i] THEN RETURN FALSE END;
  115. INC(i); INC(q)
  116. END;
  117. RETURN TRUE
  118. END Equal;
  119. PROCEDURE CheckLiteral;
  120. BEGIN
  121. CASE CurrentCh(bp0) OF
  122. "A": IF Equal("ANY") THEN sym := 23;
  123. END
  124. | "C": IF Equal("CASE") THEN sym := 19;
  125. ELSIF Equal("CHARACTERS") THEN sym := 10;
  126. ELSIF Equal("CHR") THEN sym := 24;
  127. ELSIF Equal("COMMENTS") THEN sym := 14;
  128. ELSIF Equal("COMPILER") THEN sym := 5;
  129. ELSIF Equal("CONTEXT") THEN sym := 34;
  130. END
  131. | "E": IF Equal("END") THEN sym := 9;
  132. END
  133. | "F": IF Equal("FROM") THEN sym := 15;
  134. END
  135. | "I": IF Equal("IGNORE") THEN sym := 18;
  136. END
  137. | "N": IF Equal("NAMES") THEN sym := 12;
  138. ELSIF Equal("NESTED") THEN sym := 17;
  139. END
  140. | "P": IF Equal("PRAGMAS") THEN sym := 13;
  141. ELSIF Equal("PRODUCTIONS") THEN sym := 6;
  142. END
  143. | "S": IF Equal("SYNC") THEN sym := 33;
  144. END
  145. | "T": IF Equal("TO") THEN sym := 16;
  146. ELSIF Equal("TOKENS") THEN sym := 11;
  147. END
  148. | "W": IF Equal("WEAK") THEN sym := 28;
  149. END
  150. ELSE
  151. END
  152. END CheckLiteral;
  153. BEGIN (*Get*)
  154. WHILE (ch = ' ') OR
  155. ((ch >= CHR(9)) & (ch <= CHR(10)) OR
  156. (ch = CHR(13))) DO NextCh END;
  157. IF ((ch = "/") OR (ch = "(")) & Comment() THEN Get(sym); RETURN END;
  158. pos := nextPos; nextPos := bp;
  159. col := nextCol; nextCol := FileIO.INTL(bp - lineStart);
  160. line := nextLine; nextLine := curLine;
  161. len := nextLen; nextLen := 0;
  162. apx := FileIO.Long0; state := start[ORD(ch)]; bp0 := bp;
  163. LOOP
  164. NextCh; INC(nextLen);
  165. CASE state OF
  166. 1: IF ((ch >= "0") & (ch <= "9") OR
  167. (ch >= "A") & (ch <= "Z") OR
  168. (ch = "_") OR
  169. (ch >= "a") & (ch <= "z")) THEN
  170. ELSE sym := 1; CheckLiteral; RETURN
  171. END;
  172. | 2: sym := 2; RETURN
  173. | 3: sym := 3; RETURN
  174. | 4: IF ((ch >= "0") & (ch <= "9")) THEN
  175. ELSE sym := 4; RETURN
  176. END;
  177. | 5: IF ((ch >= "0") & (ch <= "9") OR
  178. (ch >= "A") & (ch <= "Z") OR
  179. (ch = "_") OR
  180. (ch >= "a") & (ch <= "z")) THEN
  181. ELSE sym := 42; RETURN
  182. END;
  183. | 6: IF ((ch = CHR(0)) OR
  184. (ch >= " ") & (ch <= "!") OR
  185. (ch >= "#")) THEN
  186. ELSIF ((ch = CHR(10)) OR
  187. (ch = CHR(13))) THEN state := 3;
  188. ELSIF (ch = '"') THEN state := 2;
  189. ELSE sym := noSYMB; RETURN
  190. END;
  191. | 7: IF ((ch = CHR(0)) OR
  192. (ch >= " ") & (ch <= "&") OR
  193. (ch >= "(")) THEN
  194. ELSIF ((ch = CHR(10)) OR
  195. (ch = CHR(13))) THEN state := 3;
  196. ELSIF (ch = "'") THEN state := 2;
  197. ELSE sym := noSYMB; RETURN
  198. END;
  199. | 8: sym := 7; RETURN
  200. | 9: IF (ch = ".") THEN state := 12;
  201. ELSIF (ch = ">") THEN state := 23;
  202. ELSIF (ch = ")") THEN state := 25;
  203. ELSE sym := 8; RETURN
  204. END;
  205. | 10: sym := 20; RETURN
  206. | 11: sym := 21; RETURN
  207. | 12: sym := 22; RETURN
  208. | 13: IF (ch = ".") THEN state := 24;
  209. ELSE sym := 25; RETURN
  210. END;
  211. | 14: sym := 26; RETURN
  212. | 15: sym := 27; RETURN
  213. | 16: sym := 29; RETURN
  214. | 17: sym := 30; RETURN
  215. | 18: sym := 31; RETURN
  216. | 19: sym := 32; RETURN
  217. | 20: IF (ch = ".") THEN state := 22;
  218. ELSE sym := 35; RETURN
  219. END;
  220. | 21: sym := 36; RETURN
  221. | 22: sym := 37; RETURN
  222. | 23: sym := 38; RETURN
  223. | 24: sym := 39; RETURN
  224. | 25: sym := 40; RETURN
  225. | 26: sym := 0; ch := 0C; DEC(bp); RETURN
  226. ELSE sym := noSYMB; RETURN (*NextCh already done*)
  227. END
  228. END
  229. END Get;
  230. PROCEDURE GetString (pos: INT32; len: CARDINAL; VAR s: ARRAY OF CHAR);
  231. VAR
  232. i: CARDINAL;
  233. p: INT32;
  234. BEGIN
  235. IF len > HIGH(s) THEN len := HIGH(s) END;
  236. p := pos; i := 0;
  237. WHILE i < len DO
  238. s[i] := CharAt(p); INC(i); INC(p)
  239. END;
  240. s[len] := 0C;
  241. END GetString;
  242. PROCEDURE GetName (pos: INT32; len: CARDINAL; VAR s: ARRAY OF CHAR);
  243. VAR
  244. i: CARDINAL;
  245. p: INT32;
  246. BEGIN
  247. IF len > HIGH(s) THEN len := HIGH(s) END;
  248. p := pos; i := 0;
  249. WHILE i < len DO
  250. s[i] := CurrentCh(p); INC(i); INC(p)
  251. END;
  252. s[len] := 0C;
  253. END GetName;
  254. PROCEDURE CharAt (pos: INT32): CHAR;
  255. VAR
  256. ch: CHAR;
  257. BEGIN
  258. IF pos >= inputLen THEN RETURN FileIO.EOF END;
  259. ch := buf[FileIO.ORDL(pos DIV LBlkSize)]^[FileIO.ORDL(pos MOD LBlkSize)];
  260. IF ch # eof THEN RETURN ch ELSE RETURN FileIO.EOF END
  261. END CharAt;
  262. PROCEDURE CapChAt (pos: INT32): CHAR;
  263. VAR
  264. ch: CHAR;
  265. BEGIN
  266. IF pos >= inputLen THEN RETURN FileIO.EOF END;
  267. ch := CAP(buf[FileIO.ORDL(pos DIV LBlkSize)]^[FileIO.ORDL(pos MOD LBlkSize)]);
  268. IF ch # eof THEN RETURN ch ELSE RETURN FileIO.EOF END
  269. END CapChAt;
  270. PROCEDURE Reset;
  271. VAR
  272. len: INT32;
  273. i, read: CARDINAL;
  274. BEGIN (*assert: src has been opened*)
  275. len := FileIO.Length(src); i := 0; inputLen := len;
  276. WHILE len > LBlkSize DO
  277. Storage.ALLOCATE(buf[i], BlkSize);
  278. read := BlkSize; FileIO.ReadBytes(src, buf[i]^, read);
  279. len := len - FileIO.INT(read); INC(i)
  280. END;
  281. Storage.ALLOCATE(buf[i], FileIO.ORDL(len) + 1);
  282. read := FileIO.ORDL(len); FileIO.ReadBytes(src, buf[i]^, read);
  283. buf[i]^[read] := EOF;
  284. curLine := 1; lineStart := -FileIO.Long2; bp := -FileIO.Long1;
  285. oldEols := 0; apx := FileIO.Long0; errors := 0;
  286. NextCh;
  287. END Reset;
  288. BEGIN
  289. CurrentCh := CharAt;
  290. start[ 0] := 26; start[ 1] := 27; start[ 2] := 27; start[ 3] := 27;
  291. start[ 4] := 27; start[ 5] := 27; start[ 6] := 27; start[ 7] := 27;
  292. start[ 8] := 27; start[ 9] := 27; start[ 10] := 27; start[ 11] := 27;
  293. start[ 12] := 27; start[ 13] := 27; start[ 14] := 27; start[ 15] := 27;
  294. start[ 16] := 27; start[ 17] := 27; start[ 18] := 27; start[ 19] := 27;
  295. start[ 20] := 27; start[ 21] := 27; start[ 22] := 27; start[ 23] := 27;
  296. start[ 24] := 27; start[ 25] := 27; start[ 26] := 27; start[ 27] := 27;
  297. start[ 28] := 27; start[ 29] := 27; start[ 30] := 27; start[ 31] := 27;
  298. start[ 32] := 27; start[ 33] := 27; start[ 34] := 6; start[ 35] := 27;
  299. start[ 36] := 5; start[ 37] := 27; start[ 38] := 27; start[ 39] := 7;
  300. start[ 40] := 13; start[ 41] := 14; start[ 42] := 27; start[ 43] := 10;
  301. start[ 44] := 27; start[ 45] := 11; start[ 46] := 9; start[ 47] := 27;
  302. start[ 48] := 4; start[ 49] := 4; start[ 50] := 4; start[ 51] := 4;
  303. start[ 52] := 4; start[ 53] := 4; start[ 54] := 4; start[ 55] := 4;
  304. start[ 56] := 4; start[ 57] := 4; start[ 58] := 27; start[ 59] := 27;
  305. start[ 60] := 20; start[ 61] := 8; start[ 62] := 21; start[ 63] := 27;
  306. start[ 64] := 27; start[ 65] := 1; start[ 66] := 1; start[ 67] := 1;
  307. start[ 68] := 1; start[ 69] := 1; start[ 70] := 1; start[ 71] := 1;
  308. start[ 72] := 1; start[ 73] := 1; start[ 74] := 1; start[ 75] := 1;
  309. start[ 76] := 1; start[ 77] := 1; start[ 78] := 1; start[ 79] := 1;
  310. start[ 80] := 1; start[ 81] := 1; start[ 82] := 1; start[ 83] := 1;
  311. start[ 84] := 1; start[ 85] := 1; start[ 86] := 1; start[ 87] := 1;
  312. start[ 88] := 1; start[ 89] := 1; start[ 90] := 1; start[ 91] := 16;
  313. start[ 92] := 27; start[ 93] := 17; start[ 94] := 27; start[ 95] := 1;
  314. start[ 96] := 27; start[ 97] := 1; start[ 98] := 1; start[ 99] := 1;
  315. start[100] := 1; start[101] := 1; start[102] := 1; start[103] := 1;
  316. start[104] := 1; start[105] := 1; start[106] := 1; start[107] := 1;
  317. start[108] := 1; start[109] := 1; start[110] := 1; start[111] := 1;
  318. start[112] := 1; start[113] := 1; start[114] := 1; start[115] := 1;
  319. start[116] := 1; start[117] := 1; start[118] := 1; start[119] := 1;
  320. start[120] := 1; start[121] := 1; start[122] := 1; start[123] := 18;
  321. start[124] := 15; start[125] := 19; start[126] := 27; start[127] := 27;
  322. start[128] := 27; start[129] := 27; start[130] := 27; start[131] := 27;
  323. start[132] := 27; start[133] := 27; start[134] := 27; start[135] := 27;
  324. start[136] := 27; start[137] := 27; start[138] := 27; start[139] := 27;
  325. start[140] := 27; start[141] := 27; start[142] := 27; start[143] := 27;
  326. start[144] := 27; start[145] := 27; start[146] := 27; start[147] := 27;
  327. start[148] := 27; start[149] := 27; start[150] := 27; start[151] := 27;
  328. start[152] := 27; start[153] := 27; start[154] := 27; start[155] := 27;
  329. start[156] := 27; start[157] := 27; start[158] := 27; start[159] := 27;
  330. start[160] := 27; start[161] := 27; start[162] := 27; start[163] := 27;
  331. start[164] := 27; start[165] := 27; start[166] := 27; start[167] := 27;
  332. start[168] := 27; start[169] := 27; start[170] := 27; start[171] := 27;
  333. start[172] := 27; start[173] := 27; start[174] := 27; start[175] := 27;
  334. start[176] := 27; start[177] := 27; start[178] := 27; start[179] := 27;
  335. start[180] := 27; start[181] := 27; start[182] := 27; start[183] := 27;
  336. start[184] := 27; start[185] := 27; start[186] := 27; start[187] := 27;
  337. start[188] := 27; start[189] := 27; start[190] := 27; start[191] := 27;
  338. start[192] := 27; start[193] := 27; start[194] := 27; start[195] := 27;
  339. start[196] := 27; start[197] := 27; start[198] := 27; start[199] := 27;
  340. start[200] := 27; start[201] := 27; start[202] := 27; start[203] := 27;
  341. start[204] := 27; start[205] := 27; start[206] := 27; start[207] := 27;
  342. start[208] := 27; start[209] := 27; start[210] := 27; start[211] := 27;
  343. start[212] := 27; start[213] := 27; start[214] := 27; start[215] := 27;
  344. start[216] := 27; start[217] := 27; start[218] := 27; start[219] := 27;
  345. start[220] := 27; start[221] := 27; start[222] := 27; start[223] := 27;
  346. start[224] := 27; start[225] := 27; start[226] := 27; start[227] := 27;
  347. start[228] := 27; start[229] := 27; start[230] := 27; start[231] := 27;
  348. start[232] := 27; start[233] := 27; start[234] := 27; start[235] := 27;
  349. start[236] := 27; start[237] := 27; start[238] := 27; start[239] := 27;
  350. start[240] := 27; start[241] := 27; start[242] := 27; start[243] := 27;
  351. start[244] := 27; start[245] := 27; start[246] := 27; start[247] := 27;
  352. start[248] := 27; start[249] := 27; start[250] := 27; start[251] := 27;
  353. start[252] := 27; start[253] := 27; start[254] := 27; start[255] := 27;
  354. Error := Err; LBlkSize := FileIO.INT(BlkSize); lastCh := EOF;
  355. END CRS.