2 //**************************************************************************
\r
6 //**************************************************************************
\r
8 // HEADER FILES ------------------------------------------------------------
\r
29 // MACROS ------------------------------------------------------------------
\r
31 #define NON_HEX_DIGIT 255
\r
32 #define MAX_NESTED_SOURCES 16
\r
34 // TYPES -------------------------------------------------------------------
\r
52 boolean incLineNumber;
\r
54 enum ImportModes prevMode;
\r
58 // EXTERNAL FUNCTION PROTOTYPES --------------------------------------------
\r
60 // PUBLIC FUNCTION PROTOTYPES ----------------------------------------------
\r
62 // PRIVATE FUNCTION PROTOTYPES ---------------------------------------------
\r
64 static int SortKeywords(const void *a, const void *b);
\r
65 static void MakeIncludePath(char *sourceName);
\r
66 static int PopNestedSource(enum ImportModes *prevMode);
\r
67 static void ProcessLetterToken(void);
\r
68 static void ProcessNumberToken(void);
\r
69 static void EvalFixedConstant(int whole);
\r
70 static void EvalHexConstant(void);
\r
71 static void EvalRadixConstant(void);
\r
72 static int DigitValue(char digit, int radix);
\r
73 static void ProcessQuoteToken(void);
\r
74 static void ProcessSpecialToken(void);
\r
75 static boolean CheckForKeyword(void);
\r
76 static boolean CheckForLineSpecial(void);
\r
77 static boolean CheckForConstant(void);
\r
78 static void NextChr(void);
\r
79 static void SkipComment(void);
\r
80 static void SkipCPPComment(void);
\r
81 static void BumpMasterSourceLine(char Chr, boolean clear); // master line - Ty 07jan2000
\r
82 static char *AddFileName(const char *name);
\r
83 static int OctalChar();
\r
85 // EXTERNAL DATA DECLARATIONS ----------------------------------------------
\r
87 // PUBLIC DATA DEFINITIONS -------------------------------------------------
\r
89 tokenType_t tk_Token;
\r
93 U_BYTE tk_SpecialValue;
\r
94 int tk_SpecialArgCount;
\r
95 char *tk_SourceName;
\r
96 int tk_IncludedLines;
\r
97 boolean forSemicolonHack;
\r
98 char MasterSourceLine[MAX_STATEMENT_LENGTH+1]; // master line - Ty 07jan2000
\r
99 int MasterSourcePos; // master position - Ty 07jan2000
\r
100 int PrevMasterSourcePos; // previous master position - RH 09feb2000
\r
101 boolean ClearMasterSourceLine; // master clear flag - Ty 07jan2000
\r
103 // PRIVATE DATA DEFINITIONS ------------------------------------------------
\r
106 static char *FileStart;
\r
107 static char *FilePtr;
\r
108 static char *FileEnd;
\r
109 static boolean SourceOpen;
\r
110 static char ASCIIToChrCode[256];
\r
111 static byte ASCIIToHexDigit[256];
\r
112 static char TokenStringBuffer[MAX_QUOTED_LENGTH];
\r
113 static nestInfo_t OpenFiles[MAX_NESTED_SOURCES];
\r
114 static boolean AlreadyGot;
\r
115 static int NestDepth;
\r
116 static boolean IncLineNumber;
\r
117 static char IncludePath[MAX_FILE_NAME_LENGTH];
\r
118 static char *FileNames;
\r
119 static size_t FileNamesLen, FileNamesMax;
\r
121 static struct keyword_s
\r
127 { "break", TK_BREAK },
\r
128 { "case", TK_CASE },
\r
129 { "const", TK_CONST },
\r
130 { "continue", TK_CONTINUE },
\r
131 { "default", TK_DEFAULT },
\r
132 { "define", TK_DEFINE },
\r
134 { "else", TK_ELSE },
\r
136 { "goto", TK_GOTO },
\r
138 { "include", TK_INCLUDE },
\r
140 { "open", TK_OPEN },
\r
141 { "print", TK_PRINT },
\r
142 { "printbold", TK_PRINTBOLD },
\r
144 { "hudmessage", TK_HUDMESSAGE },
\r
145 { "hudmessagebold", TK_HUDMESSAGEBOLD },
\r
146 { "restart", TK_RESTART },
\r
147 { "script", TK_SCRIPT },
\r
148 { "special", TK_SPECIAL },
\r
150 { "suspend", TK_SUSPEND },
\r
151 { "switch", TK_SWITCH },
\r
152 { "terminate", TK_TERMINATE },
\r
153 { "until", TK_UNTIL },
\r
154 { "void", TK_VOID },
\r
155 { "while", TK_WHILE },
\r
156 { "world", TK_WORLD },
\r
157 { "global", TK_GLOBAL },
\r
158 // [BC] Start Skulltag tokens.
\r
159 { "respawn", TK_RESPAWN },
\r
160 { "death", TK_DEATH },
\r
161 { "enter", TK_ENTER },
\r
162 { "pickup", TK_PICKUP },
\r
163 { "bluereturn", TK_BLUERETURN },
\r
164 { "redreturn", TK_REDRETURN },
\r
165 { "whitereturn", TK_WHITERETURN },
\r
166 // [BC] End Skulltag tokens.
\r
167 { "nocompact", TK_NOCOMPACT },
\r
168 { "lightning", TK_LIGHTNING },
\r
169 { "createtranslation", TK_CREATETRANSLATION },
\r
170 { "function", TK_FUNCTION },
\r
171 { "return", TK_RETURN },
\r
172 { "wadauthor", TK_WADAUTHOR },
\r
173 { "nowadauthor", TK_NOWADAUTHOR },
\r
174 { "acs_executewait", TK_ACSEXECUTEWAIT },
\r
175 { "encryptstrings", TK_ENCRYPTSTRINGS },
\r
176 { "import", TK_IMPORT },
\r
177 { "library", TK_LIBRARY },
\r
178 { "libdefine", TK_LIBDEFINE },
\r
179 { "bool", TK_BOOL },
\r
181 { "disconnect", TK_DISCONNECT },
\r
182 { "unloading", TK_UNLOADING },
\r
183 { "static", TK_STATIC }
\r
186 #define NUM_KEYWORDS (sizeof(Keywords)/sizeof(Keywords[0]))
\r
188 // CODE --------------------------------------------------------------------
\r
190 //==========================================================================
\r
194 //==========================================================================
\r
200 for(i = 0; i < 256; i++)
\r
202 ASCIIToChrCode[i] = CHR_SPECIAL;
\r
203 ASCIIToHexDigit[i] = NON_HEX_DIGIT;
\r
205 for(i = '0'; i <= '9'; i++)
\r
207 ASCIIToChrCode[i] = CHR_NUMBER;
\r
208 ASCIIToHexDigit[i] = i-'0';
\r
210 for(i = 'A'; i <= 'F'; i++)
\r
212 ASCIIToHexDigit[i] = 10+(i-'A');
\r
214 for(i = 'a'; i <= 'f'; i++)
\r
216 ASCIIToHexDigit[i] = 10+(i-'a');
\r
218 for(i = 'A'; i <= 'Z'; i++)
\r
220 ASCIIToChrCode[i] = CHR_LETTER;
\r
222 for(i = 'a'; i <= 'z'; i++)
\r
224 ASCIIToChrCode[i] = CHR_LETTER;
\r
226 ASCIIToChrCode[ASCII_QUOTE] = CHR_QUOTE;
\r
227 ASCIIToChrCode[ASCII_UNDERSCORE] = CHR_LETTER;
\r
228 ASCIIToChrCode[EOF_CHARACTER] = CHR_EOF;
\r
229 tk_String = TokenStringBuffer;
\r
230 IncLineNumber = FALSE;
\r
231 tk_IncludedLines = 0;
\r
232 SourceOpen = FALSE;
\r
233 *MasterSourceLine = '\0'; // master line - Ty 07jan2000
\r
234 MasterSourcePos = 0; // master position - Ty 07jan2000
\r
235 ClearMasterSourceLine = TRUE; // clear the line to start
\r
236 qsort (Keywords, NUM_KEYWORDS, sizeof(Keywords[0]), SortKeywords);
\r
237 FileNames = MS_Alloc(4096, ERR_OUT_OF_MEMORY);
\r
239 FileNamesMax = 4096;
\r
242 //==========================================================================
\r
246 //==========================================================================
\r
248 static int SortKeywords(const void *a, const void *b)
\r
250 return strcmp (((struct keyword_s *)a)->name,
\r
251 ((struct keyword_s *)b)->name);
\r
254 //==========================================================================
\r
258 //==========================================================================
\r
260 void TK_OpenSource(char *fileName)
\r
265 size = MS_LoadFile(fileName, &FileStart);
\r
266 tk_SourceName = AddFileName(fileName);
\r
267 MakeIncludePath(fileName);
\r
269 FileEnd = FileStart+size;
\r
270 FilePtr = FileStart;
\r
272 tk_Token = TK_NONE;
\r
273 AlreadyGot = FALSE;
\r
278 //==========================================================================
\r
282 //==========================================================================
\r
284 static char *AddFileName(const char *name)
\r
286 size_t len = strlen(name) + 1;
\r
289 if (FileNamesLen + len > FileNamesMax)
\r
291 FileNames = MS_Alloc(FileNamesMax, ERR_OUT_OF_MEMORY);
\r
294 namespot = FileNames + FileNamesLen;
\r
295 memcpy(namespot, name, len);
\r
296 FileNamesLen += len;
\r
300 //==========================================================================
\r
304 //==========================================================================
\r
306 static void MakeIncludePath(char *sourceName)
\r
308 strcpy(IncludePath, sourceName);
\r
309 if(MS_StripFilename(IncludePath) == NO)
\r
311 IncludePath[0] = 0;
\r
314 { // Add a directory delimiter to the include path
\r
315 strcat(IncludePath, DIRECTORY_DELIMITER);
\r
319 //==========================================================================
\r
323 //==========================================================================
\r
325 void TK_Include(char *fileName)
\r
327 char sourceName[MAX_FILE_NAME_LENGTH];
\r
331 MS_Message(MSG_DEBUG, "*Including %s\n", fileName);
\r
332 if(NestDepth == MAX_NESTED_SOURCES)
\r
334 ERR_Exit(ERR_INCL_NESTING_TOO_DEEP, YES, fileName);
\r
336 info = &OpenFiles[NestDepth++];
\r
337 info->name = tk_SourceName;
\r
338 info->start = FileStart;
\r
339 info->end = FileEnd;
\r
340 info->position = FilePtr;
\r
341 info->line = tk_Line;
\r
342 info->incLineNumber = IncLineNumber;
\r
343 info->lastChar = Chr;
\r
344 info->imported = NO;
\r
345 strcpy(sourceName, IncludePath);
\r
346 strcat(sourceName, fileName);
\r
347 tk_SourceName = AddFileName(sourceName);
\r
348 size = MS_LoadFile(tk_SourceName, &FileStart);
\r
349 FileEnd = FileStart+size;
\r
350 FilePtr = FileStart;
\r
352 IncLineNumber = FALSE;
\r
353 tk_Token = TK_NONE;
\r
354 AlreadyGot = FALSE;
\r
355 BumpMasterSourceLine('x',TRUE); // dummy x
\r
359 //==========================================================================
\r
363 //==========================================================================
\r
365 void TK_Import(char *fileName, enum ImportModes prevMode)
\r
367 TK_Include (fileName);
\r
368 OpenFiles[NestDepth - 1].imported = YES;
\r
369 OpenFiles[NestDepth - 1].prevMode = prevMode;
\r
370 ImportMode = IMPORT_Importing;
\r
373 //==========================================================================
\r
377 //==========================================================================
\r
379 static int PopNestedSource(enum ImportModes *prevMode)
\r
383 MS_Message(MSG_DEBUG, "*Leaving %s\n", tk_SourceName);
\r
385 SY_FreeConstants(NestDepth);
\r
386 tk_IncludedLines += tk_Line;
\r
387 info = &OpenFiles[--NestDepth];
\r
388 tk_SourceName = info->name;
\r
389 FileStart = info->start;
\r
390 FileEnd = info->end;
\r
391 FilePtr = info->position;
\r
392 tk_Line = info->line;
\r
393 IncLineNumber = info->incLineNumber;
\r
394 Chr = info->lastChar;
\r
395 tk_Token = TK_NONE;
\r
396 AlreadyGot = FALSE;
\r
397 *prevMode = info->prevMode;
\r
398 return info->imported ? 2 : 0;
\r
401 //==========================================================================
\r
405 //==========================================================================
\r
407 void TK_CloseSource(void)
\r
414 for(i = 0; i < NestDepth; i++)
\r
416 free(OpenFiles[i].start);
\r
418 SourceOpen = FALSE;
\r
422 //==========================================================================
\r
426 //==========================================================================
\r
428 int TK_GetDepth(void)
\r
433 //==========================================================================
\r
437 //==========================================================================
\r
439 tokenType_t TK_NextToken(void)
\r
441 enum ImportModes prevMode;
\r
442 boolean validToken;
\r
444 if(AlreadyGot == TRUE)
\r
446 int t = MasterSourcePos;
\r
447 MasterSourcePos = PrevMasterSourcePos;
\r
448 PrevMasterSourcePos = t;
\r
449 AlreadyGot = FALSE;
\r
453 PrevMasterSourcePos = MasterSourcePos;
\r
456 while(Chr == ASCII_SPACE)
\r
460 switch(ASCIIToChrCode[(byte)Chr])
\r
466 ProcessLetterToken();
\r
469 ProcessNumberToken();
\r
472 ProcessQuoteToken();
\r
475 ProcessSpecialToken();
\r
478 if(tk_Token == TK_STARTCOMMENT)
\r
482 else if(tk_Token == TK_CPPCOMMENT)
\r
486 else if((tk_Token == TK_EOF) && (NestDepth > 0))
\r
488 if (PopNestedSource(&prevMode))
\r
490 ImportMode = prevMode;
\r
491 if(!ExporterFlagged)
\r
493 ERR_Exit(ERR_EXPORTER_NOT_FLAGGED, NO);
\r
502 } while(validToken == NO);
\r
506 //==========================================================================
\r
508 // TK_NextCharacter
\r
510 //==========================================================================
\r
512 int TK_NextCharacter(void)
\r
516 while(Chr == ASCII_SPACE)
\r
521 if(c == EOF_CHARACTER)
\r
529 //==========================================================================
\r
533 //==========================================================================
\r
535 void TK_SkipPast(tokenType_t token)
\r
537 while (tk_Token != token)
\r
544 //==========================================================================
\r
548 //==========================================================================
\r
550 void TK_SkipTo(tokenType_t token)
\r
552 while (tk_Token != token)
\r
558 //==========================================================================
\r
560 // TK_NextTokenMustBe
\r
562 //==========================================================================
\r
564 boolean TK_NextTokenMustBe(tokenType_t token, error_t error)
\r
566 if(TK_NextToken() != token)
\r
568 ERR_Error(error, YES);
\r
570 if(skipToken == TK_EOF)
\r
574 else if(skipToken != TK_NONE)
\r
576 TK_SkipPast(skipToken);
\r
585 //==========================================================================
\r
589 //==========================================================================
\r
591 boolean TK_TokenMustBe(tokenType_t token, error_t error)
\r
593 if (token == TK_SEMICOLON && forSemicolonHack)
\r
597 if(tk_Token != token)
\r
599 ERR_Error(error, YES);
\r
601 if(skipToken == TK_EOF)
\r
605 else if(skipToken != TK_NONE)
\r
607 while(tk_Token != skipToken)
\r
619 //==========================================================================
\r
623 //==========================================================================
\r
625 boolean TK_Member(tokenType_t *list)
\r
629 for(i = 0; list[i] != TK_NONE; i++)
\r
631 if(tk_Token == list[i])
\r
639 //==========================================================================
\r
643 //==========================================================================
\r
647 if(tk_Token != TK_NONE)
\r
649 if (AlreadyGot == FALSE)
\r
651 int t = MasterSourcePos;
\r
652 MasterSourcePos = PrevMasterSourcePos;
\r
653 PrevMasterSourcePos = t;
\r
659 //==========================================================================
\r
661 // ProcessLetterToken
\r
663 //==========================================================================
\r
665 static void ProcessLetterToken(void)
\r
671 text = TokenStringBuffer;
\r
672 while (ASCIIToChrCode[(byte)Chr] == CHR_LETTER
\r
673 || ASCIIToChrCode[(byte)Chr] == CHR_NUMBER)
\r
675 if(++i == MAX_IDENTIFIER_LENGTH)
\r
677 ERR_Error(ERR_IDENTIFIER_TOO_LONG, YES);
\r
679 if(i < MAX_IDENTIFIER_LENGTH)
\r
686 MS_StrLwr(TokenStringBuffer);
\r
687 if(CheckForKeyword() == FALSE
\r
688 && CheckForLineSpecial() == FALSE
\r
689 && CheckForConstant() == FALSE)
\r
691 tk_Token = TK_IDENTIFIER;
\r
695 //==========================================================================
\r
699 //==========================================================================
\r
701 static boolean CheckForKeyword(void)
\r
703 int min, max, probe, lexx;
\r
705 // [RH] Use a binary search
\r
707 max = NUM_KEYWORDS-1;
\r
708 probe = NUM_KEYWORDS/2;
\r
710 while (max - min >= 0)
\r
712 lexx = strcmp(tk_String, Keywords[probe].name);
\r
715 tk_Token = Keywords[probe].token;
\r
726 probe = (max-min)/2+min;
\r
731 //==========================================================================
\r
733 // CheckForLineSpecial
\r
735 //==========================================================================
\r
737 static boolean CheckForLineSpecial(void)
\r
741 sym = SY_FindGlobal(tk_String);
\r
746 if(sym->type != SY_SPECIAL)
\r
750 tk_Token = TK_LINESPECIAL;
\r
751 tk_SpecialValue = sym->info.special.value;
\r
752 tk_SpecialArgCount = sym->info.special.argCount;
\r
756 //==========================================================================
\r
758 // CheckForConstant
\r
760 //==========================================================================
\r
762 static boolean CheckForConstant(void)
\r
766 sym = SY_FindGlobal(tk_String);
\r
771 if(sym->type != SY_CONSTANT)
\r
775 tk_Token = TK_NUMBER;
\r
776 tk_Number = sym->info.constant.value;
\r
780 //==========================================================================
\r
782 // ProcessNumberToken
\r
784 //==========================================================================
\r
786 static void ProcessNumberToken(void)
\r
792 if(c == '0' && (Chr == 'x' || Chr == 'X'))
\r
793 { // Hexadecimal constant
\r
799 while(ASCIIToChrCode[(byte)Chr] == CHR_NUMBER)
\r
801 tk_Number = 10*tk_Number+(Chr-'0');
\r
806 NextChr(); // Skip period
\r
807 EvalFixedConstant(tk_Number);
\r
810 if(Chr == ASCII_UNDERSCORE)
\r
812 NextChr(); // Skip underscore
\r
813 EvalRadixConstant();
\r
816 tk_Token = TK_NUMBER;
\r
819 //==========================================================================
\r
821 // EvalFixedConstant
\r
823 //==========================================================================
\r
825 static void EvalFixedConstant(int whole)
\r
832 while(ASCIIToChrCode[(byte)Chr] == CHR_NUMBER)
\r
834 frac = 10*frac+(Chr-'0');
\r
838 tk_Number = (whole<<16)+((frac<<16)/divisor);
\r
839 tk_Token = TK_NUMBER;
\r
842 //==========================================================================
\r
846 //==========================================================================
\r
848 static void EvalHexConstant(void)
\r
851 while(ASCIIToHexDigit[(byte)Chr] != NON_HEX_DIGIT)
\r
853 tk_Number = (tk_Number<<4)+ASCIIToHexDigit[(byte)Chr];
\r
856 tk_Token = TK_NUMBER;
\r
859 //==========================================================================
\r
861 // EvalRadixConstant
\r
863 //==========================================================================
\r
865 static void EvalRadixConstant(void)
\r
871 if(radix < 2 || radix > 36)
\r
873 ERR_Error(ERR_BAD_RADIX_CONSTANT, YES, NULL);
\r
877 while((digitVal = DigitValue(Chr, radix)) != -1)
\r
879 tk_Number = radix*tk_Number+digitVal;
\r
882 tk_Token = TK_NUMBER;
\r
885 //==========================================================================
\r
889 // Returns -1 if the digit is not allowed in the specified radix.
\r
891 //==========================================================================
\r
893 static int DigitValue(char digit, int radix)
\r
895 digit = toupper(digit);
\r
896 if(digit < '0' || (digit > '9' && digit < 'A') || digit > 'Z')
\r
902 digit = 10+digit-'A';
\r
915 //==========================================================================
\r
917 // ProcessQuoteToken
\r
919 //==========================================================================
\r
921 static void ProcessQuoteToken(void)
\r
929 text = TokenStringBuffer;
\r
931 while(Chr != EOF_CHARACTER)
\r
933 if(Chr == ASCII_QUOTE && escaped == 0) // [JB]
\r
937 if(++i == MAX_QUOTED_LENGTH)
\r
939 ERR_Error(ERR_STRING_TOO_LONG, YES, NULL);
\r
941 if(i < MAX_QUOTED_LENGTH)
\r
945 // escape the character after a backslash [JB]
\r
946 if(Chr == ASCII_BACKSLASH)
\r
947 escaped ^= (Chr == ASCII_BACKSLASH);
\r
953 if(Chr == ASCII_QUOTE)
\r
957 tk_Token = TK_STRING;
\r
960 //==========================================================================
\r
962 // ProcessSpecialToken
\r
964 //==========================================================================
\r
966 static void ProcessSpecialToken(void)
\r
978 tk_Token = TK_ADDASSIGN;
\r
986 tk_Token = TK_PLUS;
\r
994 tk_Token = TK_SUBASSIGN;
\r
1002 tk_Token = TK_MINUS;
\r
1010 tk_Token = TK_MULASSIGN;
\r
1014 tk_Token = TK_ENDCOMMENT;
\r
1018 tk_Token = TK_ASTERISK;
\r
1026 tk_Token = TK_DIVASSIGN;
\r
1030 tk_Token = TK_CPPCOMMENT;
\r
1033 tk_Token = TK_STARTCOMMENT;
\r
1037 tk_Token = TK_SLASH;
\r
1044 tk_Token = TK_MODASSIGN;
\r
1049 tk_Token = TK_PERCENT;
\r
1060 tk_Token = TK_ASSIGN;
\r
1069 else if(Chr == '<')
\r
1074 tk_Token = TK_LSASSIGN;
\r
1079 tk_Token = TK_LSHIFT;
\r
1094 else if(Chr == '>')
\r
1099 tk_Token = TK_RSASSIGN;
\r
1104 tk_Token = TK_RSHIFT;
\r
1120 tk_Token = TK_NOT;
\r
1126 tk_Token = TK_ANDLOGICAL;
\r
1129 else if(Chr == '=')
\r
1131 tk_Token = TK_ANDASSIGN;
\r
1136 tk_Token = TK_ANDBITWISE;
\r
1142 tk_Token = TK_ORLOGICAL;
\r
1145 else if(Chr == '=')
\r
1147 tk_Token = TK_ORASSIGN;
\r
1152 tk_Token = TK_ORBITWISE;
\r
1156 tk_Token = TK_LPAREN;
\r
1159 tk_Token = TK_RPAREN;
\r
1162 tk_Token = TK_LBRACE;
\r
1165 tk_Token = TK_RBRACE;
\r
1168 tk_Token = TK_LBRACKET;
\r
1171 tk_Token = TK_RBRACKET;
\r
1174 tk_Token = TK_COLON;
\r
1177 tk_Token = TK_SEMICOLON;
\r
1180 tk_Token = TK_COMMA;
\r
1183 tk_Token = TK_PERIOD;
\r
1186 tk_Token = TK_NUMBERSIGN;
\r
1191 tk_Token = TK_EORASSIGN;
\r
1196 tk_Token = TK_EORBITWISE;
\r
1200 tk_Token = TK_TILDE;
\r
1208 case '0': case '1': case '2': case '3':
\r
1209 case '4': case '5': case '6': case '7':
\r
1210 tk_Number = OctalChar();
\r
1212 case 'x': case 'X':
\r
1214 EvalHexConstant();
\r
1217 ERR_Exit(ERR_BAD_CHARACTER_CONSTANT, YES, NULL);
\r
1246 ERR_Exit(ERR_BAD_CHARACTER_CONSTANT, YES, NULL);
\r
1248 tk_Token = TK_NUMBER;
\r
1250 else if(Chr == '\'')
\r
1252 ERR_Exit(ERR_BAD_CHARACTER_CONSTANT, YES, NULL);
\r
1257 tk_Token = TK_NUMBER;
\r
1262 ERR_Exit(ERR_BAD_CHARACTER_CONSTANT, YES, NULL);
\r
1267 ERR_Exit(ERR_BAD_CHARACTER, YES, NULL);
\r
1272 //==========================================================================
\r
1276 //==========================================================================
\r
1278 static void NextChr(void)
\r
1280 if(FilePtr >= FileEnd)
\r
1282 Chr = EOF_CHARACTER;
\r
1285 if(IncLineNumber == TRUE)
\r
1288 IncLineNumber = FALSE;
\r
1289 BumpMasterSourceLine('x',TRUE); // dummy x
\r
1292 if(Chr < ASCII_SPACE && Chr >= 0) // Allow high ASCII characters
\r
1296 IncLineNumber = TRUE;
\r
1298 Chr = ASCII_SPACE;
\r
1300 BumpMasterSourceLine(Chr,FALSE);
\r
1303 //==========================================================================
\r
1305 // PeekChr // [JB]
\r
1307 //==========================================================================
\r
1309 static int PeekChr(void)
\r
1312 if(FilePtr >= FileEnd)
\r
1314 return EOF_CHARACTER;
\r
1317 if(ch < ASCII_SPACE && ch >= 0) // Allow high ASCII characters
\r
1324 //==========================================================================
\r
1326 // OctalChar // [JB]
\r
1328 //==========================================================================
\r
1330 static int OctalChar()
\r
1333 int code = Chr - '0';
\r
1334 while(digits < 4 && PeekChr() >= '0' && PeekChr() <= '7')
\r
1337 code = (code << 3) + Chr - '0';
\r
1342 //==========================================================================
\r
1346 //==========================================================================
\r
1348 void SkipComment(void)
\r
1353 while(Chr != EOF_CHARACTER)
\r
1355 if(first == TRUE && Chr == '/')
\r
1359 first = (Chr == '*');
\r
1365 //==========================================================================
\r
1369 //==========================================================================
\r
1371 void SkipCPPComment(void)
\r
1373 while(FilePtr < FileEnd)
\r
1375 if(*FilePtr++ == '\n')
\r
1378 BumpMasterSourceLine('x',TRUE); // dummy x
\r
1385 //==========================================================================
\r
1387 // BumpMasterSourceLine
\r
1389 //==========================================================================
\r
1391 void BumpMasterSourceLine(char Chr, boolean clear) // master line - Ty 07jan2000
\r
1393 if (ClearMasterSourceLine) // set to clear last time, clear now for first character
\r
1395 *MasterSourceLine = '\0';
\r
1396 MasterSourcePos = 0;
\r
1397 ClearMasterSourceLine = FALSE;
\r
1401 ClearMasterSourceLine = TRUE;
\r
1405 if (MasterSourcePos < MAX_STATEMENT_LENGTH)
\r
1406 MasterSourceLine[MasterSourcePos++] = Chr;
\r
1410 //==========================================================================
\r
1414 //==========================================================================
\r
1416 void TK_SkipLine(void)
\r
1418 char *sourcenow = tk_SourceName;
\r
1419 int linenow = tk_Line;
\r
1420 do TK_NextToken(); while (tk_Line == linenow && tk_SourceName == sourcenow);
\r