diff options
| author | Pierre Bourdon <delroth@gmail.com> | 2016-06-24 10:43:46 +0200 |
|---|---|---|
| committer | Pierre Bourdon <delroth@gmail.com> | 2016-06-24 10:43:46 +0200 |
| commit | 3570c7f03a2aa90aa634f96c0af1969af610f14d (patch) | |
| tree | 4252e03c0e853ba7cffe022937698c854ad0eaa9 /Source/Core/InputCommon/ControllerInterface/ExpressionParser.cpp | |
| parent | 2115e8a4a6814e32107b5205ff5c95bbd3c6e99c (diff) | |
Reformat all the things. Have fun with merge conflicts.
Diffstat (limited to 'Source/Core/InputCommon/ControllerInterface/ExpressionParser.cpp')
| -rw-r--r-- | Source/Core/InputCommon/ControllerInterface/ExpressionParser.cpp | 981 |
1 files changed, 463 insertions, 518 deletions
diff --git a/Source/Core/InputCommon/ControllerInterface/ExpressionParser.cpp b/Source/Core/InputCommon/ControllerInterface/ExpressionParser.cpp index bcb2c95a96..a87bdf8d35 100644 --- a/Source/Core/InputCommon/ControllerInterface/ExpressionParser.cpp +++ b/Source/Core/InputCommon/ControllerInterface/ExpressionParser.cpp @@ -17,601 +17,546 @@ namespace ciface { namespace ExpressionParser { - enum TokenType { - TOK_DISCARD, - TOK_INVALID, - TOK_EOF, - TOK_LPAREN, - TOK_RPAREN, - TOK_AND, - TOK_OR, - TOK_NOT, - TOK_ADD, - TOK_CONTROL, + TOK_DISCARD, + TOK_INVALID, + TOK_EOF, + TOK_LPAREN, + TOK_RPAREN, + TOK_AND, + TOK_OR, + TOK_NOT, + TOK_ADD, + TOK_CONTROL, }; inline std::string OpName(TokenType op) { - switch (op) - { - case TOK_AND: - return "And"; - case TOK_OR: - return "Or"; - case TOK_NOT: - return "Not"; - case TOK_ADD: - return "Add"; - default: - assert(false); - return ""; - } + switch (op) + { + case TOK_AND: + return "And"; + case TOK_OR: + return "Or"; + case TOK_NOT: + return "Not"; + case TOK_ADD: + return "Add"; + default: + assert(false); + return ""; + } } class Token { public: - TokenType type; - ControlQualifier qualifier; - - Token(TokenType type_) : type(type_) {} - Token(TokenType type_, ControlQualifier qualifier_) : type(type_), qualifier(qualifier_) {} - - operator std::string() - { - switch (type) - { - case TOK_DISCARD: - return "Discard"; - case TOK_EOF: - return "EOF"; - case TOK_LPAREN: - return "("; - case TOK_RPAREN: - return ")"; - case TOK_AND: - return "&"; - case TOK_OR: - return "|"; - case TOK_NOT: - return "!"; - case TOK_ADD: - return "+"; - case TOK_CONTROL: - return "Device(" + (std::string)qualifier + ")"; - case TOK_INVALID: - break; - } - - return "Invalid"; - } + TokenType type; + ControlQualifier qualifier; + + Token(TokenType type_) : type(type_) {} + Token(TokenType type_, ControlQualifier qualifier_) : type(type_), qualifier(qualifier_) {} + operator std::string() + { + switch (type) + { + case TOK_DISCARD: + return "Discard"; + case TOK_EOF: + return "EOF"; + case TOK_LPAREN: + return "("; + case TOK_RPAREN: + return ")"; + case TOK_AND: + return "&"; + case TOK_OR: + return "|"; + case TOK_NOT: + return "!"; + case TOK_ADD: + return "+"; + case TOK_CONTROL: + return "Device(" + (std::string)qualifier + ")"; + case TOK_INVALID: + break; + } + + return "Invalid"; + } }; -class Lexer { +class Lexer +{ public: - std::string expr; - std::string::iterator it; - - Lexer(const std::string& expr_) : expr(expr_) - { - it = expr.begin(); - } - - bool FetchBacktickString(std::string &value, char otherDelim = 0) - { - value = ""; - while (it != expr.end()) - { - char c = *it; - ++it; - if (c == '`') - return false; - if (c > 0 && c == otherDelim) - return true; - value += c; - } - return false; - } - - Token GetFullyQualifiedControl() - { - ControlQualifier qualifier; - std::string value; - - if (FetchBacktickString(value, ':')) - { - // Found colon, this is the device name - qualifier.has_device = true; - qualifier.device_qualifier.FromString(value); - FetchBacktickString(value); - } - - qualifier.control_name = value; - - return Token(TOK_CONTROL, qualifier); - } - - Token GetBarewordsControl(char c) - { - std::string name; - name += c; - - while (it != expr.end()) - { - c = *it; - if (!isalpha(c)) - break; - name += c; - ++it; - } - - ControlQualifier qualifier; - qualifier.control_name = name; - return Token(TOK_CONTROL, qualifier); - } - - Token NextToken() - { - if (it == expr.end()) - return Token(TOK_EOF); - - char c = *it++; - switch (c) - { - case ' ': - case '\t': - case '\n': - case '\r': - return Token(TOK_DISCARD); - case '(': - return Token(TOK_LPAREN); - case ')': - return Token(TOK_RPAREN); - case '&': - return Token(TOK_AND); - case '|': - return Token(TOK_OR); - case '!': - return Token(TOK_NOT); - case '+': - return Token(TOK_ADD); - case '`': - return GetFullyQualifiedControl(); - default: - if (isalpha(c)) - return GetBarewordsControl(c); - else - return Token(TOK_INVALID); - } - } - - ExpressionParseStatus Tokenize(std::vector<Token> &tokens) - { - while (true) - { - Token tok = NextToken(); - - if (tok.type == TOK_DISCARD) - continue; - - if (tok.type == TOK_INVALID) - { - tokens.clear(); - return EXPRESSION_PARSE_SYNTAX_ERROR; - } - - tokens.push_back(tok); - - if (tok.type == TOK_EOF) - break; - } - return EXPRESSION_PARSE_SUCCESS; - } + std::string expr; + std::string::iterator it; + + Lexer(const std::string& expr_) : expr(expr_) { it = expr.begin(); } + bool FetchBacktickString(std::string& value, char otherDelim = 0) + { + value = ""; + while (it != expr.end()) + { + char c = *it; + ++it; + if (c == '`') + return false; + if (c > 0 && c == otherDelim) + return true; + value += c; + } + return false; + } + + Token GetFullyQualifiedControl() + { + ControlQualifier qualifier; + std::string value; + + if (FetchBacktickString(value, ':')) + { + // Found colon, this is the device name + qualifier.has_device = true; + qualifier.device_qualifier.FromString(value); + FetchBacktickString(value); + } + + qualifier.control_name = value; + + return Token(TOK_CONTROL, qualifier); + } + + Token GetBarewordsControl(char c) + { + std::string name; + name += c; + + while (it != expr.end()) + { + c = *it; + if (!isalpha(c)) + break; + name += c; + ++it; + } + + ControlQualifier qualifier; + qualifier.control_name = name; + return Token(TOK_CONTROL, qualifier); + } + + Token NextToken() + { + if (it == expr.end()) + return Token(TOK_EOF); + + char c = *it++; + switch (c) + { + case ' ': + case '\t': + case '\n': + case '\r': + return Token(TOK_DISCARD); + case '(': + return Token(TOK_LPAREN); + case ')': + return Token(TOK_RPAREN); + case '&': + return Token(TOK_AND); + case '|': + return Token(TOK_OR); + case '!': + return Token(TOK_NOT); + case '+': + return Token(TOK_ADD); + case '`': + return GetFullyQualifiedControl(); + default: + if (isalpha(c)) + return GetBarewordsControl(c); + else + return Token(TOK_INVALID); + } + } + + ExpressionParseStatus Tokenize(std::vector<Token>& tokens) + { + while (true) + { + Token tok = NextToken(); + + if (tok.type == TOK_DISCARD) + continue; + + if (tok.type == TOK_INVALID) + { + tokens.clear(); + return EXPRESSION_PARSE_SYNTAX_ERROR; + } + + tokens.push_back(tok); + + if (tok.type == TOK_EOF) + break; + } + return EXPRESSION_PARSE_SUCCESS; + } }; class ExpressionNode { public: - virtual ~ExpressionNode() {} - virtual ControlState GetValue() { return 0; } - virtual void SetValue(ControlState state) {} - virtual int CountNumControls() { return 0; } - virtual operator std::string() { return ""; } + virtual ~ExpressionNode() {} + virtual ControlState GetValue() { return 0; } + virtual void SetValue(ControlState state) {} + virtual int CountNumControls() { return 0; } + virtual operator std::string() { return ""; } }; class DummyExpression : public ExpressionNode { public: - std::string name; - - DummyExpression(const std::string& name_) : name(name_) {} - - ControlState GetValue() override - { - return 0.0; - } - - void SetValue(ControlState value) override - { - } + std::string name; - int CountNumControls() override - { - return 0; - } - - operator std::string() override - { - return "`" + name + "`"; - } + DummyExpression(const std::string& name_) : name(name_) {} + ControlState GetValue() override { return 0.0; } + void SetValue(ControlState value) override {} + int CountNumControls() override { return 0; } + operator std::string() override { return "`" + name + "`"; } }; class ControlExpression : public ExpressionNode { public: - ControlQualifier qualifier; - Device::Control *control; - - ControlExpression(ControlQualifier qualifier_, Device::Control *control_) : qualifier(qualifier_), control(control_) {} - - ControlState GetValue() override - { - return control->ToInput()->GetGatedState(); - } - - void SetValue(ControlState value) override - { - control->ToOutput()->SetGatedState(value); - } - - int CountNumControls() override - { - return 1; - } - - operator std::string() override - { - return "`" + (std::string)qualifier + "`"; - } + ControlQualifier qualifier; + Device::Control* control; + + ControlExpression(ControlQualifier qualifier_, Device::Control* control_) + : qualifier(qualifier_), control(control_) + { + } + + ControlState GetValue() override { return control->ToInput()->GetGatedState(); } + void SetValue(ControlState value) override { control->ToOutput()->SetGatedState(value); } + int CountNumControls() override { return 1; } + operator std::string() override { return "`" + (std::string)qualifier + "`"; } }; class BinaryExpression : public ExpressionNode { public: - TokenType op; - ExpressionNode *lhs; - ExpressionNode *rhs; - - BinaryExpression(TokenType op_, ExpressionNode *lhs_, ExpressionNode *rhs_) : op(op_), lhs(lhs_), rhs(rhs_) {} - virtual ~BinaryExpression() - { - delete lhs; - delete rhs; - } - - ControlState GetValue() override - { - ControlState lhsValue = lhs->GetValue(); - ControlState rhsValue = rhs->GetValue(); - switch (op) - { - case TOK_AND: - return std::min(lhsValue, rhsValue); - case TOK_OR: - return std::max(lhsValue, rhsValue); - case TOK_ADD: - return std::min(lhsValue + rhsValue, 1.0); - default: - assert(false); - return 0; - } - } - - void SetValue(ControlState value) override - { - // Don't do anything special with the op we have. - // Treat "A & B" the same as "A | B". - lhs->SetValue(value); - rhs->SetValue(value); - } - - int CountNumControls() override - { - return lhs->CountNumControls() + rhs->CountNumControls(); - } - - operator std::string() override - { - return OpName(op) + "(" + (std::string)(*lhs) + ", " + (std::string)(*rhs) + ")"; - } + TokenType op; + ExpressionNode* lhs; + ExpressionNode* rhs; + + BinaryExpression(TokenType op_, ExpressionNode* lhs_, ExpressionNode* rhs_) + : op(op_), lhs(lhs_), rhs(rhs_) + { + } + virtual ~BinaryExpression() + { + delete lhs; + delete rhs; + } + + ControlState GetValue() override + { + ControlState lhsValue = lhs->GetValue(); + ControlState rhsValue = rhs->GetValue(); + switch (op) + { + case TOK_AND: + return std::min(lhsValue, rhsValue); + case TOK_OR: + return std::max(lhsValue, rhsValue); + case TOK_ADD: + return std::min(lhsValue + rhsValue, 1.0); + default: + assert(false); + return 0; + } + } + + void SetValue(ControlState value) override + { + // Don't do anything special with the op we have. + // Treat "A & B" the same as "A | B". + lhs->SetValue(value); + rhs->SetValue(value); + } + + int CountNumControls() override { return lhs->CountNumControls() + rhs->CountNumControls(); } + operator std::string() override + { + return OpName(op) + "(" + (std::string)(*lhs) + ", " + (std::string)(*rhs) + ")"; + } }; class UnaryExpression : public ExpressionNode { public: - TokenType op; - ExpressionNode *inner; - - UnaryExpression(TokenType op_, ExpressionNode *inner_) : op(op_), inner(inner_) {} - virtual ~UnaryExpression() - { - delete inner; - } - - ControlState GetValue() override - { - ControlState value = inner->GetValue(); - switch (op) - { - case TOK_NOT: - return 1.0 - value; - default: - assert(false); - return 0; - } - } - - void SetValue(ControlState value) override - { - switch (op) - { - case TOK_NOT: - inner->SetValue(1.0 - value); - break; - - default: - assert(false); - } - } - - int CountNumControls() override - { - return inner->CountNumControls(); - } - - operator std::string() override - { - return OpName(op) + "(" + (std::string)(*inner) + ")"; - } + TokenType op; + ExpressionNode* inner; + + UnaryExpression(TokenType op_, ExpressionNode* inner_) : op(op_), inner(inner_) {} + virtual ~UnaryExpression() { delete inner; } + ControlState GetValue() override + { + ControlState value = inner->GetValue(); + switch (op) + { + case TOK_NOT: + return 1.0 - value; + default: + assert(false); + return 0; + } + } + + void SetValue(ControlState value) override + { + switch (op) + { + case TOK_NOT: + inner->SetValue(1.0 - value); + break; + + default: + assert(false); + } + } + + int CountNumControls() override { return inner->CountNumControls(); } + operator std::string() override { return OpName(op) + "(" + (std::string)(*inner) + ")"; } }; -Device *ControlFinder::FindDevice(ControlQualifier qualifier) +Device* ControlFinder::FindDevice(ControlQualifier qualifier) { - if (qualifier.has_device) - return container.FindDevice(qualifier.device_qualifier); - else - return container.FindDevice(default_device); + if (qualifier.has_device) + return container.FindDevice(qualifier.device_qualifier); + else + return container.FindDevice(default_device); } -Device::Control *ControlFinder::FindControl(ControlQualifier qualifier) +Device::Control* ControlFinder::FindControl(ControlQualifier qualifier) { - Device *device = FindDevice(qualifier); - if (!device) - return nullptr; - - if (is_input) - return device->FindInput(qualifier.control_name); - else - return device->FindOutput(qualifier.control_name); + Device* device = FindDevice(qualifier); + if (!device) + return nullptr; + + if (is_input) + return device->FindInput(qualifier.control_name); + else + return device->FindOutput(qualifier.control_name); } class Parser { public: - - Parser(std::vector<Token> tokens_, ControlFinder &finder_) : tokens(tokens_), finder(finder_) - { - m_it = tokens.begin(); - } - - ExpressionParseStatus Parse(Expression **expr_out) - { - ExpressionNode *node; - ExpressionParseStatus status = Toplevel(&node); - if (status != EXPRESSION_PARSE_SUCCESS) - return status; - - *expr_out = new Expression(node); - return EXPRESSION_PARSE_SUCCESS; - } + Parser(std::vector<Token> tokens_, ControlFinder& finder_) : tokens(tokens_), finder(finder_) + { + m_it = tokens.begin(); + } + + ExpressionParseStatus Parse(Expression** expr_out) + { + ExpressionNode* node; + ExpressionParseStatus status = Toplevel(&node); + if (status != EXPRESSION_PARSE_SUCCESS) + return status; + + *expr_out = new Expression(node); + return EXPRESSION_PARSE_SUCCESS; + } private: - std::vector<Token> tokens; - std::vector<Token>::iterator m_it; - ControlFinder &finder; - - Token Chew() - { - return *m_it++; - } - - Token Peek() - { - return *m_it; - } - - bool Expects(TokenType type) - { - Token tok = Chew(); - return tok.type == type; - } - - ExpressionParseStatus Atom(ExpressionNode **expr_out) - { - Token tok = Chew(); - switch (tok.type) - { - case TOK_CONTROL: - { - Device::Control *control = finder.FindControl(tok.qualifier); - if (control == nullptr) - { - *expr_out = new DummyExpression(tok.qualifier); - return EXPRESSION_PARSE_SUCCESS; - } - - *expr_out = new ControlExpression(tok.qualifier, control); - return EXPRESSION_PARSE_SUCCESS; - } - case TOK_LPAREN: - return Paren(expr_out); - default: - return EXPRESSION_PARSE_SYNTAX_ERROR; - } - } - - bool IsUnaryExpression(TokenType type) - { - switch (type) - { - case TOK_NOT: - return true; - default: - return false; - } - } - - ExpressionParseStatus Unary(ExpressionNode **expr_out) - { - ExpressionParseStatus status; - - if (IsUnaryExpression(Peek().type)) - { - Token tok = Chew(); - ExpressionNode *atom_expr; - if ((status = Atom(&atom_expr)) != EXPRESSION_PARSE_SUCCESS) - return status; - *expr_out = new UnaryExpression(tok.type, atom_expr); - return EXPRESSION_PARSE_SUCCESS; - } - - return Atom(expr_out); - } - - bool IsBinaryToken(TokenType type) - { - switch (type) - { - case TOK_AND: - case TOK_OR: - case TOK_ADD: - return true; - default: - return false; - } - } - - ExpressionParseStatus Binary(ExpressionNode **expr_out) - { - ExpressionParseStatus status; - - if ((status = Unary(expr_out)) != EXPRESSION_PARSE_SUCCESS) - return status; - - while (IsBinaryToken(Peek().type)) - { - Token tok = Chew(); - ExpressionNode *unary_expr; - if ((status = Unary(&unary_expr)) != EXPRESSION_PARSE_SUCCESS) - { - delete *expr_out; - return status; - } - - *expr_out = new BinaryExpression(tok.type, *expr_out, unary_expr); - } - - return EXPRESSION_PARSE_SUCCESS; - } - - ExpressionParseStatus Paren(ExpressionNode **expr_out) - { - ExpressionParseStatus status; - - // lparen already chewed - if ((status = Toplevel(expr_out)) != EXPRESSION_PARSE_SUCCESS) - return status; - - if (!Expects(TOK_RPAREN)) - { - delete *expr_out; - return EXPRESSION_PARSE_SYNTAX_ERROR; - } - - return EXPRESSION_PARSE_SUCCESS; - } - - ExpressionParseStatus Toplevel(ExpressionNode **expr_out) - { - return Binary(expr_out); - } + std::vector<Token> tokens; + std::vector<Token>::iterator m_it; + ControlFinder& finder; + + Token Chew() { return *m_it++; } + Token Peek() { return *m_it; } + bool Expects(TokenType type) + { + Token tok = Chew(); + return tok.type == type; + } + + ExpressionParseStatus Atom(ExpressionNode** expr_out) + { + Token tok = Chew(); + switch (tok.type) + { + case TOK_CONTROL: + { + Device::Control* control = finder.FindControl(tok.qualifier); + if (control == nullptr) + { + *expr_out = new DummyExpression(tok.qualifier); + return EXPRESSION_PARSE_SUCCESS; + } + + *expr_out = new ControlExpression(tok.qualifier, control); + return EXPRESSION_PARSE_SUCCESS; + } + case TOK_LPAREN: + return Paren(expr_out); + default: + return EXPRESSION_PARSE_SYNTAX_ERROR; + } + } + + bool IsUnaryExpression(TokenType type) + { + switch (type) + { + case TOK_NOT: + return true; + default: + return false; + } + } + + ExpressionParseStatus Unary(ExpressionNode** expr_out) + { + ExpressionParseStatus status; + + if (IsUnaryExpression(Peek().type)) + { + Token tok = Chew(); + ExpressionNode* atom_expr; + if ((status = Atom(&atom_expr)) != EXPRESSION_PARSE_SUCCESS) + return status; + *expr_out = new UnaryExpression(tok.type, atom_expr); + return EXPRESSION_PARSE_SUCCESS; + } + + return Atom(expr_out); + } + + bool IsBinaryToken(TokenType type) + { + switch (type) + { + case TOK_AND: + case TOK_OR: + case TOK_ADD: + return true; + default: + return false; + } + } + + ExpressionParseStatus Binary(ExpressionNode** expr_out) + { + ExpressionParseStatus status; + + if ((status = Unary(expr_out)) != EXPRESSION_PARSE_SUCCESS) + return status; + + while (IsBinaryToken(Peek().type)) + { + Token tok = Chew(); + ExpressionNode* unary_expr; + if ((status = Unary(&unary_expr)) != EXPRESSION_PARSE_SUCCESS) + { + delete *expr_out; + return status; + } + + *expr_out = new BinaryExpression(tok.type, *expr_out, unary_expr); + } + + return EXPRESSION_PARSE_SUCCESS; + } + + ExpressionParseStatus Paren(ExpressionNode** expr_out) + { + ExpressionParseStatus status; + + // lparen already chewed + if ((status = Toplevel(expr_out)) != EXPRESSION_PARSE_SUCCESS) + return status; + + if (!Expects(TOK_RPAREN)) + { + delete *expr_out; + return EXPRESSION_PARSE_SYNTAX_ERROR; + } + + return EXPRESSION_PARSE_SUCCESS; + } + + ExpressionParseStatus Toplevel(ExpressionNode** expr_out) { return Binary(expr_out); } }; ControlState Expression::GetValue() { - return node->GetValue(); + return node->GetValue(); } void Expression::SetValue(ControlState value) { - node->SetValue(value); + node->SetValue(value); } -Expression::Expression(ExpressionNode *node_) +Expression::Expression(ExpressionNode* node_) { - node = node_; - num_controls = node->CountNumControls(); + node = node_; + num_controls = node->CountNumControls(); } Expression::~Expression() { - delete node; + delete node; } -static ExpressionParseStatus ParseExpressionInner(const std::string& str, ControlFinder &finder, Expression **expr_out) +static ExpressionParseStatus ParseExpressionInner(const std::string& str, ControlFinder& finder, + Expression** expr_out) { - ExpressionParseStatus status; - Expression *expr; - *expr_out = nullptr; - - if (str == "") - return EXPRESSION_PARSE_SUCCESS; - - Lexer l(str); - std::vector<Token> tokens; - status = l.Tokenize(tokens); - if (status != EXPRESSION_PARSE_SUCCESS) - return status; - - Parser p(tokens, finder); - status = p.Parse(&expr); - if (status != EXPRESSION_PARSE_SUCCESS) - return status; - - *expr_out = expr; - return EXPRESSION_PARSE_SUCCESS; + ExpressionParseStatus status; + Expression* expr; + *expr_out = nullptr; + + if (str == "") + return EXPRESSION_PARSE_SUCCESS; + + Lexer l(str); + std::vector<Token> tokens; + status = l.Tokenize(tokens); + if (status != EXPRESSION_PARSE_SUCCESS) + return status; + + Parser p(tokens, finder); + status = p.Parse(&expr); + if (status != EXPRESSION_PARSE_SUCCESS) + return status; + + *expr_out = expr; + return EXPRESSION_PARSE_SUCCESS; } -ExpressionParseStatus ParseExpression(const std::string& str, ControlFinder &finder, Expression **expr_out) +ExpressionParseStatus ParseExpression(const std::string& str, ControlFinder& finder, + Expression** expr_out) { - // Add compatibility with old simple expressions, which are simple - // barewords control names. + // Add compatibility with old simple expressions, which are simple + // barewords control names. - ControlQualifier qualifier; - qualifier.control_name = str; - qualifier.has_device = false; + ControlQualifier qualifier; + qualifier.control_name = str; + qualifier.has_device = false; - Device::Control *control = finder.FindControl(qualifier); - if (control) - { - *expr_out = new Expression(new ControlExpression(qualifier, control)); - return EXPRESSION_PARSE_SUCCESS; - } + Device::Control* control = finder.FindControl(qualifier); + if (control) + { + *expr_out = new Expression(new ControlExpression(qualifier, control)); + return EXPRESSION_PARSE_SUCCESS; + } - return ParseExpressionInner(str, finder, expr_out); + return ParseExpressionInner(str, finder, expr_out); } - } } |
