PageRenderTime 66ms CodeModel.GetById 32ms RepoModel.GetById 1ms app.codeStats 0ms

/codemp/icarus/Tokenizer.cpp

https://github.com/Stoiss/jaMME
C++ | 2868 lines | 2621 code | 190 blank | 57 comment | 313 complexity | 305fd183c2937cf8e081fa80a387f557 MD5 | raw file
Possible License(s): GPL-2.0
  1. // Tokenizer.cpp
  2. #ifndef NOT_USING_MODULES
  3. // !!! if you are not using modules, read BELOW !!!
  4. #include "module.h" // if you are not using modules,
  5. // create an empty Module.h in your
  6. // project -- use of modules allows
  7. // the error handler to be overridden
  8. // with a custom CErrHandler
  9. #endif
  10. #include "tokenizer.h"
  11. #pragma warning(disable : 4100) //unreferenced formal parameter
  12. #pragma warning(disable : 4127) //conditional expression is constant
  13. #pragma warning(disable : 4189) //local variable is initialized but not referenced
  14. #pragma warning(disable : 4244) //conversion from x to x, possible loss of data
  15. #ifndef _WIN32
  16. #include <stdio.h>
  17. #include <stdlib.h>
  18. #endif
  19. enum
  20. {
  21. DIR_INCLUDE = TK_USERDEF,
  22. DIR_IFDEF,
  23. DIR_IFNDEF,
  24. DIR_ENDIF,
  25. DIR_ELSE,
  26. DIR_DEFINE,
  27. DIR_UNDEFINE,
  28. };
  29. keywordArray_t CTokenizer::directiveKeywords[] =
  30. {
  31. "include", DIR_INCLUDE,
  32. "ifdef", DIR_IFDEF,
  33. "ifndef", DIR_IFNDEF,
  34. "endif", DIR_ENDIF,
  35. "else", DIR_ELSE,
  36. "define", DIR_DEFINE,
  37. "undefine", DIR_UNDEFINE,
  38. "", TK_EOF,
  39. };
  40. keywordArray_t CTokenizer::errorMessages[] =
  41. {
  42. "No Error", TKERR_NONE,
  43. "Unknown Error", TKERR_UNKNOWN,
  44. "Buffer creation failed", TKERR_BUFFERCREATE,
  45. "Unrecognized symbol", TKERR_UNRECOGNIZEDSYMBOL,
  46. "Duplicate symbol", TKERR_DUPLICATESYMBOL,
  47. "String length exceeded", TKERR_STRINGLENGTHEXCEEDED,
  48. "Identifier length exceeded", TKERR_IDENTIFIERLENGTHEXCEEDED,
  49. "Expected integer", TKERR_EXPECTED_INTEGER,
  50. "Expected identifier", TKERR_EXPECTED_IDENTIFIER,
  51. "Expected string", TKERR_EXPECTED_STRING,
  52. "Expected char", TKERR_EXPECTED_CHAR,
  53. "Expected float", TKERR_EXPECTED_FLOAT,
  54. "Unexpected token", TKERR_UNEXPECTED_TOKEN,
  55. "Invalid directive", TKERR_INVALID_DIRECTIVE,
  56. "Include file not found", TKERR_INCLUDE_FILE_NOTFOUND,
  57. "Unmatched directive", TKERR_UNMATCHED_DIRECTIVE,
  58. "", TKERR_USERERROR,
  59. };
  60. //
  61. // CSymbol
  62. //
  63. CSymbol::CSymbol()
  64. {
  65. }
  66. CSymbol::~CSymbol()
  67. {
  68. }
  69. CSymbol* CSymbol::Create(LPCTSTR symbolName)
  70. {
  71. CSymbol* retval = new CSymbol();
  72. retval->Init(symbolName);
  73. return retval;
  74. }
  75. LPCTSTR CSymbol::GetName()
  76. {
  77. if (m_symbolName == NULL)
  78. {
  79. return "";
  80. }
  81. return m_symbolName;
  82. }
  83. void CSymbol::Init(LPCTSTR symbolName)
  84. {
  85. m_symbolName = (char*)malloc(strlen(symbolName) + 1);
  86. // ASSERT(m_symbolName);
  87. strcpy(m_symbolName, symbolName);
  88. }
  89. void CSymbol::Delete()
  90. {
  91. if (m_symbolName != NULL)
  92. {
  93. free(m_symbolName);
  94. m_symbolName = NULL;
  95. }
  96. delete this;
  97. }
  98. //
  99. // CDirectiveSymbol
  100. //
  101. CDirectiveSymbol::CDirectiveSymbol()
  102. {
  103. }
  104. CDirectiveSymbol::~CDirectiveSymbol()
  105. {
  106. }
  107. CDirectiveSymbol* CDirectiveSymbol::Create(LPCTSTR symbolName)
  108. {
  109. CDirectiveSymbol* retval = new CDirectiveSymbol();
  110. retval->Init(symbolName);
  111. return retval;
  112. }
  113. void CDirectiveSymbol::Init(LPCTSTR symbolName)
  114. {
  115. CSymbol::Init(symbolName);
  116. m_value = NULL;
  117. }
  118. void CDirectiveSymbol::Delete()
  119. {
  120. if (m_value != NULL)
  121. {
  122. free(m_value);
  123. m_value = NULL;
  124. }
  125. CSymbol::Delete();
  126. }
  127. void CDirectiveSymbol::SetValue(LPCTSTR value)
  128. {
  129. if (m_value != NULL)
  130. {
  131. free(m_value);
  132. }
  133. m_value = (char*)malloc(strlen(value) + 1);
  134. strcpy(m_value, value);
  135. }
  136. LPCTSTR CDirectiveSymbol::GetValue()
  137. {
  138. return m_value;
  139. }
  140. //
  141. // CIntSymbol
  142. //
  143. CIntSymbol::CIntSymbol()
  144. {
  145. }
  146. CIntSymbol* CIntSymbol::Create(LPCTSTR symbolName, int value)
  147. {
  148. CIntSymbol* retval = new CIntSymbol();
  149. retval->Init(symbolName, value);
  150. return retval;
  151. }
  152. void CIntSymbol::Delete()
  153. {
  154. CSymbol::Delete();
  155. }
  156. void CIntSymbol::Init(LPCTSTR symbolName, int value)
  157. {
  158. CSymbol::Init(symbolName);
  159. m_value = value;
  160. }
  161. int CIntSymbol::GetValue()
  162. {
  163. return m_value;
  164. }
  165. //
  166. // CSymbolTable
  167. //
  168. CSymbolTable::CSymbolTable()
  169. {
  170. Init();
  171. }
  172. CSymbolTable::~CSymbolTable()
  173. {
  174. }
  175. CSymbolTable* CSymbolTable::Create()
  176. {
  177. CSymbolTable* retval = new CSymbolTable();
  178. retval->Init();
  179. return retval;
  180. }
  181. void CSymbolTable::Init()
  182. {
  183. }
  184. void CSymbolTable::DiscardSymbols()
  185. {
  186. for (symbolmap_t::iterator isymbol = m_symbols.begin(); isymbol != m_symbols.end(); isymbol++)
  187. {
  188. (*isymbol).second->Delete();
  189. }
  190. m_symbols.erase(m_symbols.begin(), m_symbols.end());
  191. }
  192. void CSymbolTable::Delete()
  193. {
  194. DiscardSymbols();
  195. delete this;
  196. }
  197. bool CSymbolTable::AddSymbol(CSymbol* theSymbol)
  198. {
  199. LPCTSTR name = theSymbol->GetName();
  200. symbolmap_t::iterator iter = m_symbols.find(name);
  201. if (iter != m_symbols.end())
  202. {
  203. return false;
  204. }
  205. m_symbols.insert(symbolmap_t::value_type(name, theSymbol));
  206. return true;
  207. }
  208. CSymbol* CSymbolTable::FindSymbol(LPCTSTR symbolName)
  209. {
  210. symbolmap_t::iterator iter = m_symbols.find(symbolName);
  211. if (iter != m_symbols.end())
  212. {
  213. return (*iter).second;
  214. }
  215. return NULL;
  216. }
  217. CSymbol* CSymbolTable::ExtractSymbol(LPCTSTR symbolName)
  218. {
  219. symbolmap_t::iterator iter = m_symbols.find(symbolName);
  220. if (iter != m_symbols.end())
  221. {
  222. CSymbol* retval = (*iter).second;
  223. m_symbols.erase(iter);
  224. }
  225. return NULL;
  226. }
  227. void CSymbolTable::RemoveSymbol(LPCTSTR symbolName)
  228. {
  229. m_symbols.erase(symbolName);
  230. }
  231. //
  232. // CParseStream
  233. //
  234. CParseStream::CParseStream()
  235. {
  236. }
  237. CParseStream::~CParseStream()
  238. {
  239. }
  240. CParseStream* CParseStream::Create()
  241. {
  242. return NULL;
  243. }
  244. void CParseStream::Delete()
  245. {
  246. delete this;
  247. }
  248. bool CParseStream::Init()
  249. {
  250. m_next = NULL;
  251. return true;
  252. }
  253. bool CParseStream::NextChar(byte& theByte)
  254. {
  255. return false;
  256. }
  257. long CParseStream::GetRemainingSize()
  258. {
  259. return 0;
  260. }
  261. CParseStream* CParseStream::GetNext()
  262. {
  263. return m_next;
  264. }
  265. void CParseStream::SetNext(CParseStream* next)
  266. {
  267. m_next = next;
  268. }
  269. int CParseStream::GetCurLine()
  270. {
  271. return 0;
  272. }
  273. void CParseStream::GetCurFilename(char** theBuff)
  274. {
  275. *theBuff = NULL;
  276. }
  277. bool CParseStream::IsThisDefinition(void* theDefinition)
  278. {
  279. return false;
  280. }
  281. //
  282. // CParsePutBack
  283. //
  284. CParsePutBack::CParsePutBack()
  285. {
  286. }
  287. CParsePutBack::~CParsePutBack()
  288. {
  289. }
  290. CParsePutBack* CParsePutBack::Create(byte theByte, int curLine, LPCTSTR filename)
  291. {
  292. CParsePutBack* curParsePutBack = new CParsePutBack();
  293. curParsePutBack->Init(theByte, curLine, filename);
  294. return curParsePutBack;
  295. }
  296. void CParsePutBack::Delete()
  297. {
  298. if (m_curFile != NULL)
  299. {
  300. free(m_curFile);
  301. m_curFile = NULL;
  302. }
  303. delete this;
  304. }
  305. bool CParsePutBack::NextChar(byte& theByte)
  306. {
  307. if (m_consumed)
  308. {
  309. return false;
  310. }
  311. theByte = m_byte;
  312. m_consumed = true;
  313. return true;
  314. }
  315. void CParsePutBack::Init(byte theByte, int curLine, LPCTSTR filename)
  316. {
  317. CParseStream::Init();
  318. m_consumed = false;
  319. m_byte = theByte;
  320. m_curLine = curLine;
  321. if (filename != NULL)
  322. {
  323. m_curFile = (char*)malloc(strlen(filename) + 1);
  324. strcpy(m_curFile, filename);
  325. }
  326. else
  327. {
  328. m_curFile = NULL;
  329. }
  330. }
  331. long CParsePutBack::GetRemainingSize()
  332. {
  333. if (m_consumed)
  334. {
  335. return 0;
  336. }
  337. else
  338. {
  339. return 1;
  340. }
  341. }
  342. int CParsePutBack::GetCurLine()
  343. {
  344. return m_curLine;
  345. }
  346. void CParsePutBack::GetCurFilename(char** theBuff)
  347. {
  348. if (m_curFile == NULL)
  349. {
  350. *theBuff = NULL;
  351. return;
  352. }
  353. *theBuff = (char*)malloc(strlen(m_curFile) + 1);
  354. strcpy(*theBuff, m_curFile);
  355. }
  356. //
  357. // CParseFile
  358. //
  359. CParseFile::CParseFile()
  360. {
  361. }
  362. CParseFile::~CParseFile()
  363. {
  364. }
  365. CParseFile* CParseFile::Create()
  366. {
  367. CParseFile* theParseFile = new CParseFile();
  368. if ( !theParseFile->Init() )
  369. {
  370. delete theParseFile;
  371. return NULL;
  372. }
  373. return theParseFile;
  374. }
  375. CParseFile* CParseFile::Create(LPCTSTR filename, CTokenizer* tokenizer)
  376. {
  377. CParseFile* theParseFile = new CParseFile();
  378. if ( theParseFile->Init(filename, tokenizer) )
  379. return theParseFile;
  380. return NULL;
  381. }
  382. void CParseFile::Delete()
  383. {
  384. if (m_buff != NULL)
  385. {
  386. free(m_buff);
  387. m_buff = NULL;
  388. }
  389. if (m_ownsFile && (m_fileHandle != NULL))
  390. {
  391. #ifdef _WIN32
  392. CloseHandle(m_fileHandle);
  393. #else
  394. fclose(m_fileHandle);
  395. #endif
  396. m_fileHandle = NULL;
  397. }
  398. if (m_fileName != NULL)
  399. {
  400. free(m_fileName);
  401. m_fileName = NULL;
  402. }
  403. delete this;
  404. }
  405. bool CParseFile::Init()
  406. {
  407. m_fileHandle = NULL;
  408. m_buff = NULL;
  409. m_ownsFile = false;
  410. m_curByte = NULL;
  411. m_curLine = 1;
  412. m_fileName = NULL;
  413. return CParseStream::Init();
  414. }
  415. DWORD CParseFile::GetFileSize()
  416. {
  417. #ifdef _WIN32
  418. DWORD dwCur = SetFilePointer(m_fileHandle, 0L, NULL, FILE_CURRENT);
  419. DWORD dwLen = SetFilePointer(m_fileHandle, 0, NULL, FILE_END);
  420. SetFilePointer(m_fileHandle, dwCur, NULL, FILE_BEGIN);
  421. #else
  422. fseek(m_fileHandle, 0L, SEEK_END);
  423. DWORD dwLen = ftell(m_fileHandle);
  424. fseek(m_fileHandle, 0L, SEEK_SET);
  425. #endif
  426. return dwLen;
  427. }
  428. void CParseFile::Read(void* buff, UINT buffsize)
  429. {
  430. DWORD bytesRead;
  431. #ifdef _WIN32
  432. ReadFile(m_fileHandle, buff, buffsize, &bytesRead, NULL);
  433. #else
  434. fread(buff, buffsize, 1, m_fileHandle);
  435. #endif
  436. }
  437. bool CParseFile::Init(LPCTSTR filename, CTokenizer* tokenizer)
  438. {
  439. CParseStream::Init();
  440. m_fileName = (char*)malloc(strlen(filename) + 1);
  441. strcpy(m_fileName, filename);
  442. #ifdef _WIN32
  443. DWORD dwAccess = GENERIC_READ;
  444. DWORD dwShareMode = FILE_SHARE_WRITE | FILE_SHARE_READ;
  445. SECURITY_ATTRIBUTES sa;
  446. sa.nLength = sizeof(sa);
  447. sa.lpSecurityDescriptor = NULL;
  448. sa.bInheritHandle = 0;
  449. DWORD dwCreateFlag = OPEN_EXISTING;
  450. m_fileHandle = CreateFile(filename, dwAccess, dwShareMode, &sa, dwCreateFlag, FILE_ATTRIBUTE_NORMAL, NULL);
  451. if (m_fileHandle == (HANDLE)-1)
  452. {
  453. tokenizer->Error(TKERR_INCLUDE_FILE_NOTFOUND);
  454. Init();
  455. return false;
  456. }
  457. #else
  458. m_fileHandle = fopen(filename, "r+");
  459. if (m_fileHandle == NULL)
  460. {
  461. tokenizer->Error(TKERR_INCLUDE_FILE_NOTFOUND);
  462. Init();
  463. return false;
  464. }
  465. #endif
  466. m_filesize = GetFileSize();
  467. m_buff = (byte*)malloc(m_filesize);
  468. if (m_buff == NULL)
  469. {
  470. tokenizer->Error(TKERR_BUFFERCREATE);
  471. Init();
  472. return false;
  473. }
  474. Read(m_buff, m_filesize);
  475. m_curByte = 0;
  476. m_curPos = 1;
  477. m_ownsFile = true;
  478. m_curLine = 1;
  479. return true;
  480. }
  481. long CParseFile::GetRemainingSize()
  482. {
  483. return m_filesize - m_curByte;
  484. }
  485. bool CParseFile::NextChar(byte& theByte)
  486. {
  487. if (m_curByte < m_filesize)
  488. {
  489. if (m_buff[m_curByte] == '\n')
  490. {
  491. m_curLine += 1;
  492. m_curPos = 1;
  493. }
  494. else
  495. {
  496. m_curPos++;
  497. }
  498. theByte = m_buff[m_curByte++];
  499. return true;
  500. }
  501. else
  502. {
  503. return false;
  504. }
  505. }
  506. int CParseFile::GetCurLine()
  507. {
  508. return m_curLine;
  509. }
  510. void CParseFile::GetCurFilename(char** theBuff)
  511. {
  512. *theBuff = NULL;
  513. if (m_fileName != NULL)
  514. {
  515. *theBuff = (char*)malloc(strlen(m_fileName) + 1);
  516. strcpy(*theBuff, m_fileName);
  517. }
  518. }
  519. //
  520. // CParseMemory
  521. //
  522. CParseMemory::CParseMemory()
  523. {
  524. }
  525. CParseMemory::~CParseMemory()
  526. {
  527. }
  528. CParseMemory* CParseMemory::Create(byte* data, long datasize)
  529. {
  530. CParseMemory* curParse = new CParseMemory();
  531. curParse->Init(data, datasize);
  532. return curParse;
  533. }
  534. void CParseMemory::Delete()
  535. {
  536. delete this;
  537. }
  538. bool CParseMemory::NextChar(byte& theByte)
  539. {
  540. if (m_offset < m_datasize)
  541. {
  542. if (m_data[m_offset] == '\n')
  543. {
  544. m_curLine += 1;
  545. m_curPos = 1;
  546. }
  547. else
  548. {
  549. m_curPos++;
  550. }
  551. theByte = m_data[m_offset++];
  552. return true;
  553. }
  554. else
  555. {
  556. return false;
  557. }
  558. }
  559. void CParseMemory::Init(byte* data, long datasize)
  560. {
  561. m_data = data;
  562. m_curLine = 1;
  563. m_curPos = 1;
  564. m_offset = 0;
  565. m_datasize = datasize;
  566. }
  567. long CParseMemory::GetRemainingSize()
  568. {
  569. return m_datasize - m_offset;
  570. }
  571. int CParseMemory::GetCurLine()
  572. {
  573. return m_curLine;
  574. }
  575. void CParseMemory::GetCurFilename(char** theBuff)
  576. {
  577. *theBuff = NULL;
  578. }
  579. //
  580. // CParseBlock
  581. //
  582. CParseBlock::CParseBlock()
  583. {
  584. }
  585. CParseBlock::~CParseBlock()
  586. {
  587. }
  588. CParseBlock* CParseBlock::Create(byte* data, long datasize)
  589. {
  590. CParseBlock* curParse = new CParseBlock();
  591. curParse->Init(data, datasize);
  592. return curParse;
  593. }
  594. void CParseBlock::Delete()
  595. {
  596. if (m_data != NULL)
  597. {
  598. free(m_data);
  599. m_data = NULL;
  600. }
  601. delete this;
  602. }
  603. void CParseBlock::Init(byte* data, long datasize)
  604. {
  605. m_data = (byte*)malloc(datasize);
  606. memcpy(m_data, data, datasize);
  607. m_curLine = 1;
  608. m_curPos = 1;
  609. m_offset = 0;
  610. m_datasize = datasize;
  611. }
  612. //
  613. // CParseToken
  614. //
  615. CParseToken::CParseToken()
  616. {
  617. }
  618. CParseToken::~CParseToken()
  619. {
  620. }
  621. CParseToken* CParseToken::Create(CToken* token)
  622. {
  623. CParseToken* curParse = new CParseToken();
  624. curParse->Init(token);
  625. return curParse;
  626. }
  627. void CParseToken::Delete()
  628. {
  629. if (m_data != NULL)
  630. {
  631. free(m_data);
  632. m_data = NULL;
  633. }
  634. delete this;
  635. }
  636. bool CParseToken::NextChar(byte& theByte)
  637. {
  638. if (m_offset < m_datasize)
  639. {
  640. if (m_data[m_offset] == '\n')
  641. {
  642. m_curLine += 1;
  643. m_curPos = 1;
  644. }
  645. else
  646. {
  647. m_curPos++;
  648. }
  649. theByte = m_data[m_offset++];
  650. return true;
  651. }
  652. else
  653. {
  654. return false;
  655. }
  656. }
  657. void CParseToken::Init(CToken* token)
  658. {
  659. LPCTSTR tokenString = token->GetStringValue();
  660. m_datasize = strlen(tokenString);
  661. if (m_datasize > 0)
  662. {
  663. m_data = (byte*) malloc(m_datasize);
  664. memcpy(m_data, tokenString, m_datasize);
  665. }
  666. else
  667. {
  668. m_data = NULL;
  669. }
  670. m_curLine = 1;
  671. m_curPos = 1;
  672. m_offset = 0;
  673. token->Delete();
  674. }
  675. long CParseToken::GetRemainingSize()
  676. {
  677. return m_datasize - m_offset;
  678. }
  679. int CParseToken::GetCurLine()
  680. {
  681. return m_curLine;
  682. }
  683. void CParseToken::GetCurFilename(char** theBuff)
  684. {
  685. *theBuff = NULL;
  686. }
  687. //
  688. // CParseDefine
  689. //
  690. CParseDefine::CParseDefine()
  691. {
  692. }
  693. CParseDefine::~CParseDefine()
  694. {
  695. }
  696. CParseDefine* CParseDefine::Create(CDirectiveSymbol* definesymbol)
  697. {
  698. CParseDefine* retval = new CParseDefine();
  699. retval->Init(definesymbol);
  700. return retval;
  701. }
  702. void CParseDefine::Delete()
  703. {
  704. CParseMemory::Delete();
  705. }
  706. void CParseDefine::Init(CDirectiveSymbol* definesymbol)
  707. {
  708. CParseMemory::Init((byte*)definesymbol->GetValue(), strlen(definesymbol->GetValue()));
  709. m_defineSymbol = definesymbol;
  710. }
  711. bool CParseDefine::IsThisDefinition(void* theDefinition)
  712. {
  713. return (CDirectiveSymbol*)theDefinition == m_defineSymbol;
  714. }
  715. //
  716. // CToken
  717. //
  718. CToken::CToken()
  719. {
  720. }
  721. CToken::~CToken()
  722. {
  723. }
  724. CToken* CToken::Create()
  725. {
  726. CToken* theToken = new CToken();
  727. theToken->Init();
  728. return theToken;
  729. }
  730. void CToken::Delete()
  731. {
  732. if (m_string != NULL)
  733. {
  734. free(m_string);
  735. m_string = NULL;
  736. }
  737. delete this;
  738. }
  739. void CToken::Init()
  740. {
  741. m_next = NULL;
  742. m_string = NULL;
  743. }
  744. void CToken::SetNext(CToken* theToken)
  745. {
  746. m_next = theToken;
  747. }
  748. CToken* CToken::GetNext()
  749. {
  750. return m_next;
  751. }
  752. int CToken::GetType()
  753. {
  754. return TK_EOF;
  755. }
  756. int CToken::GetIntValue()
  757. {
  758. return 0;
  759. }
  760. LPCTSTR CToken::GetStringValue()
  761. {
  762. if (m_string == NULL)
  763. {
  764. return "";
  765. }
  766. return m_string;
  767. }
  768. float CToken::GetFloatValue()
  769. {
  770. return 0.0;
  771. }
  772. //
  773. // CCharToken
  774. //
  775. CCharToken::CCharToken()
  776. {
  777. }
  778. CCharToken::~CCharToken()
  779. {
  780. }
  781. CCharToken* CCharToken::Create(byte theByte)
  782. {
  783. CCharToken* theToken = new CCharToken();
  784. theToken->Init(theByte);
  785. return theToken;
  786. }
  787. void CCharToken::Delete()
  788. {
  789. CToken::Delete();
  790. }
  791. void CCharToken::Init(byte theByte)
  792. {
  793. CToken::Init();
  794. char charString[10];
  795. switch(theByte)
  796. {
  797. case '\0':
  798. strcpy(charString, "\\0");
  799. break;
  800. case '\n':
  801. strcpy(charString, "\\n");
  802. break;
  803. case '\\':
  804. strcpy(charString, "\\\\");
  805. break;
  806. case '\'':
  807. strcpy(charString, "\\'");
  808. break;
  809. case '\?':
  810. strcpy(charString, "\\?");
  811. break;
  812. case '\a':
  813. strcpy(charString, "\\a");
  814. break;
  815. case '\b':
  816. strcpy(charString, "\\b");
  817. break;
  818. case '\f':
  819. strcpy(charString, "\\f");
  820. break;
  821. case '\r':
  822. strcpy(charString, "\\r");
  823. break;
  824. case '\t':
  825. strcpy(charString, "\\t");
  826. break;
  827. case '\v':
  828. strcpy(charString, "\\v");
  829. break;
  830. default:
  831. charString[0] = (char)theByte;
  832. charString[1] = '\0';
  833. break;
  834. }
  835. m_string = (char*)malloc(strlen(charString) + 1);
  836. strcpy(m_string, charString);
  837. }
  838. int CCharToken::GetType()
  839. {
  840. return TK_CHAR;
  841. }
  842. //
  843. // CStringToken
  844. //
  845. CStringToken::CStringToken()
  846. {
  847. }
  848. CStringToken::~CStringToken()
  849. {
  850. }
  851. CStringToken* CStringToken::Create(LPCTSTR theString)
  852. {
  853. CStringToken* theToken = new CStringToken();
  854. theToken->Init(theString);
  855. return theToken;
  856. }
  857. void CStringToken::Delete()
  858. {
  859. CToken::Delete();
  860. }
  861. void CStringToken::Init(LPCTSTR theString)
  862. {
  863. CToken::Init();
  864. m_string = (char*)malloc(strlen(theString) + 1);
  865. // ASSERT(m_string);
  866. strcpy(m_string, theString);
  867. }
  868. int CStringToken::GetType()
  869. {
  870. return TK_STRING;
  871. }
  872. //
  873. // CIntToken
  874. //
  875. CIntToken::CIntToken()
  876. {
  877. }
  878. CIntToken::~CIntToken()
  879. {
  880. }
  881. CIntToken* CIntToken::Create(long value)
  882. {
  883. CIntToken* theToken = new CIntToken();
  884. theToken->Init(value);
  885. return theToken;
  886. }
  887. void CIntToken::Delete()
  888. {
  889. CToken::Delete();
  890. }
  891. void CIntToken::Init(long value)
  892. {
  893. CToken::Init();
  894. m_value = value;
  895. }
  896. int CIntToken::GetType()
  897. {
  898. return TK_INT;
  899. }
  900. int CIntToken::GetIntValue()
  901. {
  902. return m_value;
  903. }
  904. float CIntToken::GetFloatValue()
  905. {
  906. return (float)m_value;
  907. }
  908. LPCTSTR CIntToken::GetStringValue()
  909. {
  910. if (m_string != NULL)
  911. {
  912. free(m_string);
  913. m_string = NULL;
  914. }
  915. char temp[128];
  916. sprintf(temp, "%d", m_value);
  917. m_string = (char*)malloc(strlen(temp) + 1);
  918. strcpy(m_string, temp);
  919. return m_string;
  920. }
  921. //
  922. // CFloatToken
  923. //
  924. CFloatToken::CFloatToken()
  925. {
  926. }
  927. CFloatToken::~CFloatToken()
  928. {
  929. }
  930. CFloatToken* CFloatToken::Create(float value)
  931. {
  932. CFloatToken* theToken = new CFloatToken();
  933. theToken->Init(value);
  934. return theToken;
  935. }
  936. void CFloatToken::Delete()
  937. {
  938. CToken::Delete();
  939. }
  940. void CFloatToken::Init(float value)
  941. {
  942. CToken::Init();
  943. m_value = value;
  944. }
  945. int CFloatToken::GetType()
  946. {
  947. return TK_FLOAT;
  948. }
  949. float CFloatToken::GetFloatValue()
  950. {
  951. return m_value;
  952. }
  953. LPCTSTR CFloatToken::GetStringValue()
  954. {
  955. if (m_string != NULL)
  956. {
  957. free(m_string);
  958. m_string = NULL;
  959. }
  960. char temp[128];
  961. sprintf(temp, "%g", m_value);
  962. m_string = (char*)malloc(strlen(temp) + 1);
  963. strcpy(m_string, temp);
  964. return m_string;
  965. }
  966. //
  967. // CIdentifierToken
  968. //
  969. CIdentifierToken::CIdentifierToken()
  970. {
  971. }
  972. CIdentifierToken::~CIdentifierToken()
  973. {
  974. }
  975. CIdentifierToken* CIdentifierToken::Create(LPCTSTR name)
  976. {
  977. CIdentifierToken* theToken = new CIdentifierToken();
  978. theToken->Init(name);
  979. return theToken;
  980. }
  981. void CIdentifierToken::Delete()
  982. {
  983. CToken::Delete();
  984. }
  985. void CIdentifierToken::Init(LPCTSTR name)
  986. {
  987. CToken::Init();
  988. m_string = (char*)malloc(strlen(name) + 1);
  989. // ASSERT(m_string);
  990. strcpy(m_string, name);
  991. }
  992. int CIdentifierToken::GetType()
  993. {
  994. return TK_IDENTIFIER;
  995. }
  996. //
  997. // CCommentToken
  998. //
  999. CCommentToken::CCommentToken()
  1000. {
  1001. }
  1002. CCommentToken::~CCommentToken()
  1003. {
  1004. }
  1005. CCommentToken* CCommentToken::Create(LPCTSTR name)
  1006. {
  1007. CCommentToken* theToken = new CCommentToken();
  1008. theToken->Init(name);
  1009. return theToken;
  1010. }
  1011. void CCommentToken::Delete()
  1012. {
  1013. CToken::Delete();
  1014. }
  1015. void CCommentToken::Init(LPCTSTR name)
  1016. {
  1017. CToken::Init();
  1018. m_string = (char*)malloc(strlen(name) + 1);
  1019. // ASSERT(m_string);
  1020. strcpy(m_string, name);
  1021. }
  1022. int CCommentToken::GetType()
  1023. {
  1024. return TK_COMMENT;
  1025. }
  1026. //
  1027. // CUserToken
  1028. //
  1029. CUserToken::CUserToken()
  1030. {
  1031. }
  1032. CUserToken::~CUserToken()
  1033. {
  1034. }
  1035. CUserToken* CUserToken::Create(int value, LPCTSTR string)
  1036. {
  1037. CUserToken* theToken = new CUserToken();
  1038. theToken->Init(value, string);
  1039. return theToken;
  1040. }
  1041. void CUserToken::Delete()
  1042. {
  1043. CToken::Delete();
  1044. }
  1045. void CUserToken::Init(int value, LPCTSTR string)
  1046. {
  1047. CToken::Init();
  1048. m_value = value;
  1049. m_string = (char*)malloc(strlen(string) + 1);
  1050. strcpy(m_string, string);
  1051. }
  1052. int CUserToken::GetType()
  1053. {
  1054. return m_value;
  1055. }
  1056. //
  1057. // CUndefinedToken
  1058. //
  1059. CUndefinedToken::CUndefinedToken()
  1060. {
  1061. }
  1062. CUndefinedToken::~CUndefinedToken()
  1063. {
  1064. }
  1065. CUndefinedToken* CUndefinedToken::Create(LPCTSTR string)
  1066. {
  1067. CUndefinedToken* theToken = new CUndefinedToken();
  1068. theToken->Init(string);
  1069. return theToken;
  1070. }
  1071. void CUndefinedToken::Delete()
  1072. {
  1073. CToken::Delete();
  1074. }
  1075. void CUndefinedToken::Init(LPCTSTR string)
  1076. {
  1077. CToken::Init();
  1078. m_string = (char*)malloc(strlen(string) + 1);
  1079. strcpy(m_string, string);
  1080. }
  1081. int CUndefinedToken::GetType()
  1082. {
  1083. return TK_UNDEFINED;
  1084. }
  1085. //
  1086. // CTokenizerState
  1087. //
  1088. CTokenizerState::CTokenizerState()
  1089. {
  1090. }
  1091. CTokenizerState::~CTokenizerState()
  1092. {
  1093. }
  1094. CTokenizerState* CTokenizerState::Create(bool skip)
  1095. {
  1096. CTokenizerState* retval = new CTokenizerState();
  1097. retval->Init(skip);
  1098. return retval;
  1099. }
  1100. void CTokenizerState::Init(bool skip)
  1101. {
  1102. m_next = NULL;
  1103. m_skip = skip;
  1104. m_elseHit = false;
  1105. }
  1106. void CTokenizerState::Delete()
  1107. {
  1108. delete this;
  1109. }
  1110. CTokenizerState* CTokenizerState::GetNext()
  1111. {
  1112. return m_next;
  1113. }
  1114. bool CTokenizerState::ProcessElse()
  1115. {
  1116. if (!m_elseHit)
  1117. {
  1118. m_elseHit = true;
  1119. m_skip = !m_skip;
  1120. }
  1121. return m_elseHit;
  1122. }
  1123. void CTokenizerState::SetNext(CTokenizerState* next)
  1124. {
  1125. m_next = next;
  1126. }
  1127. bool CTokenizerState::Skipping()
  1128. {
  1129. return m_skip;
  1130. }
  1131. //
  1132. // CTokenizerHolderState
  1133. //
  1134. CTokenizerHolderState::CTokenizerHolderState()
  1135. {
  1136. }
  1137. CTokenizerHolderState::~CTokenizerHolderState()
  1138. {
  1139. }
  1140. CTokenizerHolderState* CTokenizerHolderState::Create()
  1141. {
  1142. CTokenizerHolderState* retval = new CTokenizerHolderState();
  1143. retval->Init();
  1144. return retval;
  1145. }
  1146. void CTokenizerHolderState::Init()
  1147. {
  1148. CTokenizerState::Init(true);
  1149. }
  1150. void CTokenizerHolderState::Delete()
  1151. {
  1152. delete this;
  1153. }
  1154. bool CTokenizerHolderState::ProcessElse()
  1155. {
  1156. if (!m_elseHit)
  1157. {
  1158. m_elseHit = true;
  1159. }
  1160. return m_elseHit;
  1161. }
  1162. //
  1163. // CKeywordTable
  1164. //
  1165. CKeywordTable::CKeywordTable(CTokenizer* tokenizer, keywordArray_t* keywords)
  1166. {
  1167. m_tokenizer = tokenizer;
  1168. m_holdKeywords = tokenizer->SetKeywords(keywords);
  1169. }
  1170. CKeywordTable::~CKeywordTable()
  1171. {
  1172. m_tokenizer->SetKeywords(m_holdKeywords);
  1173. }
  1174. //
  1175. // CTokenizer
  1176. //
  1177. CTokenizer::CTokenizer()
  1178. {
  1179. }
  1180. CTokenizer::~CTokenizer()
  1181. {
  1182. }
  1183. CTokenizer* CTokenizer::Create(UINT dwFlags)
  1184. {
  1185. CTokenizer* theTokenizer = new CTokenizer();
  1186. theTokenizer->Init(dwFlags);
  1187. return theTokenizer;
  1188. }
  1189. void CTokenizer::Delete()
  1190. {
  1191. while (m_curParseStream != NULL)
  1192. {
  1193. CParseStream* curStream = m_curParseStream;
  1194. m_curParseStream = curStream->GetNext();
  1195. curStream->Delete();
  1196. }
  1197. if (m_symbolLookup != NULL)
  1198. {
  1199. m_symbolLookup->Delete();
  1200. m_symbolLookup = NULL;
  1201. }
  1202. while (m_nextToken != NULL)
  1203. {
  1204. CToken* curToken = m_nextToken;
  1205. m_nextToken = curToken->GetNext();
  1206. curToken->Delete();
  1207. }
  1208. while (m_state != NULL)
  1209. {
  1210. Error(TKERR_UNMATCHED_DIRECTIVE);
  1211. CTokenizerState* curState = m_state;
  1212. m_state = curState->GetNext();
  1213. curState->Delete();
  1214. }
  1215. /* if (m_lastErrMsg != NULL)
  1216. {
  1217. free(m_lastErrMsg);
  1218. m_lastErrMsg = NULL;
  1219. }*/
  1220. delete this;
  1221. }
  1222. void CTokenizer::Error(int theError)
  1223. {
  1224. char errString[128];
  1225. char lookupstring[128];
  1226. int i = 0;
  1227. while ((errorMessages[i].m_tokenvalue != TKERR_USERERROR) && (errorMessages[i].m_tokenvalue != theError))
  1228. {
  1229. i++;
  1230. }
  1231. if ((errorMessages[i].m_tokenvalue == TKERR_USERERROR) && (m_errors != NULL))
  1232. {
  1233. i = 0;
  1234. while ((m_errors[i].m_tokenvalue != TK_EOF) && (m_errors[i].m_tokenvalue != theError))
  1235. {
  1236. i++;
  1237. }
  1238. strcpy(lookupstring, m_errors[i].m_keyword);
  1239. }
  1240. else
  1241. {
  1242. strcpy(lookupstring, errorMessages[i].m_keyword);
  1243. }
  1244. sprintf(errString, "Error -- %d, %s", theError, lookupstring);
  1245. Error(errString, theError);
  1246. }
  1247. void CTokenizer::Error(int theError, LPCTSTR errString)
  1248. {
  1249. char errstring[128];
  1250. char lookupstring[128];
  1251. int i = 0;
  1252. while ((errorMessages[i].m_tokenvalue != TKERR_USERERROR) && (errorMessages[i].m_tokenvalue != theError))
  1253. {
  1254. i++;
  1255. }
  1256. if ((errorMessages[i].m_tokenvalue == TKERR_USERERROR) && (m_errors != NULL))
  1257. {
  1258. i = 0;
  1259. while ((m_errors[i].m_tokenvalue != TK_EOF) && (m_errors[i].m_tokenvalue != theError))
  1260. {
  1261. i++;
  1262. }
  1263. strcpy(lookupstring, m_errors[i].m_keyword);
  1264. }
  1265. else
  1266. {
  1267. strcpy(lookupstring, errorMessages[i].m_keyword);
  1268. }
  1269. sprintf(errstring, "Error -- %d, %s - %s", theError, lookupstring, errString);
  1270. Error(errstring, theError);
  1271. }
  1272. void CTokenizer::Error(LPCTSTR errString, int theError)
  1273. {
  1274. if (m_errorProc != NULL)
  1275. {
  1276. m_errorProc(errString);
  1277. }
  1278. #ifdef USES_MODULES
  1279. else
  1280. {
  1281. ReportError(theError, errString);
  1282. }
  1283. #endif
  1284. }
  1285. bool CTokenizer::AddParseFile(LPCTSTR filename)
  1286. {
  1287. CParseStream* newStream = CParseFile::Create(filename, this);
  1288. if ( newStream != NULL )
  1289. {
  1290. newStream->SetNext(m_curParseStream);
  1291. m_curParseStream = newStream;
  1292. return true;
  1293. }
  1294. return false;
  1295. }
  1296. void CTokenizer::AddParseStream(byte* data, long datasize)
  1297. {
  1298. CParseStream* newStream = CParseMemory::Create(data, datasize);
  1299. newStream->SetNext(m_curParseStream);
  1300. m_curParseStream = newStream;
  1301. }
  1302. long CTokenizer::GetRemainingSize()
  1303. {
  1304. long retval = 0;
  1305. CParseStream* curStream = m_curParseStream;
  1306. while (curStream != NULL)
  1307. {
  1308. retval += curStream->GetRemainingSize();
  1309. curStream = curStream->GetNext();
  1310. }
  1311. return retval;
  1312. }
  1313. LPCTSTR CTokenizer::LookupToken(int tokenID, keywordArray_t* theTable)
  1314. {
  1315. if (theTable == NULL)
  1316. {
  1317. theTable = m_keywords;
  1318. }
  1319. if (theTable == NULL)
  1320. {
  1321. return NULL;
  1322. }
  1323. int i = 0;
  1324. while (theTable[i].m_tokenvalue != TK_EOF)
  1325. {
  1326. if (theTable[i].m_tokenvalue == tokenID)
  1327. {
  1328. return theTable[i].m_keyword;
  1329. }
  1330. i++;
  1331. }
  1332. return NULL;
  1333. }
  1334. void CTokenizer::PutBackToken(CToken* theToken, bool commented, LPCTSTR addedChars, bool bIgnoreThisTokenType)
  1335. {
  1336. if (commented)
  1337. {
  1338. CParseToken* newStream = CParseToken::Create(theToken);
  1339. newStream->SetNext(m_curParseStream);
  1340. m_curParseStream = newStream;
  1341. if (addedChars != NULL)
  1342. {
  1343. CParsePutBack* spacer = CParsePutBack::Create(' ', 0, NULL);
  1344. spacer->SetNext(m_curParseStream);
  1345. m_curParseStream = spacer;
  1346. CParseBlock* newBlock = CParseBlock::Create((byte*)addedChars, strlen(addedChars));
  1347. newBlock->SetNext(m_curParseStream);
  1348. m_curParseStream = newBlock;
  1349. }
  1350. char temp[] = "// * ";
  1351. CParseBlock* newBlock = CParseBlock::Create((byte*)temp, strlen(temp));
  1352. newBlock->SetNext(m_curParseStream);
  1353. m_curParseStream = newBlock;
  1354. return;
  1355. }
  1356. switch(theToken->GetType())
  1357. {
  1358. case TK_INT:
  1359. case TK_EOF:
  1360. case TK_UNDEFINED:
  1361. case TK_FLOAT:
  1362. case TK_CHAR:
  1363. case TK_STRING:
  1364. case TK_EOL:
  1365. case TK_COMMENT:
  1366. if (!bIgnoreThisTokenType)
  1367. {
  1368. theToken->SetNext(m_nextToken);
  1369. m_nextToken = theToken;
  1370. break;
  1371. }
  1372. default:
  1373. CParseToken* newStream = CParseToken::Create(theToken);
  1374. newStream->SetNext(m_curParseStream);
  1375. m_curParseStream = newStream;
  1376. break;
  1377. }
  1378. if (addedChars != NULL)
  1379. {
  1380. CParseBlock* newBlock = CParseBlock::Create((byte*)addedChars, strlen(addedChars));
  1381. newBlock->SetNext(m_curParseStream);
  1382. m_curParseStream = newBlock;
  1383. }
  1384. }
  1385. CToken* CTokenizer::GetToken(keywordArray_t* keywords, UINT onFlags, UINT offFlags)
  1386. {
  1387. keywordArray_t* holdKeywords = SetKeywords(keywords);
  1388. CToken* retval = GetToken(onFlags, offFlags);
  1389. SetKeywords(holdKeywords);
  1390. return retval;
  1391. }
  1392. CToken* CTokenizer::GetToken(UINT onFlags, UINT offFlags)
  1393. {
  1394. UINT holdFlags = m_flags;
  1395. m_flags |= onFlags;
  1396. m_flags &= (~offFlags);
  1397. CToken* theToken = NULL;
  1398. while (theToken == NULL)
  1399. {
  1400. theToken = FetchToken();
  1401. if (theToken == NULL)
  1402. {
  1403. continue;
  1404. }
  1405. if (theToken->GetType() == TK_EOF)
  1406. {
  1407. break;
  1408. }
  1409. if (m_state != NULL)
  1410. {
  1411. if (m_state->Skipping())
  1412. {
  1413. theToken->Delete();
  1414. theToken = NULL;
  1415. }
  1416. }
  1417. }
  1418. m_flags = holdFlags;
  1419. return theToken;
  1420. }
  1421. CToken* CTokenizer::GetToEndOfLine(int tokenType)
  1422. {
  1423. // update, if you just want the whole line returned as a string, then allow a much bigger size than
  1424. // the default string size of only 128 chars...
  1425. //
  1426. if (tokenType == TK_STRING)
  1427. {
  1428. #define iRETURN_STRING_SIZE 2048
  1429. char theString[iRETURN_STRING_SIZE];
  1430. theString[0] = ' ';
  1431. for (int i = 1; i < iRETURN_STRING_SIZE; i++)
  1432. {
  1433. if (NextChar((byte&)theString[i]))
  1434. {
  1435. if (theString[i] != '\n')
  1436. {
  1437. continue;
  1438. }
  1439. PutBackChar(theString[i]);
  1440. }
  1441. theString[i] = '\0';
  1442. return CStringToken::Create(theString);
  1443. }
  1444. // line would maks a string too big to fit in buffer...
  1445. //
  1446. Error(TKERR_STRINGLENGTHEXCEEDED);
  1447. }
  1448. else
  1449. {
  1450. char theString[MAX_IDENTIFIER_LENGTH];
  1451. theString[0] = ' ';
  1452. while (theString[0] == ' ')
  1453. {
  1454. if (!NextChar((byte&)theString[0]))
  1455. {
  1456. return NULL;
  1457. }
  1458. }
  1459. for (int i = 1; i < MAX_IDENTIFIER_LENGTH; i++)
  1460. {
  1461. if (NextChar((byte&)theString[i]))
  1462. {
  1463. if (theString[i] != '\n')
  1464. {
  1465. continue;
  1466. }
  1467. PutBackChar(theString[i]);
  1468. }
  1469. theString[i] = '\0';
  1470. switch(tokenType)
  1471. {
  1472. case TK_COMMENT:
  1473. return CCommentToken::Create(theString);
  1474. case TK_IDENTIFIER:
  1475. default:
  1476. return CIdentifierToken::Create(theString);
  1477. }
  1478. }
  1479. Error(TKERR_IDENTIFIERLENGTHEXCEEDED);
  1480. }
  1481. return NULL;
  1482. }
  1483. void CTokenizer::SkipToLineEnd()
  1484. {
  1485. byte theByte;
  1486. while(NextChar(theByte))
  1487. {
  1488. if (theByte == '\n')
  1489. {
  1490. break;
  1491. }
  1492. }
  1493. }
  1494. CToken* CTokenizer::FetchToken()
  1495. {
  1496. if (m_nextToken != NULL)
  1497. {
  1498. CToken* curToken = m_nextToken;
  1499. m_nextToken = curToken->GetNext();
  1500. curToken->SetNext(NULL);
  1501. return curToken;
  1502. }
  1503. byte theByte;
  1504. CToken* theToken = NULL;
  1505. while (true)
  1506. {
  1507. if (!NextChar(theByte))
  1508. {
  1509. return CToken::Create();
  1510. }
  1511. if (theByte <= ' ')
  1512. {
  1513. if ((theByte == '\n') && ((TKF_USES_EOL & m_flags) != 0))
  1514. {
  1515. return CUserToken::Create(TK_EOL, "-EOLN-");
  1516. }
  1517. continue;
  1518. }
  1519. switch(theByte)
  1520. {
  1521. case '#':
  1522. if ((m_flags & TKF_IGNOREDIRECTIVES) == 0)
  1523. {
  1524. theToken = HandleDirective();
  1525. }
  1526. else
  1527. {
  1528. if ((m_flags & TKF_NODIRECTIVES) != 0)
  1529. {
  1530. return HandleSymbol('#');
  1531. }
  1532. SkipToLineEnd();
  1533. }
  1534. break;
  1535. case '/':
  1536. theToken = HandleSlash();
  1537. break;
  1538. case '"':
  1539. theToken = HandleString();
  1540. break;
  1541. case '\'':
  1542. theToken = HandleQuote();
  1543. break;
  1544. default:
  1545. if (((theByte >= 'a') && (theByte <= 'z'))
  1546. || ((theByte >= 'A') && (theByte <= 'Z'))
  1547. || ((theByte == '_') && ((m_flags & TKF_NOUNDERSCOREINIDENTIFIER) == 0)))
  1548. {
  1549. theToken = HandleIdentifier(theByte);
  1550. }
  1551. else if (((m_flags & TKF_NUMERICIDENTIFIERSTART) != 0) && (theByte >= '0') && (theByte <= '9'))
  1552. {
  1553. theToken = HandleIdentifier(theByte);
  1554. }
  1555. else if (((theByte >= '0') && (theByte <= '9')) || (theByte == '-'))
  1556. {
  1557. theToken = HandleNumeric(theByte);
  1558. }
  1559. else if (theByte == '.')
  1560. {
  1561. theToken = HandleDecimal();
  1562. }
  1563. else if (theByte <= ' ')
  1564. {
  1565. break;
  1566. }
  1567. else
  1568. {
  1569. theToken = HandleSymbol(theByte);
  1570. }
  1571. }
  1572. if (theToken != NULL)
  1573. {
  1574. return theToken;
  1575. }
  1576. }
  1577. }
  1578. bool CTokenizer::NextChar(byte& theByte)
  1579. {
  1580. while (m_curParseStream != NULL)
  1581. {
  1582. if (m_curParseStream->NextChar(theByte))
  1583. {
  1584. return true;
  1585. }
  1586. CParseStream* curParseStream = m_curParseStream;
  1587. m_curParseStream = curParseStream->GetNext();
  1588. curParseStream->Delete();
  1589. }
  1590. return false;
  1591. }
  1592. bool CTokenizer::RequireToken(int tokenType)
  1593. {
  1594. CToken* theToken = GetToken();
  1595. bool retValue = theToken->GetType() == tokenType;
  1596. theToken->Delete();
  1597. return retValue;
  1598. }
  1599. void CTokenizer::ScanUntilToken(int tokenType)
  1600. {
  1601. CToken* curToken;
  1602. int tokenValue = TK_UNDEFINED;
  1603. while (tokenValue != tokenType)
  1604. {
  1605. curToken = GetToken();
  1606. tokenValue = curToken->GetType();
  1607. if (tokenValue == TK_EOF)
  1608. {
  1609. PutBackToken(curToken);
  1610. break;
  1611. }
  1612. if (tokenValue == tokenType)
  1613. {
  1614. PutBackToken(curToken);
  1615. }
  1616. else
  1617. {
  1618. curToken->Delete();
  1619. }
  1620. }
  1621. }
  1622. void CTokenizer::Init(UINT dwFlags)
  1623. {
  1624. m_symbolLookup = NULL;
  1625. m_nextToken = NULL;
  1626. m_curParseStream = NULL;
  1627. m_keywords = NULL;
  1628. m_symbols = NULL;
  1629. m_errors = NULL;
  1630. m_state = NULL;
  1631. m_flags = dwFlags;
  1632. m_errorProc = NULL;
  1633. }
  1634. void CTokenizer::SetErrorProc(LPTokenizerErrorProc errorProc)
  1635. {
  1636. m_errorProc = errorProc;
  1637. }
  1638. void CTokenizer::SetAdditionalErrors(keywordArray_t* theErrors)
  1639. {
  1640. m_errors = theErrors;
  1641. }
  1642. keywordArray_t* CTokenizer::SetKeywords(keywordArray_t* theKeywords)
  1643. {
  1644. keywordArray_t* retval = m_keywords;
  1645. m_keywords = theKeywords;
  1646. return retval;
  1647. }
  1648. void CTokenizer::SetSymbols(keywordArray_t* theSymbols)
  1649. {
  1650. m_symbols = theSymbols;
  1651. if (m_symbolLookup != NULL)
  1652. {
  1653. m_symbolLookup->Delete();
  1654. m_symbolLookup = NULL;
  1655. }
  1656. int i = 0;
  1657. if (theSymbols == NULL)
  1658. {
  1659. return;
  1660. }
  1661. while(theSymbols[i].m_tokenvalue != TK_EOF)
  1662. {
  1663. InsertSymbol(theSymbols[i].m_keyword, theSymbols[i].m_tokenvalue);
  1664. i++;
  1665. }
  1666. }
  1667. void CTokenizer::InsertSymbol(LPCTSTR theSymbol, int theValue)
  1668. {
  1669. CSymbolLookup** curHead = &m_symbolLookup;
  1670. CSymbolLookup* curParent = NULL;
  1671. CSymbolLookup* curLookup = NULL;
  1672. for (UINT i = 0; i < strlen(theSymbol); i++)
  1673. {
  1674. bool found = false;
  1675. curLookup = *curHead;
  1676. while (curLookup != NULL)
  1677. {
  1678. if (curLookup->GetByte() == theSymbol[i])
  1679. {
  1680. found = true;
  1681. break;
  1682. }
  1683. curLookup = curLookup->GetNext();
  1684. }
  1685. if (!found)
  1686. {
  1687. curLookup = CSymbolLookup::Create(theSymbol[i]);
  1688. curLookup->SetParent(curParent);
  1689. curLookup->SetNext(*curHead);
  1690. *curHead = curLookup;
  1691. }
  1692. curHead = curLookup->GetChildAddress();
  1693. curParent = curLookup;
  1694. }
  1695. if (curLookup->GetValue() != -1)
  1696. {
  1697. Error(TKERR_DUPLICATESYMBOL);
  1698. }
  1699. curLookup->SetValue(theValue);
  1700. }
  1701. CToken* CTokenizer::HandleString()
  1702. {
  1703. char theString[MAX_STRING_LENGTH];
  1704. for (int i = 0; i < MAX_STRING_LENGTH; i++)
  1705. {
  1706. if (!NextChar((byte&)theString[i]))
  1707. {
  1708. return NULL;
  1709. }
  1710. if (theString[i] == '"')
  1711. {
  1712. theString[i] = '\0';
  1713. return CStringToken::Create(theString);
  1714. }
  1715. if (theString[i] == '\\')
  1716. {
  1717. theString[i] = Escapement();
  1718. }
  1719. }
  1720. Error(TKERR_STRINGLENGTHEXCEEDED);
  1721. return NULL;
  1722. }
  1723. void CTokenizer::GetCurFilename(char** filename)
  1724. {
  1725. if (m_curParseStream == NULL)
  1726. {
  1727. *filename = (char*)malloc(1);
  1728. *filename[0] = '\0';
  1729. return;
  1730. }
  1731. m_curParseStream->GetCurFilename(filename);
  1732. }
  1733. int CTokenizer::GetCurLine()
  1734. {
  1735. if (m_curParseStream == NULL)
  1736. {
  1737. return 0;
  1738. }
  1739. return m_curParseStream->GetCurLine();
  1740. }
  1741. void CTokenizer::PutBackChar(byte theByte, int curLine, LPCTSTR filename)
  1742. {
  1743. CParseStream* newStream;
  1744. if (filename == NULL)
  1745. {
  1746. curLine = m_curParseStream->GetCurLine();
  1747. char* theFile = NULL;
  1748. m_curParseStream->GetCurFilename(&theFile);
  1749. newStream = CParsePutBack::Create(theByte, curLine, theFile);
  1750. if (theFile != NULL)
  1751. {
  1752. free(theFile);
  1753. }
  1754. }
  1755. else
  1756. {
  1757. newStream = CParsePutBack::Create(theByte, curLine, filename);
  1758. }
  1759. newStream->SetNext(m_curParseStream);
  1760. m_curParseStream = newStream;
  1761. }
  1762. byte CTokenizer::Escapement()
  1763. {
  1764. byte theByte;
  1765. if (NextChar(theByte))
  1766. {
  1767. switch(theByte)
  1768. {
  1769. case 'n':
  1770. return '\n';
  1771. case '\\':
  1772. return '\\';
  1773. case '\'':
  1774. return '\'';
  1775. case '?':
  1776. return '\?';
  1777. case 'a':
  1778. return '\a';
  1779. case 'b':
  1780. return '\b';
  1781. case 'f':
  1782. return '\f';
  1783. case 'r':
  1784. return '\r';
  1785. case 't':
  1786. return '\t';
  1787. case 'v':
  1788. return '\v';
  1789. case '0':
  1790. return '\0';
  1791. // support for octal or hex sequences?? \000 or \xhhh
  1792. default:
  1793. PutBackChar(theByte);
  1794. }
  1795. }
  1796. return '\\';
  1797. }
  1798. bool CTokenizer::AddDefineSymbol(CDirectiveSymbol* definesymbol)
  1799. {
  1800. CParseStream* curStream = m_curParseStream;
  1801. while(curStream != NULL)
  1802. {
  1803. if (curStream->IsThisDefinition(definesymbol))
  1804. {
  1805. return false;
  1806. }
  1807. curStream = curStream->GetNext();
  1808. }
  1809. CParseStream* newStream = CParseDefine::Create(definesymbol);
  1810. newStream->SetNext(m_curParseStream);
  1811. m_curParseStream = newStream;
  1812. return true;
  1813. }
  1814. CToken* CTokenizer::TokenFromName(LPCTSTR name)
  1815. {
  1816. CDirectiveSymbol* defineSymbol = (CDirectiveSymbol*)m_defines.FindSymbol(name);
  1817. if (defineSymbol != NULL)
  1818. {
  1819. if (AddDefineSymbol(defineSymbol))
  1820. {
  1821. return FetchToken();
  1822. }
  1823. }
  1824. if ((m_keywords != NULL) && ((m_flags & TKF_IGNOREKEYWORDS) == 0))
  1825. {
  1826. int i = 0;
  1827. if ((m_flags & TKF_NOCASEKEYWORDS) == 0)
  1828. {
  1829. while (m_keywords[i].m_tokenvalue != TK_EOF)
  1830. {
  1831. if (strcmp(m_keywords[i].m_keyword, name) == 0)
  1832. {
  1833. return CUserToken::Create(m_keywords[i].m_tokenvalue, name);
  1834. }
  1835. i++;
  1836. }
  1837. }
  1838. else
  1839. {
  1840. while (m_keywords[i].m_tokenvalue != TK_EOF)
  1841. {
  1842. if (stricmp(m_keywords[i].m_keyword, name) == 0)
  1843. {
  1844. return CUserToken::Create(m_keywords[i].m_tokenvalue, name);
  1845. }
  1846. i++;
  1847. }
  1848. }
  1849. }
  1850. return CIdentifierToken::Create(name);
  1851. }
  1852. int CTokenizer::DirectiveFromName(LPCTSTR name)
  1853. {
  1854. if (directiveKeywords != NULL)
  1855. {
  1856. int i = 0;
  1857. while (directiveKeywords[i].m_tokenvalue != TK_EOF)
  1858. {
  1859. if (strcmp(directiveKeywords[i].m_keyword, name) == 0)
  1860. {
  1861. return directiveKeywords[i].m_tokenvalue;
  1862. }
  1863. i++;
  1864. }
  1865. }
  1866. return -1;
  1867. }
  1868. CToken* CTokenizer::HandleIdentifier(byte theByte)
  1869. {
  1870. char theString[MAX_IDENTIFIER_LENGTH];
  1871. theString[0] = theByte;
  1872. for (int i = 1; i < MAX_IDENTIFIER_LENGTH; i++)
  1873. {
  1874. if (NextChar((byte&)theString[i]))
  1875. {
  1876. if (((theString[i] != '_') || ((m_flags & TKF_NOUNDERSCOREINIDENTIFIER) == 0)) &&
  1877. ((theString[i] != '-') || ((m_flags & TKF_NODASHINIDENTIFIER) == 0)))
  1878. {
  1879. if (((theString[i] >= 'A') && (theString[i] <= 'Z'))
  1880. || ((theString[i] >= 'a') && (theString[i] <= 'z'))
  1881. || ((theString[i] >= '0') && (theString[i] <= '9'))
  1882. || (theString[i] == '_') || (theString[i] == '-'))
  1883. {
  1884. continue;
  1885. }
  1886. }
  1887. PutBackChar(theString[i]);
  1888. }
  1889. theString[i] = '\0';
  1890. return TokenFromName(theString);
  1891. }
  1892. Error(TKERR_IDENTIFIERLENGTHEXCEEDED);
  1893. return NULL;
  1894. }
  1895. CToken* CTokenizer::HandleSlash()
  1896. {
  1897. byte theByte;
  1898. if (!NextChar(theByte))
  1899. {
  1900. return NULL;
  1901. }
  1902. if (theByte == '/')
  1903. {
  1904. if (m_flags & TKF_COMMENTTOKENS)
  1905. {
  1906. return GetToEndOfLine(TK_COMMENT);
  1907. }
  1908. SkipToLineEnd();
  1909. return NULL;
  1910. }
  1911. if (theByte == '*')
  1912. {
  1913. if (m_flags & TKF_COMMENTTOKENS)
  1914. {
  1915. char theString[MAX_IDENTIFIER_LENGTH + 1];
  1916. theString[0] = ' ';
  1917. while (theString[0] == ' ')
  1918. {
  1919. if (!NextChar((byte&)theString[0]))
  1920. {
  1921. return NULL;
  1922. }
  1923. }
  1924. for (int i = 1; i < MAX_IDENTIFIER_LENGTH; i++)
  1925. {
  1926. if (NextChar((byte&)theString[i]))
  1927. {
  1928. if (theString[i] != '*')
  1929. {
  1930. continue;
  1931. }
  1932. i++;
  1933. if (NextChar((byte&)theString[i]))
  1934. {
  1935. if (theString[i] == '/')
  1936. {
  1937. i--;
  1938. theString[i] = '\0';
  1939. return CCommentToken::Create(theString);
  1940. }
  1941. }
  1942. }
  1943. }
  1944. Error(TKERR_IDENTIFIERLENGTHEXCEEDED);
  1945. return NULL;
  1946. }
  1947. while(NextChar(theByte))
  1948. {
  1949. while(theByte == '*')
  1950. {
  1951. if (!NextChar(theByte))
  1952. {
  1953. break;
  1954. }
  1955. if (theByte == '/')
  1956. {
  1957. return NULL;
  1958. }
  1959. }
  1960. }
  1961. return NULL;
  1962. }
  1963. PutBackChar(theByte);
  1964. return HandleSymbol('/');
  1965. }
  1966. CToken* CTokenizer::HandleNumeric(byte theByte)
  1967. {
  1968. bool thesign = theByte == '-';
  1969. if (thesign)
  1970. {
  1971. if (!NextChar(theByte))
  1972. {
  1973. return HandleSymbol('-');
  1974. }
  1975. if (theByte == '.')
  1976. {
  1977. return HandleDecimal(thesign);
  1978. }
  1979. if ((theByte < '0') || (theByte > '9'))
  1980. {
  1981. PutBackChar(theByte);
  1982. return HandleSymbol('-');
  1983. }
  1984. }
  1985. if (theByte == '0')
  1986. {
  1987. return HandleOctal(thesign);
  1988. }
  1989. long value = 0;
  1990. bool digithit = false;
  1991. while((theByte >= '0') && (theByte <= '9'))
  1992. {
  1993. value = (value * 10) + (theByte - '0');
  1994. if (!NextChar(theByte))
  1995. {
  1996. if (thesign)
  1997. {
  1998. value = -value;
  1999. }
  2000. return CIntToken::Create(value);
  2001. }
  2002. digithit = true;
  2003. }
  2004. if (theByte == '.')
  2005. {
  2006. if (digithit)
  2007. {
  2008. return HandleFloat(thesign, value);
  2009. }
  2010. if (thesign)
  2011. {
  2012. PutBackChar(theByte);
  2013. theByte = '-';
  2014. }
  2015. return HandleSymbol(theByte);
  2016. }
  2017. PutBackChar(theByte);
  2018. if (thesign)
  2019. {
  2020. value = -value;
  2021. }
  2022. return CIntToken::Create(value);
  2023. }
  2024. CToken* CTokenizer::HandleOctal(bool thesign)
  2025. {
  2026. byte theByte;
  2027. int value = 0;
  2028. if (!NextChar(theByte))
  2029. {
  2030. return CIntToken::Create(value);
  2031. }
  2032. if (theByte == '.')
  2033. {
  2034. return HandleDecimal(thesign);
  2035. }
  2036. if ((theByte == 'x') || (theByte == 'X'))
  2037. {
  2038. return HandleHex(thesign);
  2039. }
  2040. while(true)
  2041. {
  2042. if((theByte >= '0') && (theByte <='7'))
  2043. {
  2044. value = (value * 8) + (theByte - '0');
  2045. }
  2046. else
  2047. {
  2048. PutBackChar(theByte);
  2049. if (thesign)
  2050. {
  2051. value = -value;
  2052. }
  2053. return CIntToken::Create(value);
  2054. }
  2055. if (!NextChar(theByte))
  2056. {
  2057. if (thesign)
  2058. {
  2059. value = -value;
  2060. }
  2061. return CIntToken::Create(value);
  2062. }
  2063. }
  2064. }
  2065. CToken* CTokenizer::HandleHex(bool thesign)
  2066. {
  2067. int value = 0;
  2068. while (true)
  2069. {
  2070. byte theByte;
  2071. if (!NextChar(theByte))
  2072. {
  2073. if (thesign)
  2074. {
  2075. value = -value;
  2076. }
  2077. return CIntToken::Create(value);
  2078. }
  2079. switch (theByte)
  2080. {
  2081. case '0':
  2082. case '1':
  2083. case '2':
  2084. case '3':
  2085. case '4':
  2086. case '5':
  2087. case '6':
  2088. case '7':
  2089. case '8':
  2090. case '9':
  2091. theByte = theByte - '0';
  2092. break;
  2093. case 'A':
  2094. case 'B':
  2095. case 'C':
  2096. case 'D':
  2097. case 'E':
  2098. case 'F':
  2099. theByte = theByte - 'A' + 10;
  2100. break;
  2101. case 'a':
  2102. case 'b':
  2103. case 'c':
  2104. case 'd':
  2105. case 'e':
  2106. case 'f':
  2107. theByte = theByte - 'a' + 10;
  2108. break;
  2109. default:
  2110. PutBackChar(theByte);
  2111. if (thesign)
  2112. {
  2113. value = -value;
  2114. }
  2115. return CIntToken::Create(value);
  2116. }
  2117. value = (value * 16) + theByte;
  2118. }
  2119. }
  2120. CToken* CTokenizer::HandleDecimal(bool thesign)
  2121. {
  2122. byte theByte;
  2123. if (!NextChar(theByte))
  2124. {
  2125. if (thesign)
  2126. {
  2127. PutBackChar('.');
  2128. return HandleSymbol('-');
  2129. }
  2130. HandleSymbol('.');
  2131. }
  2132. PutBackChar(theByte);
  2133. if ((theByte <= '9') && (theByte >= '0'))
  2134. {
  2135. return HandleFloat(thesign);
  2136. }
  2137. if (thesign)
  2138. {
  2139. PutBackChar('.');
  2140. theByte = '-';
  2141. }
  2142. else
  2143. {
  2144. theByte = '.';
  2145. }
  2146. return HandleSymbol(theByte);
  2147. }
  2148. CToken* CTokenizer::HandleFloat(bool thesign, long value)
  2149. {
  2150. float lower = 1.0;
  2151. float newValue = (float)value;
  2152. byte theByte;
  2153. while(NextChar(theByte))
  2154. {
  2155. if ((theByte >= '0') && (theByte <= '9'))
  2156. {
  2157. lower = lower / 10;
  2158. newValue = newValue + ((theByte - '0') * lower);
  2159. continue;
  2160. }
  2161. PutBackChar(theByte);
  2162. break;
  2163. }
  2164. if (thesign)
  2165. {
  2166. newValue = -newValue;
  2167. }
  2168. return CFloatToken::Create(newValue);
  2169. }
  2170. CToken* CTokenizer::HandleQuote()
  2171. {
  2172. byte theByte;
  2173. if (!NextChar(theByte))
  2174. {
  2175. Error(TKERR_EXPECTED_CHAR);
  2176. return NULL;
  2177. }
  2178. if (theByte == '\\')
  2179. {
  2180. theByte = Escapement();
  2181. }
  2182. byte dummy;
  2183. if (!NextChar(dummy))
  2184. {
  2185. Error(TKERR_EXPECTED_CHAR);
  2186. return NULL;
  2187. }
  2188. if (dummy != '\'')
  2189. {
  2190. PutBackChar(dummy);
  2191. PutBackChar(theByte);
  2192. Error(TKERR_EXPECTED_CHAR);
  2193. return NULL;
  2194. }
  2195. return CCharToken::Create(theByte);
  2196. }
  2197. void CTokenizer::SetFlags(UINT flags)
  2198. {
  2199. m_flags = flags;
  2200. }
  2201. UINT CTokenizer::GetFlags()
  2202. {
  2203. return m_flags;
  2204. }
  2205. CToken* CTokenizer::HandleSymbol(byte theByte)
  2206. {
  2207. char symbolString[128];
  2208. int curStrLen = 0;
  2209. symbolString[0] = '\0';
  2210. bool consumed = false;
  2211. CSymbolLookup* curLookup;
  2212. if ((m_flags & TKF_RAWSYMBOLSONLY) == 0)
  2213. {
  2214. curLookup = m_symbolLookup;
  2215. }
  2216. else
  2217. {
  2218. curLookup = NULL;
  2219. }
  2220. CSymbolLookup* lastLookup = NULL;
  2221. while(curLookup != NULL)
  2222. {
  2223. if (curLookup->GetByte() == theByte)
  2224. {
  2225. symbolString[curStrLen++] = theByte;
  2226. symbolString[curStrLen] = '\0';
  2227. lastLookup = curLookup;
  2228. consumed = true;
  2229. if (curLookup->GetChild() == NULL)
  2230. {
  2231. break;
  2232. }
  2233. if (!NextChar(theByte))
  2234. {
  2235. PutBackToken(CToken::Create());
  2236. break;
  2237. }
  2238. consumed = false;
  2239. curLookup = curLookup->GetChild();
  2240. continue;
  2241. }
  2242. curLookup = curLookup->GetNext();
  2243. }
  2244. if ((!consumed) && (lastLookup != NULL))
  2245. {
  2246. PutBackChar(theByte);
  2247. }
  2248. while ((lastLookup != NULL) && (lastLookup->GetValue() == -1))
  2249. {
  2250. curStrLen--;
  2251. symbolString[curStrLen] = '\0';
  2252. // symbolString = symbolString.Left(symbolString.GetLength() - 1);
  2253. if (lastLookup->GetParent() == NULL)
  2254. {
  2255. if ((m_flags & TKF_WANTUNDEFINED) == 0)
  2256. {
  2257. Error(TKERR_UNRECOGNIZEDSYMBOL);
  2258. }
  2259. }
  2260. else
  2261. {
  2262. PutBackChar(lastLookup->GetByte());
  2263. }
  2264. lastLookup = lastLookup->GetParent();
  2265. }
  2266. if (lastLookup == NULL)
  2267. {
  2268. if ((m_flags & TKF_WANTUNDEFINED) == 0)
  2269. {
  2270. return NULL;
  2271. }
  2272. curStrLen = 0;
  2273. symbolString[curStrLen++] = char(theByte);
  2274. symbolString[curStrLen] = '\0';
  2275. if ((m_flags & TKF_WIDEUNDEFINEDSYMBOLS) != 0)
  2276. {
  2277. while (true)
  2278. {
  2279. if (!NextChar(theByte))
  2280. {
  2281. PutBackToken(CToken::Create());
  2282. break;
  2283. }
  2284. if (theByte == ' ')
  2285. {
  2286. break;
  2287. }
  2288. if (((theByte >= 'a') && (theByte <= 'z')) || ((theByte >= 'A') && (theByte <= 'Z')) ||
  2289. ((theByte >= '0') && (theByte <= '9')))
  2290. {
  2291. PutBackChar(theByte);
  2292. break;
  2293. }
  2294. if (theByte < ' ')
  2295. {
  2296. if ((theByte == '\n') && ((TKF_USES_EOL & m_flags) != 0))
  2297. {
  2298. PutBackToken(CUserToken::Create(TK_EOL, "-EOLN-"));
  2299. break;
  2300. }
  2301. continue;
  2302. }
  2303. symbolString[curStrLen++] = theByte;
  2304. symbolString[curStrLen] = '\0';
  2305. }
  2306. }
  2307. return CUndefinedToken::Create(symbolString);
  2308. }
  2309. return CUserToken::Create(lastLookup->GetValue(), symbolString);
  2310. }
  2311. CToken* CTokenizer::HandleDirective()
  2312. {
  2313. int tokenValue = 0;
  2314. CToken* theToken = FetchToken();
  2315. if (theToken->GetType() == TK_EOF)
  2316. {
  2317. return theToken;
  2318. }
  2319. if (theToken->GetType() != TK_IDENTIFIER)
  2320. {
  2321. Error(TKERR_INVALID_DIRECTIVE);
  2322. theToken->Delete();
  2323. SkipToLineEnd();
  2324. return NULL;
  2325. }
  2326. CDirectiveSymbol* curSymbol;
  2327. CTokenizerState* state;
  2328. int theDirective = DirectiveFromName(theToken->GetStringValue());
  2329. theToken->Delete();
  2330. byte theByte;
  2331. switch(theDirective)
  2332. {
  2333. case DIR_INCLUDE:
  2334. if ((m_state != NULL) && (m_state->Skipping()))
  2335. {
  2336. break;
  2337. }
  2338. theToken = GetToken();
  2339. if (theToken->GetType() != TK_STRING)
  2340. {
  2341. Error(TKERR_INCLUDE_FILE_NOTFOUND);
  2342. theToken->Delete();
  2343. SkipToLineEnd();
  2344. break;
  2345. }
  2346. AddParseFile(theToken->GetStringValue());
  2347. theToken->Delete();
  2348. break;
  2349. case DIR_IFDEF:
  2350. if ((m_state != NULL) && (m_state->Skipping()))
  2351. {
  2352. state = CTokenizerHolderState::Create();
  2353. state->SetNext(m_state);
  2354. m_state = state;
  2355. break;
  2356. }
  2357. theToken = GetToken();
  2358. if (theToken->GetType() != TK_IDENTIFIER)
  2359. {
  2360. Error(TKERR_EXPECTED_IDENTIFIER);
  2361. theToken->Delete();
  2362. SkipToLineEnd();
  2363. break;
  2364. }
  2365. state = CTokenizerState::Create(m_defines.FindSymbol(theToken->GetStringValue()) == NULL);
  2366. theToken->Delete();
  2367. state->SetNext(m_state);
  2368. m_state = state;
  2369. break;
  2370. case DIR_IFNDEF:
  2371. if ((m_state != NULL) && (m_state->Skipping()))
  2372. {
  2373. state = CTokenizerHolderState::Create();
  2374. state->SetNext(m_state);
  2375. m_state = state;
  2376. break;
  2377. }
  2378. theToken = GetToken();
  2379. if (theToken->GetType() != TK_IDENTIFIER)
  2380. {
  2381. Error(TKERR_EXPECTED_IDENTIFIER);
  2382. theToken->Delete();
  2383. SkipToLineEnd();
  2384. break;
  2385. }
  2386. state = CTokenizerState::Create(m_defines.FindSymbol(theToken->GetStringValue()) != NULL);
  2387. theToken->Delete();
  2388. state->SetNext(m_state);
  2389. m_state = state;
  2390. break;
  2391. case DIR_ENDIF:
  2392. if (m_state == NULL)
  2393. {
  2394. Error(TKERR_UNMATCHED_DIRECTIVE);
  2395. break;
  2396. }
  2397. state = m_state;
  2398. m_state = state->GetNext();
  2399. state->Delete();
  2400. break;
  2401. case DIR_ELSE:
  2402. if (m_state == NULL)
  2403. {
  2404. Error(TKERR_UNMATCHED_DIRECTIVE);
  2405. break;
  2406. }
  2407. if (!m_state->ProcessElse())
  2408. {
  2409. Error(TKERR_UNMATCHED_DIRECTIVE);
  2410. break;
  2411. }
  2412. break;
  2413. case DIR_DEFINE:
  2414. if ((m_state != NULL) && (m_state->Skipping()))
  2415. {
  2416. break;
  2417. }
  2418. theToken = GetToken();
  2419. if (theToken->GetType() != TK_IDENTIFIER)
  2420. {
  2421. Error(TKERR_EXPECTED_IDENTIFIER);
  2422. theToken->Delete();
  2423. SkipToLineEnd();
  2424. break;
  2425. }
  2426. // blind add - should check first for value changes
  2427. {
  2428. curSymbol = CDirectiveSymbol::Create(theToken->GetStringValue());
  2429. char temp[128];
  2430. int tempsize = 0;
  2431. while(NextChar(theByte))
  2432. {
  2433. if (theByte == '\n')
  2434. {
  2435. break;
  2436. }
  2437. temp[tempsize++] = char(theByte);
  2438. }
  2439. temp[tempsize] = '\0';
  2440. curSymbol->SetValue(temp);
  2441. if (!m_defines.AddSymbol(curSymbol))
  2442. {
  2443. curSymbol->Delete();
  2444. }
  2445. }
  2446. break;
  2447. case DIR_UNDEFINE:
  2448. if ((m_state != NULL) && (m_state->Skipping()))
  2449. {
  2450. break;
  2451. }
  2452. theToken = GetToken();
  2453. if (theToken->GetType() != TK_IDENTIFIER)
  2454. {
  2455. Error(TKERR_EXPECTED_IDENTIFIER);
  2456. theToken->Delete();
  2457. SkipToLineEnd();
  2458. break;
  2459. }
  2460. m_defines.RemoveSymbol(theToken->GetStringValue());
  2461. break;
  2462. default:
  2463. Error(TKERR_INVALID_DIRECTIVE);
  2464. SkipToLineEnd();
  2465. break;
  2466. }
  2467. return NULL;
  2468. }
  2469. COLORREF CTokenizer::ParseRGB()
  2470. {
  2471. CToken* theToken = GetToken();
  2472. if (theToken->GetType() != TK_INT)
  2473. {
  2474. Error(TKERR_EXPECTED_INTEGER);
  2475. theToken->Delete();
  2476. return RGB(0, 0, 0);
  2477. }
  2478. int red = theToken->GetIntValue();
  2479. theToken->Delete();
  2480. theToken = GetToken();
  2481. if (theToken->GetType() != TK_INT)
  2482. {
  2483. Error(TKERR_EXPECTED_INTEGER);
  2484. theToken->Delete();
  2485. return RGB(0, 0, 0);
  2486. }
  2487. int green = theToken->GetIntValue();
  2488. theToken->Delete();
  2489. theToken = GetToken();
  2490. if (theToken->GetType() != TK_INT)
  2491. {
  2492. Error(TKERR_EXPECTED_INTEGER);
  2493. theToken->Delete();
  2494. return RGB(0, 0, 0);
  2495. }
  2496. int blue = theToken->GetIntValue();
  2497. theToken->Delete();
  2498. return RGB(red, green, blue);
  2499. }
  2500. //
  2501. // CSymbolLookup
  2502. //
  2503. CSymbolLookup::CSymbolLookup()
  2504. {
  2505. }
  2506. CSymbolLookup::~CSymbolLookup()
  2507. {
  2508. }
  2509. CSymbolLookup* CSymbolLookup::Create(byte theByte)
  2510. {
  2511. CSymbolLookup* curLookup = new CSymbolLookup();
  2512. curLookup->Init(theByte);
  2513. return curLookup;
  2514. }
  2515. void CSymbolLookup::Delete()
  2516. {
  2517. if (m_sibling != NULL)
  2518. {
  2519. m_sibling->Delete();
  2520. m_sibling = NULL;
  2521. }
  2522. if (m_child != NULL)
  2523. {
  2524. m_child->Delete();
  2525. m_child = NULL;
  2526. }
  2527. delete this;
  2528. }
  2529. void CSymbolLookup::Init(byte theByte)
  2530. {
  2531. m_parent = NULL;
  2532. m_child = NULL;
  2533. m_sibling = NULL;
  2534. m_value = -1;
  2535. m_byte = theByte;
  2536. }
  2537. CSymbolLookup* CSymbolLookup::GetNext()
  2538. {
  2539. return m_sibling;
  2540. }
  2541. void CSymbolLookup::SetNext(CSymbolLookup* next)
  2542. {
  2543. m_sibling = next;
  2544. }
  2545. void CSymbolLookup::SetParent(CSymbolLookup* parent)
  2546. {
  2547. m_parent = parent;
  2548. }
  2549. void CSymbolLookup::SetValue(int value)
  2550. {
  2551. m_value = value;
  2552. }
  2553. int CSymbolLookup::GetValue()
  2554. {
  2555. return m_value;
  2556. }
  2557. byte CSymbolLookup::GetByte()
  2558. {
  2559. return m_byte;
  2560. }
  2561. CSymbolLookup** CSymbolLookup::GetChildAddress()
  2562. {
  2563. return &m_child;
  2564. }
  2565. CSymbolLookup* CSymbolLookup::GetChild()
  2566. {
  2567. return m_child;
  2568. }
  2569. CSymbolLookup* CSymbolLookup::GetParent()
  2570. {
  2571. return m_parent;
  2572. }