mirror of
https://github.com/vcmi/vcmi.git
synced 2024-12-24 22:14:36 +02:00
* a few bugs in interpreter fixed
This commit is contained in:
parent
7c771e5c56
commit
95b16906aa
@ -378,13 +378,13 @@ void ERMInterpreter::scanForScripts()
|
||||
FileInfo * finfo = new FileInfo;
|
||||
finfo->filename = dir->path().string();
|
||||
|
||||
std::vector<ERM::TLine> buf = ep.parseFile();
|
||||
std::vector<LineInfo> buf = ep.parseFile();
|
||||
finfo->length = buf.size();
|
||||
files.push_back(finfo);
|
||||
|
||||
for(int g=0; g<buf.size(); ++g)
|
||||
{
|
||||
scripts[LinePointer(finfo, g)] = buf[g];
|
||||
scripts[LinePointer(finfo, g, buf[g].realLineNum)] = buf[g].tl;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -509,11 +509,11 @@ bool ERMInterpreter::isATrigger( const ERM::TLine & line )
|
||||
break;
|
||||
case 1: //erm
|
||||
{
|
||||
TERMline line = boost::get<TERMline>(line);
|
||||
switch(line.which())
|
||||
TERMline ermline = boost::get<TERMline>(line);
|
||||
switch(ermline.which())
|
||||
{
|
||||
case 0: //tcmd
|
||||
return isCMDATrigger( boost::get<ERM::Tcommand>(line) );
|
||||
return isCMDATrigger( boost::get<ERM::Tcommand>(ermline) );
|
||||
break;
|
||||
default:
|
||||
return false;
|
||||
@ -550,7 +550,7 @@ bool ERMInterpreter::isCMDATrigger( const ERM::Tcommand & cmd )
|
||||
|
||||
ERM::TLine ERMInterpreter::retrieveLine( LinePointer linePtr ) const
|
||||
{
|
||||
return *scripts.find(linePtr);
|
||||
return scripts.find(linePtr)->second;
|
||||
}
|
||||
|
||||
/////////
|
||||
@ -1062,7 +1062,7 @@ struct LVL1IexpDisemboweler : boost::static_visitor<IexpValStr>
|
||||
{
|
||||
if(dir == IexpDisemboweler::GET)
|
||||
{
|
||||
IexpValStr ret = IexpValStr(constant);
|
||||
return IexpValStr(constant);
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -1094,7 +1094,7 @@ IexpValStr ERMInterpreter::getIexp( const ERM::TIdentifierInternal & tid ) const
|
||||
{
|
||||
if(tid.which() == 0)
|
||||
{
|
||||
IexpValStr ievs = getIexp(boost::get<ERM::TIexp>(tid));
|
||||
return getIexp(boost::get<ERM::TIexp>(tid));
|
||||
}
|
||||
else
|
||||
throw EScriptExecError("Identifier must be a valid i-expression to perform this operation!");
|
||||
@ -1138,12 +1138,14 @@ ERM::Ttrigger ERMInterpreter::retrieveTrigger( ERM::TLine line )
|
||||
ERM::TERMline tl = boost::get<ERM::TERMline>(line);
|
||||
if(tl.which() == 0)
|
||||
{
|
||||
ERM::Tcommand tcm = boost::get<ERM::Tcommand>(line);
|
||||
ERM::Tcommand tcm = boost::get<ERM::Tcommand>(tl);
|
||||
if(tcm.cmd.which() == 0)
|
||||
{
|
||||
return boost::get<ERM::Ttrigger>(tcm.cmd);
|
||||
}
|
||||
throw ELineProblem("Given line is not a trigger!");
|
||||
}
|
||||
throw ELineProblem("Given line is not a command!");
|
||||
}
|
||||
throw ELineProblem("Given line is not an ERM trigger!");
|
||||
}
|
||||
@ -1412,6 +1414,7 @@ double & VERMInterpreter::TriggerLocalVars::getEvar( int num )
|
||||
|
||||
int & VERMInterpreter::TriggerLocalVars::getYvar( int num )
|
||||
{
|
||||
num = -num; //we handle negative indices
|
||||
if(num < 1 || num > YVAR_NUM)
|
||||
throw EScriptExecError("Number of trigger local variable out of bounds");
|
||||
|
||||
|
@ -220,10 +220,13 @@ namespace VERMInterpreter
|
||||
const FileInfo * file; //non-owning
|
||||
int lineNum;
|
||||
|
||||
int realLineNum;
|
||||
|
||||
LinePointer() : file(NULL)
|
||||
{}
|
||||
|
||||
LinePointer(const FileInfo * finfo, int line) : file(finfo), lineNum(line)
|
||||
LinePointer(const FileInfo * finfo, int line, int _realLineNum) : file(finfo), lineNum(line),
|
||||
realLineNum(_realLineNum)
|
||||
{}
|
||||
|
||||
//lexicographical order
|
||||
|
@ -177,10 +177,10 @@ ERMParser::ERMParser(std::string file)
|
||||
:srcFile(file)
|
||||
{}
|
||||
|
||||
std::vector<ERM::TLine> ERMParser::parseFile()
|
||||
std::vector<LineInfo> ERMParser::parseFile()
|
||||
{
|
||||
CERMPreprocessor preproc(srcFile);
|
||||
std::vector<ERM::TLine> ret;
|
||||
std::vector<LineInfo> ret;
|
||||
try
|
||||
{
|
||||
while(1)
|
||||
@ -190,7 +190,10 @@ std::vector<ERM::TLine> ERMParser::parseFile()
|
||||
break;
|
||||
|
||||
repairEncoding(command);
|
||||
ret.push_back(parseLine(command));
|
||||
LineInfo li;
|
||||
li.realLineNum = preproc.getCurLineNo();
|
||||
li.tl = parseLine(command, li.realLineNum);
|
||||
ret.push_back(li);
|
||||
}
|
||||
}
|
||||
catch (ParseErrorException & e)
|
||||
@ -482,7 +485,7 @@ namespace ERM
|
||||
};
|
||||
};
|
||||
|
||||
ERM::TLine ERMParser::parseLine( const std::string & line )
|
||||
ERM::TLine ERMParser::parseLine( const std::string & line, int realLineNo )
|
||||
{
|
||||
std::string::const_iterator beg = line.begin(),
|
||||
end = line.end();
|
||||
@ -493,7 +496,7 @@ ERM::TLine ERMParser::parseLine( const std::string & line )
|
||||
bool r = qi::phrase_parse(beg, end, ERMgrammar, ascii::space, AST);
|
||||
if(!r || beg != end)
|
||||
{
|
||||
tlog1 << "Parse error in file " << srcFile << " (line " << parsedLine << ") :\n" << line << std::endl;
|
||||
tlog1 << "Parse error in file " << srcFile << " (line " << realLineNo << ") :\n" << line << std::endl;
|
||||
tlog1 << "\tCannot parse: " << std::string(beg, end) << std::endl;
|
||||
throw ParseErrorException();
|
||||
}
|
||||
|
@ -28,6 +28,10 @@ class CERMPreprocessor
|
||||
public:
|
||||
CERMPreprocessor(const std::string &Fname);
|
||||
std::string retreiveCommandLine();
|
||||
int getCurLineNo() const
|
||||
{
|
||||
return lineNo;
|
||||
}
|
||||
};
|
||||
|
||||
//various classes that represent ERM/VERM AST
|
||||
@ -231,20 +235,25 @@ namespace ERM
|
||||
typedef boost::variant<TVExp, TERMline> TLine;
|
||||
}
|
||||
|
||||
struct LineInfo
|
||||
{
|
||||
ERM::TLine tl;
|
||||
int realLineNum;
|
||||
};
|
||||
|
||||
class ERMParser
|
||||
{
|
||||
private:
|
||||
std::string srcFile;
|
||||
int parsedLine;
|
||||
void repairEncoding(char * str, int len) const; //removes nonstandard ascii characters from string
|
||||
void repairEncoding(std::string & str) const; //removes nonstandard ascii characters from string
|
||||
enum ELineType{COMMAND_FULL, COMMENT, UNFINISHED, END_OF};
|
||||
int countHatsBeforeSemicolon(const std::string & line) const;
|
||||
ELineType classifyLine(const std::string & line, bool inString) const;
|
||||
ERM::TLine parseLine(const std::string & line);
|
||||
ERM::TLine parseLine(const std::string & line, int realLineNo);
|
||||
|
||||
|
||||
public:
|
||||
ERMParser(std::string file);
|
||||
std::vector<ERM::TLine> parseFile();
|
||||
std::vector<LineInfo> parseFile();
|
||||
};
|
||||
|
Loading…
Reference in New Issue
Block a user