Variables, GO!

Also, broke up the parser a bit to ease compilation


git-svn-id: file:///srv/svn/ircclient/trunk@3 a9804ffe-773b-11dd-bd7c-89c3ef1d2733
This commit is contained in:
Correl Roush 2008-08-31 17:00:39 +00:00
parent 7315012830
commit 3dac90e658
6 changed files with 136 additions and 130 deletions

View file

@ -22,8 +22,11 @@ public:
bool unload(QString filename); bool unload(QString filename);
QString call_alias(QString alias, QStringList arguments); QString call_alias(QString alias, QStringList arguments);
QString variable(QString variable);
*/ */
bool hasVariable(QString variable);
QString variable(QString variable);
void variable(QString variable, QString value);
QMap<QString, QString> variables();
}; };
#endif #endif

View file

@ -1,3 +1,6 @@
#ifndef MIRC_PARSER_H
#define MIRC_PARSER_H
/* /*
Mercenary Mercenary
@ -17,7 +20,7 @@
#include <QStringList> #include <QStringList>
#include <QMap> #include <QMap>
#include <QStack> #include <QStack>
//#include "mirc.h"
class MIRCScriptManager; class MIRCScriptManager;
using namespace std; using namespace std;
@ -54,83 +57,18 @@ public:
mirc_aliases aliases; mirc_aliases aliases;
mirc_variables vars; mirc_variables vars;
mirc_script_engine(MIRCScriptManager *m) : script() { mirc_script_engine(MIRCScriptManager *m);
manager = m;
stage = PARSE;
current_alias = aliases.end();
current_variable = vars.end();
}
void handle_alias_definition(char const* str, char const* end) { void handle_alias_definition(char const* str, char const* end);
if (stage != PARSE) return; void handle_alias_definition_local(char const* str, char const* end);
void close_alias(char const*, char const*);
string s(str, end); void store_code(char const* str, char const* end);
aliases.insert(s.c_str(), mirc_alias(true)); void call_alias(char const*, char const*);
current_alias = aliases.find(s.c_str()); void return_alias(char const*, char const*);
} void declare_variable(char const* str, char const* end);
void handle_alias_definition_local(char const* str, char const* end) { void assign_variable(char const* str, char const* end);
if (stage != PARSE) return; void fetch_variable(char const*, char const*);
void append_expression(char const* str, char const *end);
string s(str, end);
aliases.insert(s.c_str(), mirc_alias(false));
current_alias = aliases.find(s.c_str());
}
void close_alias(char const*, char const*) {
if (stage != PARSE) return;
if (!aliases.empty() && current_alias != aliases.end()) {
current_alias = aliases.end();
}
}
void store_code(char const* str, char const* end) {
if (stage != PARSE) return;
string s(str, end);
if (!aliases.empty() && current_alias != aliases.end()) {
current_alias->code.append(s.c_str()).append("\n");
} else {
script.code.append(s.c_str()).append("\n");
}
}
void call_alias(char const*, char const*) {
if (stage != EXECUTE) return;
}
void return_alias(char const*, char const*) {
}
void declare_variable(char const* str, char const* end) {
if (stage != EXECUTE) return;
string s(str, end);
vars.insert(s.c_str(), "");
current_variable = vars.find(s.c_str());
stack.push(QStringList());
}
void assign_variable(char const* str, char const* end) {
if (stage != EXECUTE) return;
if (current_variable != vars.end()) {
string s(str, end);
*current_variable = (!stack.isEmpty() ? stack.pop().join(" ") : "");
current_variable = vars.end();
}
}
void fetch_variable(char const*, char const*) {
if (stage != EXECUTE) return;
}
void append_expression(char const* str, char const *end) {
if (stage != EXECUTE) return;
string s(str, end);
QStringList list;
if (stack.isEmpty()) {
list << s.c_str();
} else {
list = stack.pop();
list << s.c_str();
}
stack.push(list);
}
}; };
struct mirc_script : public grammar<mirc_script> { struct mirc_script : public grammar<mirc_script> {
@ -164,8 +102,11 @@ struct mirc_script : public grammar<mirc_script> {
s_action a_def ( bind( &mirc_script_engine::handle_alias_definition, self.actions, _1, _2 ) ); s_action a_def ( bind( &mirc_script_engine::handle_alias_definition, self.actions, _1, _2 ) );
s_action l_def ( bind( &mirc_script_engine::handle_alias_definition_local, self.actions, _1, _2 ) ); s_action l_def ( bind( &mirc_script_engine::handle_alias_definition_local, self.actions, _1, _2 ) );
s_action a_close ( bind( &mirc_script_engine::close_alias, self.actions, _1, _2 ) ); s_action a_close ( bind( &mirc_script_engine::close_alias, self.actions, _1, _2 ) );
s_action a_call ( bind( &mirc_script_engine::call_alias, self.actions, _1, _2 ) );
s_action a_return ( bind( &mirc_script_engine::return_alias, self.actions, _1, _2 ) );
s_action v_def ( bind( &mirc_script_engine::declare_variable, self.actions, _1, _2 ) ); s_action v_def ( bind( &mirc_script_engine::declare_variable, self.actions, _1, _2 ) );
s_action v_assign ( bind( &mirc_script_engine::assign_variable, self.actions, _1, _2 ) ); s_action v_assign ( bind( &mirc_script_engine::assign_variable, self.actions, _1, _2 ) );
s_action v_fetch ( bind( &mirc_script_engine::fetch_variable, self.actions, _1, _2 ) );
s_action e_append ( bind( &mirc_script_engine::append_expression, self.actions, _1, _2 ) ); s_action e_append ( bind( &mirc_script_engine::append_expression, self.actions, _1, _2 ) );
s_action s_code ( bind( &mirc_script_engine::store_code, self.actions, _1, _2 ) ); s_action s_code ( bind( &mirc_script_engine::store_code, self.actions, _1, _2 ) );
@ -177,7 +118,6 @@ struct mirc_script : public grammar<mirc_script> {
; ;
space space
= ( blank_p = ( blank_p
//| (ch_p('\\') >> eol_p)
| str_p("$&") >> *blank_p >> eol_p | str_p("$&") >> *blank_p >> eol_p
) )
; ;
@ -185,10 +125,10 @@ struct mirc_script : public grammar<mirc_script> {
= alpha_p >> *alnum_p = alpha_p >> *alnum_p
; ;
string string
= ( variable = ( variable[e_append][v_fetch]
| alias_function | alias_function[e_append]
| +(graph_p - ch_p(',') - ch_p('(') - ch_p(')')) | (+(graph_p - ch_p(',') - ch_p('(') - ch_p(')')))[e_append]
)[e_append] )
; ;
expression expression
= string >> *(*space >> string) = string >> *(*space >> string)
@ -217,19 +157,11 @@ struct mirc_script : public grammar<mirc_script> {
>> !( >> !(
ch_p('(') >> *space ch_p('(') >> *space
>> parameters >> *space >> parameters >> *space
/*
>> (expression - ch_p(','))
>> *( *space
>> ch_p(',') >> *space
>> (expression - ch_p(','))
)
*/
>> ch_p(')') >> ch_p(')')
) )
; ;
alias_definition alias_definition
= str_p("alias") >> *space = str_p("alias") >> *space
//>> !(str_p("-l") >> *space)
>> if_p(str_p("-l") >> *space)[identifier[l_def]].else_p[identifier[a_def]] >> if_p(str_p("-l") >> *space)[identifier[l_def]].else_p[identifier[a_def]]
>> *space >> !eol_p >> *space >> !eol_p
>> code_block >> code_block
@ -271,3 +203,5 @@ struct mirc_script : public grammar<mirc_script> {
rule<ScannerT> const& start() const { return script; } rule<ScannerT> const& start() const { return script; }
}; };
}; };
#endif

View file

@ -13,4 +13,5 @@ INCLUDEPATH += . includes
HEADERS += includes/mirc.h includes/parser.h includes/script.h HEADERS += includes/mirc.h includes/parser.h includes/script.h
SOURCES += src/mirc.cpp \ SOURCES += src/mirc.cpp \
src/parser.cpp \ src/parser.cpp \
src/script.cpp src/script.cpp \
src/main.cpp

View file

@ -3,3 +3,19 @@
MIRCScriptManager::MIRCScriptManager(QObject *parent) { MIRCScriptManager::MIRCScriptManager(QObject *parent) {
this->parent = parent; this->parent = parent;
} }
bool MIRCScriptManager::hasVariable(QString variable) {
return _variables.contains(variable);
}
QString MIRCScriptManager::variable(QString variable) {
return _variables.value(variable);
}
void MIRCScriptManager::variable(QString variable, QString value) {
_variables[variable] = value;
}
QMap<QString, QString> MIRCScriptManager::variables() {
return _variables;
}

View file

@ -1,39 +1,90 @@
#include <QTextStream> #include "parser.h"
#include "script.h" #include "mirc.h"
int main(int argc, char* argv[]) { mirc_script_engine::mirc_script_engine(MIRCScriptManager *m) : script() {
QTextStream output(stdout); manager = m;
stage = PARSE;
current_alias = aliases.end();
current_variable = vars.end();
}
MIRCScriptManager *mirc = new MIRCScriptManager; void mirc_script_engine::handle_alias_definition(char const* str, char const* end) {
MIRCScript *ms = new MIRCScript(mirc); if (stage != PARSE) return;
if (argc < 2) {
output << "No mIRC script file was specified!\n"; string s(str, end);
return(1); aliases.insert(s.c_str(), mirc_alias(true));
current_alias = aliases.find(s.c_str());
} }
output << "Attempting to load " << argv[1] << "\n"; void mirc_script_engine::handle_alias_definition_local(char const* str, char const* end) {
if (ms->load(argv[1])) { if (stage != PARSE) return;
output << "MRC LOADED\n";
output << "Code:\n" << ms->code(); string s(str, end);
output << "Aliases:\n"; aliases.insert(s.c_str(), mirc_alias(false));
QMapIterator<QString, mirc_alias> alias(ms->aliases()); current_alias = aliases.find(s.c_str());
while(alias.hasNext()) {
alias.next();
output << (alias.value().global ? "global" : "local");
output << " " << alias.key() << "\n";
} }
if (ms->run()) { void mirc_script_engine::close_alias(char const*, char const*) {
output << "MRC RAN SUCCESSFULLY\n"; if (stage != PARSE) return;
QMapIterator<QString, QString> i(ms->variables());
output << "Variables:\n"; if (!aliases.empty() && current_alias != aliases.end()) {
while(i.hasNext()) { current_alias = aliases.end();
i.next();
output << i.key() << " = " << i.value() << "\n";
} }
} }
void mirc_script_engine::store_code(char const* str, char const* end) {
if (stage != PARSE) return;
string s(str, end);
if (!aliases.empty() && current_alias != aliases.end()) {
current_alias->code.append(s.c_str()).append("\n");
} else { } else {
output << "Failed to load " << argv[1] << "\n"; script.code.append(s.c_str()).append("\n");
return(1);
} }
}
void mirc_script_engine::call_alias(char const*, char const*) {
if (stage != EXECUTE) return;
return 0; }
void mirc_script_engine::return_alias(char const*, char const*) {
}
void mirc_script_engine::declare_variable(char const* str, char const* end) {
if (stage != EXECUTE) return;
string s(str, end);
vars.insert(s.c_str(), "");
current_variable = vars.find(s.c_str());
stack.push(QStringList());
}
void mirc_script_engine::assign_variable(char const* str, char const* end) {
if (stage != EXECUTE) return;
if (current_variable != vars.end()) {
string s(str, end);
*current_variable = (!stack.isEmpty() ? stack.pop().join(" ") : "");
manager->variable(current_variable.key(), current_variable.value());
current_variable = vars.end();
}
}
void mirc_script_engine::fetch_variable(char const*, char const*) {
if (stage != EXECUTE) return;
if (!stack.isEmpty()) {
QStringList values = stack.pop();
if (!values.isEmpty()) {
QString var = values.last();
values.removeLast();
values << (manager->hasVariable(var) ? manager->variable(var) : vars[var]);
}
stack.push(values);
}
}
void mirc_script_engine::append_expression(char const* str, char const *end) {
if (stage != EXECUTE) return;
string s(str, end);
QStringList list;
if (stack.isEmpty()) {
list << s.c_str();
} else {
list = stack.pop();
list << s.c_str();
}
stack.push(list);
} }

View file

@ -1,6 +1,7 @@
; Hey, here's some test code ; Hey, here's some test code
set name Correl set name Correl
%name = Correl $& %first = Correl
%name = %first $&
Roush Roush
echo Hello, %name! echo Hello, %name!
alias dostuff { alias dostuff {