1 #include "stringparser.hpp"
2 
3 #include <algorithm>
4 #include <iterator>
5 
6 #include <components/misc/stringops.hpp>
7 
8 #include "scanner.hpp"
9 #include "generator.hpp"
10 #include "context.hpp"
11 #include "extensions.hpp"
12 
13 namespace Compiler
14 {
StringParser(ErrorHandler & errorHandler,const Context & context,Literals & literals)15     StringParser::StringParser (ErrorHandler& errorHandler, const Context& context, Literals& literals)
16     : Parser (errorHandler, context), mLiterals (literals), mState (StartState), mSmashCase (false), mDiscard (false)
17     {
18 
19     }
20 
parseName(const std::string & name,const TokenLoc & loc,Scanner & scanner)21     bool StringParser::parseName (const std::string& name, const TokenLoc& loc,
22         Scanner& scanner)
23     {
24         if (mState==StartState || mState==CommaState)
25         {
26             start();
27             mTokenLoc = loc;
28 
29             if (!mDiscard)
30             {
31                 if (mSmashCase)
32                     Generator::pushString (mCode, mLiterals, Misc::StringUtils::lowerCase (name));
33                 else
34                     Generator::pushString (mCode, mLiterals, name);
35             }
36 
37             return false;
38         }
39 
40         return Parser::parseName (name, loc, scanner);
41     }
42 
parseKeyword(int keyword,const TokenLoc & loc,Scanner & scanner)43     bool StringParser::parseKeyword (int keyword, const TokenLoc& loc, Scanner& scanner)
44     {
45         if (const Extensions *extensions = getContext().getExtensions())
46         {
47             std::string argumentType; // ignored
48             bool hasExplicit = false; // ignored
49             if (extensions->isInstruction (keyword, argumentType, hasExplicit))
50             {
51                 // pretend this is not a keyword
52                 std::string name = loc.mLiteral;
53                 if (name.size()>=2 && name[0]=='"' && name[name.size()-1]=='"')
54                     name = name.substr (1, name.size()-2);
55                 return parseName (name, loc, scanner);
56             }
57         }
58 
59         if (keyword==Scanner::K_end || keyword==Scanner::K_begin ||
60             keyword==Scanner::K_short || keyword==Scanner::K_long ||
61             keyword==Scanner::K_float || keyword==Scanner::K_if ||
62             keyword==Scanner::K_endif || keyword==Scanner::K_else ||
63             keyword==Scanner::K_elseif || keyword==Scanner::K_while ||
64             keyword==Scanner::K_endwhile || keyword==Scanner::K_return ||
65             keyword==Scanner::K_messagebox || keyword==Scanner::K_set ||
66             keyword==Scanner::K_to || keyword==Scanner::K_getsquareroot)
67         {
68             return parseName (loc.mLiteral, loc, scanner);
69         }
70 
71         return Parser::parseKeyword (keyword, loc, scanner);
72     }
73 
parseSpecial(int code,const TokenLoc & loc,Scanner & scanner)74     bool StringParser::parseSpecial (int code, const TokenLoc& loc, Scanner& scanner)
75     {
76         if (code==Scanner::S_comma && mState==StartState)
77         {
78             mState = CommaState;
79             return true;
80         }
81 
82         return Parser::parseSpecial (code, loc, scanner);
83     }
84 
append(std::vector<Interpreter::Type_Code> & code)85     void StringParser::append (std::vector<Interpreter::Type_Code>& code)
86     {
87         std::copy (mCode.begin(), mCode.end(), std::back_inserter (code));
88     }
89 
reset()90     void StringParser::reset()
91     {
92         mState = StartState;
93         mCode.clear();
94         mSmashCase = false;
95         mTokenLoc = TokenLoc();
96         mDiscard = false;
97         Parser::reset();
98     }
99 
smashCase()100     void StringParser::smashCase()
101     {
102         mSmashCase = true;
103     }
104 
getTokenLoc() const105     const TokenLoc& StringParser::getTokenLoc() const
106     {
107         return mTokenLoc;
108     }
109 
discard()110     void StringParser::discard()
111     {
112         mDiscard = true;
113     }
114 }
115