2020-11-10 15:26:38 +01:00
# pragma once
2021-09-21 21:29:18 +02:00
# include <hex/pattern_language/token.hpp>
# include <hex/pattern_language/evaluator.hpp>
# include <hex/pattern_language/pattern_data.hpp>
2020-11-10 15:26:38 +01:00
2021-10-09 23:07:58 +02:00
# include <algorithm>
2020-12-06 21:40:57 +01:00
# include <bit>
2020-11-10 15:26:38 +01:00
# include <optional>
2021-09-11 23:14:22 +02:00
# include <map>
2021-04-21 10:17:42 +02:00
# include <variant>
2020-11-10 15:26:38 +01:00
# include <vector>
2021-09-08 15:18:24 +02:00
namespace hex : : pl {
2020-11-10 15:26:38 +01:00
2021-10-31 15:06:48 +01:00
class ASTNode ;
class ASTNodeAttribute ;
2021-09-21 21:29:18 +02:00
class PatternData ;
2021-10-31 15:06:48 +01:00
class Evaluator ;
class Attributable {
protected :
Attributable ( ) = default ;
Attributable ( const Attributable & ) = default ;
public :
void addAttribute ( ASTNodeAttribute * attribute ) {
this - > m_attributes . push_back ( attribute ) ;
}
[[nodiscard]] const auto & getAttributes ( ) const {
return this - > m_attributes ;
}
private :
std : : vector < ASTNodeAttribute * > m_attributes ;
} ;
class Clonable {
public :
[[nodiscard]]
virtual ASTNode * clone ( ) const = 0 ;
} ;
class ASTNode : public Clonable {
public :
constexpr ASTNode ( ) = default ;
constexpr virtual ~ ASTNode ( ) = default ;
constexpr ASTNode ( const ASTNode & ) = default ;
[[nodiscard]] constexpr u32 getLineNumber ( ) const { return this - > m_lineNumber ; }
[[maybe_unused]] constexpr void setLineNumber ( u32 lineNumber ) { this - > m_lineNumber = lineNumber ; }
[[nodiscard]] virtual ASTNode * evaluate ( Evaluator * evaluator ) const { return this - > clone ( ) ; }
[[nodiscard]] virtual std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const { return { } ; }
using FunctionResult = std : : pair < bool , std : : optional < Token : : Literal > > ;
2021-11-27 12:57:59 +01:00
virtual FunctionResult execute ( Evaluator * evaluator ) const { throw std : : pair < u32 , std : : string > ( this - > getLineNumber ( ) , " cannot execute non-function statement " ) ; }
2021-10-31 15:06:48 +01:00
private :
u32 m_lineNumber = 1 ;
} ;
2021-01-21 17:49:30 +01:00
2021-09-21 21:29:18 +02:00
class ASTNodeAttribute : public ASTNode {
2021-01-21 17:49:30 +01:00
public :
2021-09-21 21:29:18 +02:00
explicit ASTNodeAttribute ( std : : string attribute , std : : optional < std : : string > value = std : : nullopt )
: ASTNode ( ) , m_attribute ( std : : move ( attribute ) ) , m_value ( std : : move ( value ) ) { }
2021-01-21 17:49:30 +01:00
2021-09-21 21:29:18 +02:00
~ ASTNodeAttribute ( ) override = default ;
2021-01-21 17:49:30 +01:00
2021-09-21 21:29:18 +02:00
ASTNodeAttribute ( const ASTNodeAttribute & other ) : ASTNode ( other ) {
this - > m_attribute = other . m_attribute ;
this - > m_value = other . m_value ;
2021-01-21 17:49:30 +01:00
}
2021-09-21 21:29:18 +02:00
[[nodiscard]] ASTNode * clone ( ) const override {
return new ASTNodeAttribute ( * this ) ;
}
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
2021-09-21 21:29:18 +02:00
[[nodiscard]] const std : : string & getAttribute ( ) const {
return this - > m_attribute ;
}
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
2021-09-21 21:29:18 +02:00
[[nodiscard]] const std : : optional < std : : string > & getValue ( ) const {
return this - > m_value ;
}
2020-11-10 15:26:38 +01:00
private :
2021-09-21 21:29:18 +02:00
std : : string m_attribute ;
std : : optional < std : : string > m_value ;
2020-11-10 15:26:38 +01:00
} ;
2021-09-21 21:29:18 +02:00
class ASTNodeLiteral : public ASTNode {
2020-11-10 15:26:38 +01:00
public :
2021-09-21 21:29:18 +02:00
explicit ASTNodeLiteral ( Token : : Literal literal ) : ASTNode ( ) , m_literal ( literal ) { }
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
2021-09-21 21:29:18 +02:00
ASTNodeLiteral ( const ASTNodeLiteral & ) = default ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
2021-09-21 21:29:18 +02:00
return new ASTNodeLiteral ( * this ) ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
}
[[nodiscard]] const auto & getValue ( ) const {
2021-06-20 21:22:31 +02:00
return this - > m_literal ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
}
2020-11-10 15:26:38 +01:00
private :
2021-09-21 21:29:18 +02:00
Token : : Literal m_literal ;
2020-11-10 15:26:38 +01:00
} ;
2021-09-21 21:29:18 +02:00
class ASTNodeMathematicalExpression : public ASTNode {
# define FLOAT_BIT_OPERATION(name) \
auto name ( hex : : floating_point auto left , auto right ) const { LogConsole : : abortEvaluation ( " invalid floating point operation " , this ) ; return 0 ; } \
auto name ( auto left , hex : : floating_point auto right ) const { LogConsole : : abortEvaluation ( " invalid floating point operation " , this ) ; return 0 ; } \
auto name ( hex : : floating_point auto left , hex : : floating_point auto right ) const { LogConsole : : abortEvaluation ( " invalid floating point operation " , this ) ; return 0 ; } \
auto name ( hex : : integral auto left , hex : : integral auto right ) const
FLOAT_BIT_OPERATION ( shiftLeft ) {
return left < < right ;
}
FLOAT_BIT_OPERATION ( shiftRight ) {
return left > > right ;
}
FLOAT_BIT_OPERATION ( bitAnd ) {
return left & right ;
}
FLOAT_BIT_OPERATION ( bitOr ) {
return left | right ;
}
FLOAT_BIT_OPERATION ( bitXor ) {
return left ^ right ;
}
FLOAT_BIT_OPERATION ( bitNot ) {
return ~ right ;
}
FLOAT_BIT_OPERATION ( modulus ) {
return left % right ;
}
# undef FLOAT_BIT_OPERATION
2020-11-10 15:26:38 +01:00
public :
2021-09-21 21:29:18 +02:00
ASTNodeMathematicalExpression ( ASTNode * left , ASTNode * right , Token : : Operator op )
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
: ASTNode ( ) , m_left ( left ) , m_right ( right ) , m_operator ( op ) { }
2021-09-21 21:29:18 +02:00
~ ASTNodeMathematicalExpression ( ) override {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
delete this - > m_left ;
delete this - > m_right ;
}
2021-09-21 21:29:18 +02:00
ASTNodeMathematicalExpression ( const ASTNodeMathematicalExpression & other ) : ASTNode ( other ) {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
this - > m_operator = other . m_operator ;
this - > m_left = other . m_left - > clone ( ) ;
this - > m_right = other . m_right - > clone ( ) ;
}
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
2021-09-21 21:29:18 +02:00
return new ASTNodeMathematicalExpression ( * this ) ;
}
[[nodiscard]] ASTNode * evaluate ( Evaluator * evaluator ) const override {
if ( this - > getLeftOperand ( ) = = nullptr | | this - > getRightOperand ( ) = = nullptr )
LogConsole : : abortEvaluation ( " attempted to use void expression in mathematical expression " , this ) ;
auto * left = dynamic_cast < ASTNodeLiteral * > ( this - > getLeftOperand ( ) - > evaluate ( evaluator ) ) ;
auto * right = dynamic_cast < ASTNodeLiteral * > ( this - > getRightOperand ( ) - > evaluate ( evaluator ) ) ;
ON_SCOPE_EXIT { delete left ; delete right ; } ;
return std : : visit ( overloaded {
// TODO: :notlikethis:
[ this ] ( u128 left , PatternData * const & right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( s128 left , PatternData * const & right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( double left , PatternData * const & right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( char left , PatternData * const & right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( bool left , PatternData * const & right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( std : : string left , PatternData * const & right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( PatternData * const & left , u128 right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( PatternData * const & left , s128 right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( PatternData * const & left , double right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( PatternData * const & left , char right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( PatternData * const & left , bool right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( PatternData * const & left , std : : string right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( PatternData * const & left , PatternData * right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( auto & & left , std : : string right ) - > ASTNode * { LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ; } ,
[ this ] ( std : : string left , auto & & right ) - > ASTNode * {
switch ( this - > getOperator ( ) ) {
case Token : : Operator : : Star : {
std : : string result ;
for ( auto i = 0 ; i < right ; i + + )
result + = left ;
return new ASTNodeLiteral ( result ) ;
}
default :
LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ;
}
} ,
[ this ] ( std : : string left , std : : string right ) - > ASTNode * {
switch ( this - > getOperator ( ) ) {
case Token : : Operator : : Plus :
return new ASTNodeLiteral ( left + right ) ;
case Token : : Operator : : BoolEquals :
return new ASTNodeLiteral ( left = = right ) ;
case Token : : Operator : : BoolNotEquals :
return new ASTNodeLiteral ( left ! = right ) ;
case Token : : Operator : : BoolGreaterThan :
return new ASTNodeLiteral ( left > right ) ;
case Token : : Operator : : BoolLessThan :
return new ASTNodeLiteral ( left < right ) ;
case Token : : Operator : : BoolGreaterThanOrEquals :
return new ASTNodeLiteral ( left > = right ) ;
case Token : : Operator : : BoolLessThanOrEquals :
return new ASTNodeLiteral ( left < = right ) ;
default :
LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ;
}
} ,
2021-10-04 20:26:34 +02:00
[ this ] ( std : : string left , char right ) - > ASTNode * {
switch ( this - > getOperator ( ) ) {
case Token : : Operator : : Plus :
return new ASTNodeLiteral ( left + right ) ;
default :
LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ;
}
} ,
[ this ] ( char left , std : : string right ) - > ASTNode * {
switch ( this - > getOperator ( ) ) {
case Token : : Operator : : Plus :
return new ASTNodeLiteral ( left + right ) ;
default :
LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ;
}
} ,
2021-09-21 21:29:18 +02:00
[ this ] ( auto & & left , auto & & right ) - > ASTNode * {
switch ( this - > getOperator ( ) ) {
case Token : : Operator : : Plus :
return new ASTNodeLiteral ( left + right ) ;
case Token : : Operator : : Minus :
return new ASTNodeLiteral ( left - right ) ;
case Token : : Operator : : Star :
return new ASTNodeLiteral ( left * right ) ;
case Token : : Operator : : Slash :
if ( right = = 0 ) LogConsole : : abortEvaluation ( " division by zero! " , this ) ;
return new ASTNodeLiteral ( left / right ) ;
case Token : : Operator : : Percent :
if ( right = = 0 ) LogConsole : : abortEvaluation ( " division by zero! " , this ) ;
return new ASTNodeLiteral ( modulus ( left , right ) ) ;
case Token : : Operator : : ShiftLeft :
return new ASTNodeLiteral ( shiftLeft ( left , right ) ) ;
case Token : : Operator : : ShiftRight :
return new ASTNodeLiteral ( shiftRight ( left , right ) ) ;
case Token : : Operator : : BitAnd :
return new ASTNodeLiteral ( bitAnd ( left , right ) ) ;
case Token : : Operator : : BitXor :
return new ASTNodeLiteral ( bitXor ( left , right ) ) ;
case Token : : Operator : : BitOr :
return new ASTNodeLiteral ( bitOr ( left , right ) ) ;
case Token : : Operator : : BitNot :
return new ASTNodeLiteral ( bitNot ( left , right ) ) ;
case Token : : Operator : : BoolEquals :
2021-09-24 12:15:50 +02:00
return new ASTNodeLiteral ( bool ( left = = right ) ) ;
2021-09-21 21:29:18 +02:00
case Token : : Operator : : BoolNotEquals :
2021-09-24 12:15:50 +02:00
return new ASTNodeLiteral ( bool ( left ! = right ) ) ;
2021-09-21 21:29:18 +02:00
case Token : : Operator : : BoolGreaterThan :
2021-09-24 12:15:50 +02:00
return new ASTNodeLiteral ( bool ( left > right ) ) ;
2021-09-21 21:29:18 +02:00
case Token : : Operator : : BoolLessThan :
2021-09-24 12:15:50 +02:00
return new ASTNodeLiteral ( bool ( left < right ) ) ;
2021-09-21 21:29:18 +02:00
case Token : : Operator : : BoolGreaterThanOrEquals :
2021-09-24 12:15:50 +02:00
return new ASTNodeLiteral ( bool ( left > = right ) ) ;
2021-09-21 21:29:18 +02:00
case Token : : Operator : : BoolLessThanOrEquals :
2021-09-24 12:15:50 +02:00
return new ASTNodeLiteral ( bool ( left < = right ) ) ;
2021-09-21 21:29:18 +02:00
case Token : : Operator : : BoolAnd :
2021-09-24 12:15:50 +02:00
return new ASTNodeLiteral ( bool ( left & & right ) ) ;
2021-09-21 21:29:18 +02:00
case Token : : Operator : : BoolXor :
2021-09-24 12:15:50 +02:00
return new ASTNodeLiteral ( bool ( left & & ! right | | ! left & & right ) ) ;
2021-09-21 21:29:18 +02:00
case Token : : Operator : : BoolOr :
2021-09-24 12:15:50 +02:00
return new ASTNodeLiteral ( bool ( left | | right ) ) ;
2021-09-21 21:29:18 +02:00
case Token : : Operator : : BoolNot :
2021-09-24 12:15:50 +02:00
return new ASTNodeLiteral ( bool ( ! right ) ) ;
2021-09-21 21:29:18 +02:00
default :
LogConsole : : abortEvaluation ( " invalid operand used in mathematical expression " , this ) ;
}
}
} , left - > getValue ( ) , right - > getValue ( ) ) ;
}
[[nodiscard]] ASTNode * getLeftOperand ( ) const { return this - > m_left ; }
[[nodiscard]] ASTNode * getRightOperand ( ) const { return this - > m_right ; }
[[nodiscard]] Token : : Operator getOperator ( ) const { return this - > m_operator ; }
2020-11-10 15:26:38 +01:00
private :
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
ASTNode * m_left , * m_right ;
Token : : Operator m_operator ;
2020-11-10 15:26:38 +01:00
} ;
2021-01-07 01:19:54 +01:00
class ASTNodeTernaryExpression : public ASTNode {
public :
ASTNodeTernaryExpression ( ASTNode * first , ASTNode * second , ASTNode * third , Token : : Operator op )
: ASTNode ( ) , m_first ( first ) , m_second ( second ) , m_third ( third ) , m_operator ( op ) { }
~ ASTNodeTernaryExpression ( ) override {
delete this - > m_first ;
delete this - > m_second ;
delete this - > m_third ;
}
ASTNodeTernaryExpression ( const ASTNodeTernaryExpression & other ) : ASTNode ( other ) {
this - > m_operator = other . m_operator ;
this - > m_first = other . m_first - > clone ( ) ;
this - > m_second = other . m_second - > clone ( ) ;
this - > m_third = other . m_third - > clone ( ) ;
}
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
2021-01-07 01:19:54 +01:00
return new ASTNodeTernaryExpression ( * this ) ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]] ASTNode * evaluate ( Evaluator * evaluator ) const override {
if ( this - > getFirstOperand ( ) = = nullptr | | this - > getSecondOperand ( ) = = nullptr | | this - > getThirdOperand ( ) = = nullptr )
LogConsole : : abortEvaluation ( " attempted to use void expression in mathematical expression " , this ) ;
auto * first = dynamic_cast < ASTNodeLiteral * > ( this - > getFirstOperand ( ) - > evaluate ( evaluator ) ) ;
auto * second = dynamic_cast < ASTNodeLiteral * > ( this - > getSecondOperand ( ) - > evaluate ( evaluator ) ) ;
auto * third = dynamic_cast < ASTNodeLiteral * > ( this - > getThirdOperand ( ) - > evaluate ( evaluator ) ) ;
ON_SCOPE_EXIT { delete first ; delete second ; delete third ; } ;
auto condition = std : : visit ( overloaded {
[ this ] ( std : : string value ) - > bool { return ! value . empty ( ) ; } ,
[ this ] ( PatternData * const & ) - > bool { LogConsole : : abortEvaluation ( " cannot cast custom type to bool " , this ) ; } ,
[ ] ( auto & & value ) - > bool { return bool ( value ) ; }
} , first - > getValue ( ) ) ;
return std : : visit ( overloaded {
[ condition ] < typename T > ( const T & second , const T & third ) - > ASTNode * { return new ASTNodeLiteral ( condition ? second : third ) ; } ,
[ this ] ( auto & & second , auto & & third ) - > ASTNode * { LogConsole : : abortEvaluation ( " operands to ternary expression have different types " , this ) ; }
} , second - > getValue ( ) , third - > getValue ( ) ) ;
}
[[nodiscard]] ASTNode * getFirstOperand ( ) const { return this - > m_first ; }
[[nodiscard]] ASTNode * getSecondOperand ( ) const { return this - > m_second ; }
[[nodiscard]] ASTNode * getThirdOperand ( ) const { return this - > m_third ; }
[[nodiscard]] Token : : Operator getOperator ( ) const { return this - > m_operator ; }
2021-01-07 01:19:54 +01:00
private :
ASTNode * m_first , * m_second , * m_third ;
Token : : Operator m_operator ;
} ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
class ASTNodeBuiltinType : public ASTNode {
public :
constexpr explicit ASTNodeBuiltinType ( Token : : ValueType type )
: ASTNode ( ) , m_type ( type ) { }
[[nodiscard]] constexpr const auto & getType ( ) const { return this - > m_type ; }
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
return new ASTNodeBuiltinType ( * this ) ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
auto offset = evaluator - > dataOffset ( ) ;
auto size = Token : : getTypeSize ( this - > m_type ) ;
evaluator - > dataOffset ( ) + = size ;
PatternData * pattern ;
if ( Token : : isUnsigned ( this - > m_type ) )
2021-10-02 15:22:38 +02:00
pattern = new PatternDataUnsigned ( offset , size , evaluator ) ;
2021-09-21 21:29:18 +02:00
else if ( Token : : isSigned ( this - > m_type ) )
2021-10-02 15:22:38 +02:00
pattern = new PatternDataSigned ( offset , size , evaluator ) ;
2021-09-21 21:29:18 +02:00
else if ( Token : : isFloatingPoint ( this - > m_type ) )
2021-10-02 15:22:38 +02:00
pattern = new PatternDataFloat ( offset , size , evaluator ) ;
2021-09-21 21:29:18 +02:00
else if ( this - > m_type = = Token : : ValueType : : Boolean )
2021-10-02 15:22:38 +02:00
pattern = new PatternDataBoolean ( offset , evaluator ) ;
2021-09-21 21:29:18 +02:00
else if ( this - > m_type = = Token : : ValueType : : Character )
2021-10-02 15:22:38 +02:00
pattern = new PatternDataCharacter ( offset , evaluator ) ;
2021-09-21 21:29:18 +02:00
else if ( this - > m_type = = Token : : ValueType : : Character16 )
2021-10-02 15:22:38 +02:00
pattern = new PatternDataCharacter16 ( offset , evaluator ) ;
2021-09-21 21:29:18 +02:00
else if ( this - > m_type = = Token : : ValueType : : Padding )
2021-10-02 15:22:38 +02:00
pattern = new PatternDataPadding ( offset , 1 , evaluator ) ;
2021-09-21 21:29:18 +02:00
else if ( this - > m_type = = Token : : ValueType : : String )
2021-10-02 15:22:38 +02:00
pattern = new PatternDataString ( offset , 1 , evaluator ) ;
2021-09-23 23:43:16 +02:00
else if ( this - > m_type = = Token : : ValueType : : Auto )
return { nullptr } ;
2021-09-21 21:29:18 +02:00
else
LogConsole : : abortEvaluation ( " invalid built-in type " , this ) ;
pattern - > setTypeName ( Token : : getTypeName ( this - > m_type ) ) ;
return { pattern } ;
}
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
private :
const Token : : ValueType m_type ;
} ;
2021-01-21 17:49:30 +01:00
class ASTNodeTypeDecl : public ASTNode , public Attributable {
2020-11-10 15:26:38 +01:00
public :
2021-09-08 15:18:24 +02:00
ASTNodeTypeDecl ( std : : string name , ASTNode * type , std : : optional < std : : endian > endian = std : : nullopt )
: ASTNode ( ) , m_name ( std : : move ( name ) ) , m_type ( type ) , m_endian ( endian ) { }
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
2021-01-21 17:49:30 +01:00
ASTNodeTypeDecl ( const ASTNodeTypeDecl & other ) : ASTNode ( other ) , Attributable ( other ) {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
this - > m_name = other . m_name ;
2021-09-25 22:03:55 +02:00
this - > m_type = other . m_type ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
this - > m_endian = other . m_endian ;
}
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
return new ASTNodeTypeDecl ( * this ) ;
}
2021-08-25 17:07:01 +02:00
void setName ( const std : : string & name ) { this - > m_name = name ; }
2021-09-08 15:18:24 +02:00
[[nodiscard]] const std : : string & getName ( ) const { return this - > m_name ; }
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
[[nodiscard]] ASTNode * getType ( ) { return this - > m_type ; }
[[nodiscard]] std : : optional < std : : endian > getEndian ( ) const { return this - > m_endian ; }
2020-11-10 15:26:38 +01:00
2021-09-21 21:29:18 +02:00
[[nodiscard]] ASTNode * evaluate ( Evaluator * evaluator ) const override {
return this - > m_type - > evaluate ( evaluator ) ;
}
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
auto patterns = this - > m_type - > createPatterns ( evaluator ) ;
for ( auto & pattern : patterns ) {
2021-09-23 23:43:16 +02:00
if ( pattern = = nullptr )
continue ;
2021-09-21 21:29:18 +02:00
if ( ! this - > m_name . empty ( ) )
pattern - > setTypeName ( this - > m_name ) ;
pattern - > setEndian ( this - > m_endian . value_or ( evaluator - > getDefaultEndian ( ) ) ) ;
}
return patterns ;
}
2020-11-10 15:26:38 +01:00
private :
std : : string m_name ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
ASTNode * m_type ;
std : : optional < std : : endian > m_endian ;
2020-11-10 15:26:38 +01:00
} ;
2021-09-21 21:29:18 +02:00
class ASTNodeCast : public ASTNode {
public :
ASTNodeCast ( ASTNode * value , ASTNode * type ) : m_value ( value ) , m_type ( type ) { }
ASTNodeCast ( const ASTNodeCast & other ) {
this - > m_value = other . m_value - > clone ( ) ;
this - > m_type = other . m_type - > clone ( ) ;
}
~ ASTNodeCast ( ) override {
delete this - > m_value ;
delete this - > m_type ;
}
[[nodiscard]] ASTNode * clone ( ) const override {
return new ASTNodeCast ( * this ) ;
}
[[nodiscard]] ASTNode * evaluate ( Evaluator * evaluator ) const override {
auto literal = dynamic_cast < ASTNodeLiteral * > ( this - > m_value - > evaluate ( evaluator ) ) ;
auto type = dynamic_cast < ASTNodeBuiltinType * > ( this - > m_type - > evaluate ( evaluator ) ) - > getType ( ) ;
2021-12-03 16:06:40 +01:00
auto startOffset = evaluator - > dataOffset ( ) ;
2021-09-21 21:29:18 +02:00
auto typePattern = this - > m_type - > createPatterns ( evaluator ) . front ( ) ;
2021-12-03 16:06:40 +01:00
ON_SCOPE_EXIT {
evaluator - > dataOffset ( ) = startOffset ;
delete typePattern ;
} ;
2021-09-21 21:29:18 +02:00
return std : : visit ( overloaded {
[ & , this ] ( PatternData * value ) - > ASTNode * { LogConsole : : abortEvaluation ( hex : : format ( " cannot cast custom type '{}' to '{}' " , value - > getTypeName ( ) , Token : : getTypeName ( type ) ) , this ) ; } ,
[ & , this ] ( const std : : string & ) - > ASTNode * { LogConsole : : abortEvaluation ( hex : : format ( " cannot cast string to '{}' " , Token : : getTypeName ( type ) ) , this ) ; } ,
[ & , this ] ( auto & & value ) - > ASTNode * {
auto endianAdjustedValue = hex : : changeEndianess ( value , typePattern - > getSize ( ) , typePattern - > getEndian ( ) ) ;
switch ( type ) {
case Token : : ValueType : : Unsigned8Bit :
return new ASTNodeLiteral ( u128 ( u8 ( endianAdjustedValue ) ) ) ;
case Token : : ValueType : : Unsigned16Bit :
return new ASTNodeLiteral ( u128 ( u16 ( endianAdjustedValue ) ) ) ;
case Token : : ValueType : : Unsigned32Bit :
return new ASTNodeLiteral ( u128 ( u32 ( endianAdjustedValue ) ) ) ;
case Token : : ValueType : : Unsigned64Bit :
return new ASTNodeLiteral ( u128 ( u64 ( endianAdjustedValue ) ) ) ;
case Token : : ValueType : : Unsigned128Bit :
return new ASTNodeLiteral ( u128 ( endianAdjustedValue ) ) ;
case Token : : ValueType : : Signed8Bit :
return new ASTNodeLiteral ( s128 ( s8 ( endianAdjustedValue ) ) ) ;
case Token : : ValueType : : Signed16Bit :
return new ASTNodeLiteral ( s128 ( s16 ( endianAdjustedValue ) ) ) ;
case Token : : ValueType : : Signed32Bit :
return new ASTNodeLiteral ( s128 ( s32 ( endianAdjustedValue ) ) ) ;
case Token : : ValueType : : Signed64Bit :
return new ASTNodeLiteral ( s128 ( s64 ( endianAdjustedValue ) ) ) ;
case Token : : ValueType : : Signed128Bit :
return new ASTNodeLiteral ( s128 ( endianAdjustedValue ) ) ;
case Token : : ValueType : : Float :
return new ASTNodeLiteral ( double ( float ( endianAdjustedValue ) ) ) ;
case Token : : ValueType : : Double :
return new ASTNodeLiteral ( double ( endianAdjustedValue ) ) ;
case Token : : ValueType : : Character :
return new ASTNodeLiteral ( char ( endianAdjustedValue ) ) ;
case Token : : ValueType : : Character16 :
return new ASTNodeLiteral ( u128 ( char16_t ( endianAdjustedValue ) ) ) ;
case Token : : ValueType : : Boolean :
return new ASTNodeLiteral ( bool ( endianAdjustedValue ) ) ;
2021-09-21 23:45:45 +02:00
case Token : : ValueType : : String :
{
std : : string string ( sizeof ( value ) , ' \x00 ' ) ;
std : : memcpy ( string . data ( ) , & value , string . size ( ) ) ;
hex : : trim ( string ) ;
if ( typePattern - > getEndian ( ) ! = std : : endian : : native )
std : : reverse ( string . begin ( ) , string . end ( ) ) ;
return new ASTNodeLiteral ( string ) ;
}
2021-09-21 21:29:18 +02:00
default :
LogConsole : : abortEvaluation ( hex : : format ( " cannot cast value to '{}' " , Token : : getTypeName ( type ) ) , this ) ;
}
} ,
} , literal - > getValue ( ) ) ;
}
private :
ASTNode * m_value ;
ASTNode * m_type ;
} ;
class ASTNodeWhileStatement : public ASTNode {
public :
explicit ASTNodeWhileStatement ( ASTNode * condition , std : : vector < ASTNode * > body )
: ASTNode ( ) , m_condition ( condition ) , m_body ( std : : move ( body ) ) { }
~ ASTNodeWhileStatement ( ) override {
delete this - > m_condition ;
for ( auto & statement : this - > m_body )
delete statement ;
}
ASTNodeWhileStatement ( const ASTNodeWhileStatement & other ) : ASTNode ( other ) {
this - > m_condition = other . m_condition - > clone ( ) ;
2021-09-26 18:27:18 +02:00
for ( auto & statement : other . m_body )
this - > m_body . push_back ( statement - > clone ( ) ) ;
2021-09-21 21:29:18 +02:00
}
[[nodiscard]] ASTNode * clone ( ) const override {
return new ASTNodeWhileStatement ( * this ) ;
}
[[nodiscard]] ASTNode * getCondition ( ) {
return this - > m_condition ;
}
[[nodiscard]] const std : : vector < ASTNode * > & getBody ( ) {
return this - > m_body ;
}
2021-11-27 12:57:59 +01:00
FunctionResult execute ( Evaluator * evaluator ) const override {
2021-09-21 21:29:18 +02:00
2021-10-07 11:34:46 +02:00
u64 loopIterations = 0 ;
2021-09-21 21:29:18 +02:00
while ( evaluateCondition ( evaluator ) ) {
2021-10-07 11:34:46 +02:00
evaluator - > handleAbort ( ) ;
2021-09-21 21:29:18 +02:00
auto variables = * evaluator - > getScope ( 0 ) . scope ;
u32 startVariableCount = variables . size ( ) ;
ON_SCOPE_EXIT {
s64 stackSize = evaluator - > getStack ( ) . size ( ) ;
for ( u32 i = startVariableCount ; i < variables . size ( ) ; i + + ) {
stackSize - - ;
delete variables [ i ] ;
}
if ( stackSize < 0 ) LogConsole : : abortEvaluation ( " stack pointer underflow! " , this ) ;
evaluator - > getStack ( ) . resize ( stackSize ) ;
} ;
evaluator - > pushScope ( nullptr , variables ) ;
ON_SCOPE_EXIT { evaluator - > popScope ( ) ; } ;
for ( auto & statement : this - > m_body ) {
auto [ executionStopped , result ] = statement - > execute ( evaluator ) ;
if ( executionStopped ) {
return { true , result } ;
}
}
2021-10-07 11:34:46 +02:00
loopIterations + + ;
if ( loopIterations > = evaluator - > getLoopLimit ( ) )
LogConsole : : abortEvaluation ( hex : : format ( " loop iterations exceeded limit of {} " , evaluator - > getLoopLimit ( ) ) , this ) ;
evaluator - > handleAbort ( ) ;
2021-09-21 21:29:18 +02:00
}
return { false , { } } ;
}
[[nodiscard]]
bool evaluateCondition ( Evaluator * evaluator ) const {
auto literal = dynamic_cast < ASTNodeLiteral * > ( this - > m_condition - > evaluate ( evaluator ) ) ;
ON_SCOPE_EXIT { delete literal ; } ;
return std : : visit ( overloaded {
[ ] ( std : : string value ) - > bool { return ! value . empty ( ) ; } ,
[ this ] ( PatternData * const & ) - > bool { LogConsole : : abortEvaluation ( " cannot cast custom type to bool " , this ) ; } ,
[ ] ( auto & & value ) - > bool { return value ! = 0 ; }
} , literal - > getValue ( ) ) ;
}
private :
ASTNode * m_condition ;
std : : vector < ASTNode * > m_body ;
} ;
inline void applyVariableAttributes ( Evaluator * evaluator , const Attributable * attributable , PatternData * pattern ) {
2021-10-05 21:55:30 +02:00
auto endOffset = evaluator - > dataOffset ( ) ;
evaluator - > dataOffset ( ) = pattern - > getOffset ( ) ;
ON_SCOPE_EXIT { evaluator - > dataOffset ( ) = endOffset ; } ;
2021-09-21 21:29:18 +02:00
for ( ASTNodeAttribute * attribute : attributable - > getAttributes ( ) ) {
auto & name = attribute - > getAttribute ( ) ;
auto value = attribute - > getValue ( ) ;
auto node = reinterpret_cast < const ASTNode * > ( attributable ) ;
auto requiresValue = [ & ] ( ) {
if ( ! value . has_value ( ) )
LogConsole : : abortEvaluation ( hex : : format ( " used attribute '{}' without providing a value " , name ) , node ) ;
return true ;
} ;
auto noValue = [ & ] ( ) {
if ( value . has_value ( ) )
LogConsole : : abortEvaluation ( hex : : format ( " provided a value to attribute '{}' which doesn't take one " , name ) , node ) ;
return true ;
} ;
if ( name = = " color " & & requiresValue ( ) ) {
u32 color = strtoul ( value - > c_str ( ) , nullptr , 16 ) ;
2021-10-09 23:38:00 +02:00
pattern - > setColor ( hex : : changeEndianess ( color , std : : endian : : big ) > > 8 ) ;
2021-09-21 21:29:18 +02:00
} else if ( name = = " name " & & requiresValue ( ) ) {
2021-10-18 09:57:26 +02:00
pattern - > setDisplayName ( * value ) ;
2021-09-21 21:29:18 +02:00
} else if ( name = = " comment " & & requiresValue ( ) ) {
pattern - > setComment ( * value ) ;
} else if ( name = = " hidden " & & noValue ( ) ) {
pattern - > setHidden ( true ) ;
2021-09-27 13:31:10 +02:00
} else if ( name = = " inline " & & noValue ( ) ) {
auto inlinable = dynamic_cast < Inlinable * > ( pattern ) ;
if ( inlinable = = nullptr )
LogConsole : : abortEvaluation ( " inline attribute can only be applied to nested types " , node ) ;
else
inlinable - > setInlined ( true ) ;
2021-09-21 21:29:18 +02:00
} else if ( name = = " format " & & requiresValue ( ) ) {
auto functions = evaluator - > getCustomFunctions ( ) ;
if ( ! functions . contains ( * value ) )
LogConsole : : abortEvaluation ( hex : : format ( " cannot find formatter function '{}' " , * value ) , node ) ;
const auto & function = functions [ * value ] ;
if ( function . parameterCount ! = 1 )
LogConsole : : abortEvaluation ( " formatter function needs exactly one parameter " , node ) ;
2021-09-27 18:32:48 +02:00
pattern - > setFormatterFunction ( function ) ;
} else if ( name = = " transform " & & requiresValue ( ) ) {
auto functions = evaluator - > getCustomFunctions ( ) ;
if ( ! functions . contains ( * value ) )
LogConsole : : abortEvaluation ( hex : : format ( " cannot find transform function '{}' " , * value ) , node ) ;
const auto & function = functions [ * value ] ;
if ( function . parameterCount ! = 1 )
LogConsole : : abortEvaluation ( " transform function needs exactly one parameter " , node ) ;
pattern - > setTransformFunction ( function ) ;
} else if ( name = = " pointer_base " & & requiresValue ( ) ) {
auto functions = evaluator - > getCustomFunctions ( ) ;
if ( ! functions . contains ( * value ) )
LogConsole : : abortEvaluation ( hex : : format ( " cannot find pointer base function '{}' " , * value ) , node ) ;
const auto & function = functions [ * value ] ;
if ( function . parameterCount ! = 1 )
LogConsole : : abortEvaluation ( " pointer base function needs exactly one parameter " , node ) ;
if ( auto pointerPattern = dynamic_cast < PatternDataPointer * > ( pattern ) ) {
u128 value = 0 ;
evaluator - > getProvider ( ) - > read ( pattern - > getOffset ( ) , & value , pattern - > getSize ( ) ) ;
2021-10-31 15:20:19 +01:00
value = hex : : changeEndianess ( value , pattern - > getSize ( ) , pattern - > getEndian ( ) ) ;
2021-09-27 18:32:48 +02:00
auto result = function . func ( evaluator , { value } ) ;
if ( ! result . has_value ( ) )
LogConsole : : abortEvaluation ( " pointer base function did not return a value " , node ) ;
pointerPattern - > rebase ( Token : : literalToUnsigned ( result . value ( ) ) ) ;
} else {
LogConsole : : abortEvaluation ( " pointer_base attribute may only be applied to a pointer " ) ;
}
2021-09-21 21:29:18 +02:00
}
}
}
2021-01-21 17:49:30 +01:00
class ASTNodeVariableDecl : public ASTNode , public Attributable {
2020-11-20 21:29:28 +01:00
public :
2021-12-18 22:56:36 +01:00
ASTNodeVariableDecl ( std : : string name , ASTNode * type , ASTNode * placementOffset = nullptr , bool inVariable = false , bool outVariable = false )
: ASTNode ( ) , m_name ( std : : move ( name ) ) , m_type ( type ) , m_placementOffset ( placementOffset ) , m_inVariable ( inVariable ) , m_outVariable ( outVariable ) { }
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
2021-01-21 17:49:30 +01:00
ASTNodeVariableDecl ( const ASTNodeVariableDecl & other ) : ASTNode ( other ) , Attributable ( other ) {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
this - > m_name = other . m_name ;
this - > m_type = other . m_type - > clone ( ) ;
if ( other . m_placementOffset ! = nullptr )
this - > m_placementOffset = other . m_placementOffset - > clone ( ) ;
else
this - > m_placementOffset = nullptr ;
}
~ ASTNodeVariableDecl ( ) override {
delete this - > m_type ;
2021-02-19 10:51:30 +01:00
delete this - > m_placementOffset ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
}
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
return new ASTNodeVariableDecl ( * this ) ;
}
2021-09-08 15:18:24 +02:00
[[nodiscard]] const std : : string & getName ( ) const { return this - > m_name ; }
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
[[nodiscard]] constexpr ASTNode * getType ( ) const { return this - > m_type ; }
[[nodiscard]] constexpr auto getPlacementOffset ( ) const { return this - > m_placementOffset ; }
2020-11-20 21:29:28 +01:00
2021-12-18 22:56:36 +01:00
[[nodiscard]] constexpr bool isInVariable ( ) const { return this - > m_inVariable ; }
[[nodiscard]] constexpr bool isOutVariable ( ) const { return this - > m_outVariable ; }
2021-09-21 21:29:18 +02:00
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
if ( this - > m_placementOffset ! = nullptr ) {
auto offset = dynamic_cast < ASTNodeLiteral * > ( this - > m_placementOffset - > evaluate ( evaluator ) ) ;
ON_SCOPE_EXIT { delete offset ; } ;
evaluator - > dataOffset ( ) = std : : visit ( overloaded {
[ this ] ( std : : string ) - > u64 { LogConsole : : abortEvaluation ( " placement offset cannot be a string " , this ) ; } ,
[ this ] ( PatternData * const & ) - > u64 { LogConsole : : abortEvaluation ( " placement offset cannot be a custom type " , this ) ; } ,
[ ] ( auto & & offset ) - > u64 { return offset ; }
} , offset - > getValue ( ) ) ;
}
auto pattern = this - > m_type - > createPatterns ( evaluator ) . front ( ) ;
pattern - > setVariableName ( this - > m_name ) ;
applyVariableAttributes ( evaluator , this , pattern ) ;
return { pattern } ;
}
2021-11-27 12:57:59 +01:00
FunctionResult execute ( Evaluator * evaluator ) const override {
2021-09-21 21:29:18 +02:00
evaluator - > createVariable ( this - > getName ( ) , this - > getType ( ) ) ;
return { false , { } } ;
}
2020-11-20 21:29:28 +01:00
private :
std : : string m_name ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
ASTNode * m_type ;
ASTNode * m_placementOffset ;
2021-12-18 22:56:36 +01:00
bool m_inVariable , m_outVariable ;
2020-11-20 21:29:28 +01:00
} ;
2021-01-21 17:49:30 +01:00
class ASTNodeArrayVariableDecl : public ASTNode , public Attributable {
2020-11-20 20:26:19 +01:00
public :
2021-09-08 15:18:24 +02:00
ASTNodeArrayVariableDecl ( std : : string name , ASTNode * type , ASTNode * size , ASTNode * placementOffset = nullptr )
: ASTNode ( ) , m_name ( std : : move ( name ) ) , m_type ( type ) , m_size ( size ) , m_placementOffset ( placementOffset ) { }
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
2021-01-21 17:49:30 +01:00
ASTNodeArrayVariableDecl ( const ASTNodeArrayVariableDecl & other ) : ASTNode ( other ) , Attributable ( other ) {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
this - > m_name = other . m_name ;
this - > m_type = other . m_type - > clone ( ) ;
2021-01-07 21:16:34 +01:00
if ( other . m_size ! = nullptr )
this - > m_size = other . m_size - > clone ( ) ;
else
this - > m_size = nullptr ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
if ( other . m_placementOffset ! = nullptr )
this - > m_placementOffset = other . m_placementOffset - > clone ( ) ;
else
this - > m_placementOffset = nullptr ;
}
~ ASTNodeArrayVariableDecl ( ) override {
delete this - > m_type ;
delete this - > m_size ;
2021-02-19 10:51:30 +01:00
delete this - > m_placementOffset ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
}
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
return new ASTNodeArrayVariableDecl ( * this ) ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
if ( this - > m_placementOffset ! = nullptr ) {
auto offset = dynamic_cast < ASTNodeLiteral * > ( this - > m_placementOffset - > evaluate ( evaluator ) ) ;
ON_SCOPE_EXIT { delete offset ; } ;
evaluator - > dataOffset ( ) = std : : visit ( overloaded {
[ this ] ( std : : string ) - > u64 { LogConsole : : abortEvaluation ( " placement offset cannot be a string " , this ) ; } ,
[ this ] ( PatternData * const & ) - > u64 { LogConsole : : abortEvaluation ( " placement offset cannot be a custom type " , this ) ; } ,
[ ] ( auto & & offset ) - > u64 { return offset ; }
} , offset - > getValue ( ) ) ;
}
auto type = this - > m_type - > evaluate ( evaluator ) ;
ON_SCOPE_EXIT { delete type ; } ;
PatternData * pattern ;
if ( dynamic_cast < ASTNodeBuiltinType * > ( type ) )
pattern = createStaticArray ( evaluator ) ;
else if ( auto attributable = dynamic_cast < Attributable * > ( type ) ) {
auto & attributes = attributable - > getAttributes ( ) ;
bool isStaticType = std : : any_of ( attributes . begin ( ) , attributes . end ( ) , [ ] ( ASTNodeAttribute * attribute ) {
return attribute - > getAttribute ( ) = = " static " & & ! attribute - > getValue ( ) . has_value ( ) ;
} ) ;
if ( isStaticType )
pattern = createStaticArray ( evaluator ) ;
else
pattern = createDynamicArray ( evaluator ) ;
} else {
LogConsole : : abortEvaluation ( " invalid type used in array " , this ) ;
}
applyVariableAttributes ( evaluator , this , pattern ) ;
return { pattern } ;
}
2021-09-08 15:18:24 +02:00
[[nodiscard]] const std : : string & getName ( ) const { return this - > m_name ; }
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
[[nodiscard]] constexpr ASTNode * getType ( ) const { return this - > m_type ; }
[[nodiscard]] constexpr ASTNode * getSize ( ) const { return this - > m_size ; }
[[nodiscard]] constexpr auto getPlacementOffset ( ) const { return this - > m_placementOffset ; }
2020-11-20 20:26:19 +01:00
private :
std : : string m_name ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
ASTNode * m_type ;
ASTNode * m_size ;
ASTNode * m_placementOffset ;
2021-09-21 21:29:18 +02:00
PatternData * createStaticArray ( Evaluator * evaluator ) const {
u64 startOffset = evaluator - > dataOffset ( ) ;
PatternData * templatePattern = this - > m_type - > createPatterns ( evaluator ) . front ( ) ;
ON_SCOPE_EXIT { delete templatePattern ; } ;
evaluator - > dataOffset ( ) = startOffset ;
u128 entryCount = 0 ;
if ( this - > m_size ! = nullptr ) {
auto sizeNode = this - > m_size - > evaluate ( evaluator ) ;
ON_SCOPE_EXIT { delete sizeNode ; } ;
if ( auto literal = dynamic_cast < ASTNodeLiteral * > ( sizeNode ) ) {
entryCount = std : : visit ( overloaded {
[ this ] ( std : : string ) - > u128 { LogConsole : : abortEvaluation ( " cannot use string to index array " , this ) ; } ,
[ this ] ( PatternData * ) - > u128 { LogConsole : : abortEvaluation ( " cannot use custom type to index array " , this ) ; } ,
[ ] ( auto & & size ) - > u128 { return size ; }
} , literal - > getValue ( ) ) ;
} else if ( auto whileStatement = dynamic_cast < ASTNodeWhileStatement * > ( sizeNode ) ) {
while ( whileStatement - > evaluateCondition ( evaluator ) ) {
entryCount + + ;
evaluator - > dataOffset ( ) + = templatePattern - > getSize ( ) ;
2021-10-07 11:34:46 +02:00
evaluator - > handleAbort ( ) ;
2021-09-21 21:29:18 +02:00
}
}
} else {
std : : vector < u8 > buffer ( templatePattern - > getSize ( ) ) ;
while ( true ) {
if ( evaluator - > dataOffset ( ) > = evaluator - > getProvider ( ) - > getActualSize ( ) - buffer . size ( ) )
LogConsole : : abortEvaluation ( " reached end of file before finding end of unsized array " , this ) ;
evaluator - > getProvider ( ) - > read ( evaluator - > dataOffset ( ) , buffer . data ( ) , buffer . size ( ) ) ;
evaluator - > dataOffset ( ) + = buffer . size ( ) ;
entryCount + + ;
bool reachedEnd = true ;
for ( u8 & byte : buffer ) {
if ( byte ! = 0x00 ) {
reachedEnd = false ;
break ;
}
}
if ( reachedEnd ) break ;
2021-10-07 11:34:46 +02:00
evaluator - > handleAbort ( ) ;
2021-09-21 21:29:18 +02:00
}
}
PatternData * outputPattern ;
if ( dynamic_cast < PatternDataPadding * > ( templatePattern ) ) {
2021-10-02 15:22:38 +02:00
outputPattern = new PatternDataPadding ( startOffset , 0 , evaluator ) ;
2021-09-21 21:29:18 +02:00
} else if ( dynamic_cast < PatternDataCharacter * > ( templatePattern ) ) {
2021-10-02 15:22:38 +02:00
outputPattern = new PatternDataString ( startOffset , 0 , evaluator ) ;
2021-09-21 21:29:18 +02:00
} else if ( dynamic_cast < PatternDataCharacter16 * > ( templatePattern ) ) {
2021-10-02 15:22:38 +02:00
outputPattern = new PatternDataString16 ( startOffset , 0 , evaluator ) ;
2021-09-21 21:29:18 +02:00
} else {
2021-10-02 15:22:38 +02:00
auto arrayPattern = new PatternDataStaticArray ( startOffset , 0 , evaluator ) ;
2021-09-21 21:29:18 +02:00
arrayPattern - > setEntries ( templatePattern - > clone ( ) , entryCount ) ;
outputPattern = arrayPattern ;
}
outputPattern - > setVariableName ( this - > m_name ) ;
outputPattern - > setEndian ( templatePattern - > getEndian ( ) ) ;
outputPattern - > setColor ( templatePattern - > getColor ( ) ) ;
outputPattern - > setTypeName ( templatePattern - > getTypeName ( ) ) ;
outputPattern - > setSize ( templatePattern - > getSize ( ) * entryCount ) ;
evaluator - > dataOffset ( ) = startOffset + outputPattern - > getSize ( ) ;
return outputPattern ;
}
PatternData * createDynamicArray ( Evaluator * evaluator ) const {
2021-10-02 15:22:38 +02:00
auto arrayPattern = new PatternDataDynamicArray ( evaluator - > dataOffset ( ) , 0 , evaluator ) ;
2021-09-21 21:29:18 +02:00
arrayPattern - > setVariableName ( this - > m_name ) ;
std : : vector < PatternData * > entries ;
2021-10-02 15:22:38 +02:00
auto arrayCleanup = SCOPE_GUARD {
for ( auto entry : entries )
delete entry ;
} ;
2021-09-21 21:29:18 +02:00
size_t size = 0 ;
u64 entryCount = 0 ;
if ( this - > m_size ! = nullptr ) {
auto sizeNode = this - > m_size - > evaluate ( evaluator ) ;
ON_SCOPE_EXIT { delete sizeNode ; } ;
{
auto templatePattern = this - > m_type - > createPatterns ( evaluator ) . front ( ) ;
ON_SCOPE_EXIT { delete templatePattern ; } ;
arrayPattern - > setTypeName ( templatePattern - > getTypeName ( ) ) ;
evaluator - > dataOffset ( ) - = templatePattern - > getSize ( ) ;
}
if ( auto literal = dynamic_cast < ASTNodeLiteral * > ( sizeNode ) ) {
entryCount = std : : visit ( overloaded {
[ this ] ( std : : string ) - > u128 { LogConsole : : abortEvaluation ( " cannot use string to index array " , this ) ; } ,
[ this ] ( PatternData * ) - > u128 { LogConsole : : abortEvaluation ( " cannot use custom type to index array " , this ) ; } ,
[ ] ( auto & & size ) - > u128 { return size ; }
} , literal - > getValue ( ) ) ;
2021-09-22 00:45:04 +02:00
auto limit = evaluator - > getArrayLimit ( ) ;
if ( entryCount > limit )
LogConsole : : abortEvaluation ( hex : : format ( " array grew past set limit of {} " , limit ) , this ) ;
2021-09-21 21:29:18 +02:00
for ( u64 i = 0 ; i < entryCount ; i + + ) {
auto pattern = this - > m_type - > createPatterns ( evaluator ) . front ( ) ;
pattern - > setVariableName ( hex : : format ( " [{}] " , i ) ) ;
pattern - > setEndian ( arrayPattern - > getEndian ( ) ) ;
pattern - > setColor ( arrayPattern - > getColor ( ) ) ;
entries . push_back ( pattern ) ;
size + = pattern - > getSize ( ) ;
2021-10-07 11:34:46 +02:00
evaluator - > handleAbort ( ) ;
2021-09-21 21:29:18 +02:00
}
} else if ( auto whileStatement = dynamic_cast < ASTNodeWhileStatement * > ( sizeNode ) ) {
while ( whileStatement - > evaluateCondition ( evaluator ) ) {
2021-09-22 00:45:04 +02:00
auto limit = evaluator - > getArrayLimit ( ) ;
if ( entryCount > limit )
LogConsole : : abortEvaluation ( hex : : format ( " array grew past set limit of {} " , limit ) , this ) ;
2021-09-21 21:29:18 +02:00
auto pattern = this - > m_type - > createPatterns ( evaluator ) . front ( ) ;
pattern - > setVariableName ( hex : : format ( " [{}] " , entryCount ) ) ;
pattern - > setEndian ( arrayPattern - > getEndian ( ) ) ;
pattern - > setColor ( arrayPattern - > getColor ( ) ) ;
entries . push_back ( pattern ) ;
entryCount + + ;
size + = pattern - > getSize ( ) ;
2021-10-07 11:34:46 +02:00
evaluator - > handleAbort ( ) ;
2021-09-21 21:29:18 +02:00
}
}
} else {
while ( true ) {
2021-09-22 00:45:04 +02:00
auto limit = evaluator - > getArrayLimit ( ) ;
if ( entryCount > limit )
LogConsole : : abortEvaluation ( hex : : format ( " array grew past set limit of {} " , limit ) , this ) ;
2021-09-21 21:29:18 +02:00
auto pattern = this - > m_type - > createPatterns ( evaluator ) . front ( ) ;
std : : vector < u8 > buffer ( pattern - > getSize ( ) ) ;
if ( evaluator - > dataOffset ( ) > = evaluator - > getProvider ( ) - > getActualSize ( ) - buffer . size ( ) ) {
delete pattern ;
LogConsole : : abortEvaluation ( " reached end of file before finding end of unsized array " , this ) ;
}
pattern - > setVariableName ( hex : : format ( " [{}] " , entryCount ) ) ;
pattern - > setEndian ( arrayPattern - > getEndian ( ) ) ;
pattern - > setColor ( arrayPattern - > getColor ( ) ) ;
entries . push_back ( pattern ) ;
size + = pattern - > getSize ( ) ;
entryCount + + ;
evaluator - > getProvider ( ) - > read ( evaluator - > dataOffset ( ) - pattern - > getSize ( ) , buffer . data ( ) , buffer . size ( ) ) ;
bool reachedEnd = true ;
for ( u8 & byte : buffer ) {
if ( byte ! = 0x00 ) {
reachedEnd = false ;
break ;
}
}
if ( reachedEnd ) break ;
2021-10-07 11:34:46 +02:00
evaluator - > handleAbort ( ) ;
2021-09-21 21:29:18 +02:00
}
}
arrayPattern - > setEntries ( entries ) ;
arrayPattern - > setSize ( size ) ;
2021-10-02 15:22:38 +02:00
arrayCleanup . release ( ) ;
2021-09-21 21:29:18 +02:00
return arrayPattern ;
}
2020-11-20 20:26:19 +01:00
} ;
2021-01-21 17:49:30 +01:00
class ASTNodePointerVariableDecl : public ASTNode , public Attributable {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
public :
2021-09-08 15:18:24 +02:00
ASTNodePointerVariableDecl ( std : : string name , ASTNode * type , ASTNode * sizeType , ASTNode * placementOffset = nullptr )
: ASTNode ( ) , m_name ( std : : move ( name ) ) , m_type ( type ) , m_sizeType ( sizeType ) , m_placementOffset ( placementOffset ) { }
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
2021-01-21 17:49:30 +01:00
ASTNodePointerVariableDecl ( const ASTNodePointerVariableDecl & other ) : ASTNode ( other ) , Attributable ( other ) {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
this - > m_name = other . m_name ;
this - > m_type = other . m_type - > clone ( ) ;
this - > m_sizeType = other . m_sizeType - > clone ( ) ;
if ( other . m_placementOffset ! = nullptr )
this - > m_placementOffset = other . m_placementOffset - > clone ( ) ;
else
this - > m_placementOffset = nullptr ;
}
~ ASTNodePointerVariableDecl ( ) override {
delete this - > m_type ;
2021-02-19 10:51:30 +01:00
delete this - > m_sizeType ;
delete this - > m_placementOffset ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
}
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
return new ASTNodePointerVariableDecl ( * this ) ;
}
2021-09-08 15:18:24 +02:00
[[nodiscard]] const std : : string & getName ( ) const { return this - > m_name ; }
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
[[nodiscard]] constexpr ASTNode * getType ( ) const { return this - > m_type ; }
[[nodiscard]] constexpr ASTNode * getSizeType ( ) const { return this - > m_sizeType ; }
[[nodiscard]] constexpr auto getPlacementOffset ( ) const { return this - > m_placementOffset ; }
2021-09-21 21:29:18 +02:00
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
if ( this - > m_placementOffset ! = nullptr ) {
auto offset = dynamic_cast < ASTNodeLiteral * > ( this - > m_placementOffset - > evaluate ( evaluator ) ) ;
ON_SCOPE_EXIT { delete offset ; } ;
evaluator - > dataOffset ( ) = std : : visit ( overloaded {
[ this ] ( std : : string ) - > u64 { LogConsole : : abortEvaluation ( " placement offset cannot be a string " , this ) ; } ,
[ this ] ( PatternData * ) - > u64 { LogConsole : : abortEvaluation ( " placement offset cannot be a custom type " , this ) ; } ,
[ ] ( auto & & offset ) - > u64 { return u64 ( offset ) ; }
} , offset - > getValue ( ) ) ;
}
2021-09-25 18:45:23 +02:00
auto offset = evaluator - > dataOffset ( ) ;
2021-09-21 21:29:18 +02:00
auto sizePattern = this - > m_sizeType - > createPatterns ( evaluator ) . front ( ) ;
ON_SCOPE_EXIT { delete sizePattern ; } ;
2021-10-02 15:22:38 +02:00
auto pattern = new PatternDataPointer ( offset , sizePattern - > getSize ( ) , evaluator ) ;
2021-09-27 20:16:23 +02:00
pattern - > setVariableName ( this - > m_name ) ;
2021-09-25 18:45:23 +02:00
offset = evaluator - > dataOffset ( ) ;
{
u128 pointerAddress = 0 ;
evaluator - > getProvider ( ) - > read ( pattern - > getOffset ( ) , & pointerAddress , pattern - > getSize ( ) ) ;
2021-10-31 15:20:19 +01:00
pointerAddress = hex : : changeEndianess ( pointerAddress , sizePattern - > getSize ( ) , sizePattern - > getEndian ( ) ) ;
2021-12-05 21:54:09 +01:00
evaluator - > dataOffset ( ) = pointerAddress ;
auto pointedAtPattern = this - > m_type - > createPatterns ( evaluator ) . front ( ) ;
2021-09-25 18:45:23 +02:00
pattern - > setPointedAtPattern ( pointedAtPattern ) ;
2021-10-31 15:20:19 +01:00
pattern - > setEndian ( sizePattern - > getEndian ( ) ) ;
2021-09-25 18:45:23 +02:00
}
2021-09-27 18:32:48 +02:00
evaluator - > dataOffset ( ) = offset ;
2021-09-21 21:29:18 +02:00
applyVariableAttributes ( evaluator , this , pattern ) ;
return { pattern } ;
}
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
private :
std : : string m_name ;
ASTNode * m_type ;
ASTNode * m_sizeType ;
ASTNode * m_placementOffset ;
} ;
2021-08-25 17:54:47 +02:00
class ASTNodeMultiVariableDecl : public ASTNode {
public :
explicit ASTNodeMultiVariableDecl ( std : : vector < ASTNode * > variables ) : m_variables ( std : : move ( variables ) ) { }
ASTNodeMultiVariableDecl ( const ASTNodeMultiVariableDecl & other ) : ASTNode ( other ) {
for ( auto & variable : other . m_variables )
this - > m_variables . push_back ( variable - > clone ( ) ) ;
}
~ ASTNodeMultiVariableDecl ( ) override {
for ( auto & variable : this - > m_variables )
delete variable ;
}
[[nodiscard]] ASTNode * clone ( ) const override {
return new ASTNodeMultiVariableDecl ( * this ) ;
}
[[nodiscard]] std : : vector < ASTNode * > getVariables ( ) {
return this - > m_variables ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
std : : vector < PatternData * > patterns ;
for ( auto & node : this - > m_variables ) {
auto newPatterns = node - > createPatterns ( evaluator ) ;
patterns . insert ( patterns . end ( ) , newPatterns . begin ( ) , newPatterns . end ( ) ) ;
}
return patterns ;
}
2021-11-27 12:57:59 +01:00
FunctionResult execute ( Evaluator * evaluator ) const override {
2021-09-21 21:29:18 +02:00
for ( auto & variable : this - > m_variables ) {
auto variableDecl = dynamic_cast < ASTNodeVariableDecl * > ( variable ) ;
evaluator - > createVariable ( variableDecl - > getName ( ) , variableDecl - > getType ( ) - > evaluate ( evaluator ) ) ;
}
return { false , { } } ;
}
2021-08-25 17:54:47 +02:00
private :
std : : vector < ASTNode * > m_variables ;
} ;
2021-01-21 17:49:30 +01:00
class ASTNodeStruct : public ASTNode , public Attributable {
2020-11-10 15:26:38 +01:00
public :
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
ASTNodeStruct ( ) : ASTNode ( ) { }
2021-01-21 17:49:30 +01:00
ASTNodeStruct ( const ASTNodeStruct & other ) : ASTNode ( other ) , Attributable ( other ) {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
for ( const auto & otherMember : other . getMembers ( ) )
this - > m_members . push_back ( otherMember - > clone ( ) ) ;
2021-09-24 00:47:34 +02:00
for ( const auto & otherInheritance : other . getInheritance ( ) )
this - > m_inheritance . push_back ( otherInheritance - > clone ( ) ) ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
}
~ ASTNodeStruct ( ) override {
for ( auto & member : this - > m_members )
delete member ;
2021-09-24 00:47:34 +02:00
for ( auto & inheritance : this - > m_inheritance )
delete inheritance ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
}
2020-11-10 15:26:38 +01:00
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
return new ASTNodeStruct ( * this ) ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
2021-10-02 15:22:38 +02:00
auto pattern = new PatternDataStruct ( evaluator - > dataOffset ( ) , 0 , evaluator ) ;
2021-09-21 21:29:18 +02:00
u64 startOffset = evaluator - > dataOffset ( ) ;
std : : vector < PatternData * > memberPatterns ;
2021-10-02 15:22:38 +02:00
auto structCleanup = SCOPE_GUARD {
delete pattern ;
for ( auto member : memberPatterns )
delete member ;
} ;
2021-09-21 21:29:18 +02:00
evaluator - > pushScope ( pattern , memberPatterns ) ;
2021-09-24 00:47:34 +02:00
for ( auto inheritance : this - > m_inheritance ) {
auto inheritancePatterns = inheritance - > createPatterns ( evaluator ) . front ( ) ;
ON_SCOPE_EXIT {
delete inheritancePatterns ;
} ;
if ( auto structPattern = dynamic_cast < PatternDataStruct * > ( inheritancePatterns ) ) {
for ( auto member : structPattern - > getMembers ( ) ) {
memberPatterns . push_back ( member - > clone ( ) ) ;
}
}
}
2021-09-21 21:29:18 +02:00
for ( auto member : this - > m_members ) {
for ( auto & memberPattern : member - > createPatterns ( evaluator ) ) {
memberPatterns . push_back ( memberPattern ) ;
}
}
2021-09-24 00:47:34 +02:00
2021-09-21 21:29:18 +02:00
evaluator - > popScope ( ) ;
pattern - > setMembers ( memberPatterns ) ;
pattern - > setSize ( evaluator - > dataOffset ( ) - startOffset ) ;
2021-10-02 15:22:38 +02:00
structCleanup . release ( ) ;
2021-09-21 21:29:18 +02:00
return { pattern } ;
}
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
[[nodiscard]] const std : : vector < ASTNode * > & getMembers ( ) const { return this - > m_members ; }
void addMember ( ASTNode * node ) { this - > m_members . push_back ( node ) ; }
2020-11-10 15:26:38 +01:00
2021-09-24 00:47:34 +02:00
[[nodiscard]] const std : : vector < ASTNode * > & getInheritance ( ) const { return this - > m_inheritance ; }
void addInheritance ( ASTNode * node ) { this - > m_inheritance . push_back ( node ) ; }
2020-11-10 15:26:38 +01:00
private :
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
std : : vector < ASTNode * > m_members ;
2021-09-24 00:47:34 +02:00
std : : vector < ASTNode * > m_inheritance ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
} ;
2021-01-21 17:49:30 +01:00
class ASTNodeUnion : public ASTNode , public Attributable {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
public :
ASTNodeUnion ( ) : ASTNode ( ) { }
2021-01-21 17:49:30 +01:00
ASTNodeUnion ( const ASTNodeUnion & other ) : ASTNode ( other ) , Attributable ( other ) {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
for ( const auto & otherMember : other . getMembers ( ) )
this - > m_members . push_back ( otherMember - > clone ( ) ) ;
}
~ ASTNodeUnion ( ) override {
for ( auto & member : this - > m_members )
delete member ;
}
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
return new ASTNodeUnion ( * this ) ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
2021-10-02 15:22:38 +02:00
auto pattern = new PatternDataUnion ( evaluator - > dataOffset ( ) , 0 , evaluator ) ;
2021-09-21 21:29:18 +02:00
size_t size = 0 ;
std : : vector < PatternData * > memberPatterns ;
u64 startOffset = evaluator - > dataOffset ( ) ;
2021-10-02 15:22:38 +02:00
auto unionCleanup = SCOPE_GUARD {
delete pattern ;
for ( auto member : memberPatterns )
delete member ;
} ;
2021-09-21 21:29:18 +02:00
evaluator - > pushScope ( pattern , memberPatterns ) ;
for ( auto member : this - > m_members ) {
for ( auto & memberPattern : member - > createPatterns ( evaluator ) ) {
memberPattern - > setOffset ( startOffset ) ;
memberPatterns . push_back ( memberPattern ) ;
size = std : : max ( memberPattern - > getSize ( ) , size ) ;
}
}
evaluator - > popScope ( ) ;
evaluator - > dataOffset ( ) = startOffset + size ;
pattern - > setMembers ( memberPatterns ) ;
pattern - > setSize ( size ) ;
2021-10-02 15:22:38 +02:00
unionCleanup . release ( ) ;
2021-09-21 21:29:18 +02:00
return { pattern } ;
}
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
[[nodiscard]] const std : : vector < ASTNode * > & getMembers ( ) const { return this - > m_members ; }
void addMember ( ASTNode * node ) { this - > m_members . push_back ( node ) ; }
private :
std : : vector < ASTNode * > m_members ;
2020-11-10 15:26:38 +01:00
} ;
2021-01-21 17:49:30 +01:00
class ASTNodeEnum : public ASTNode , public Attributable {
2020-11-14 14:40:21 +01:00
public :
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
explicit ASTNodeEnum ( ASTNode * underlyingType ) : ASTNode ( ) , m_underlyingType ( underlyingType ) { }
2021-01-21 17:49:30 +01:00
ASTNodeEnum ( const ASTNodeEnum & other ) : ASTNode ( other ) , Attributable ( other ) {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
for ( const auto & [ name , entry ] : other . getEntries ( ) )
2021-09-21 21:29:18 +02:00
this - > m_entries . emplace ( name , entry - > clone ( ) ) ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
this - > m_underlyingType = other . m_underlyingType - > clone ( ) ;
}
~ ASTNodeEnum ( ) override {
for ( auto & [ name , expr ] : this - > m_entries )
delete expr ;
delete this - > m_underlyingType ;
}
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
return new ASTNodeEnum ( * this ) ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
2021-10-02 15:22:38 +02:00
auto pattern = new PatternDataEnum ( evaluator - > dataOffset ( ) , 0 , evaluator ) ;
auto enumCleanup = SCOPE_GUARD { delete pattern ; } ;
2021-09-21 21:29:18 +02:00
std : : vector < std : : pair < Token : : Literal , std : : string > > enumEntries ;
for ( const auto & [ name , value ] : this - > m_entries ) {
auto literal = dynamic_cast < ASTNodeLiteral * > ( value - > evaluate ( evaluator ) ) ;
ON_SCOPE_EXIT { delete literal ; } ;
enumEntries . emplace_back ( literal - > getValue ( ) , name ) ;
}
pattern - > setEnumValues ( enumEntries ) ;
auto underlying = this - > m_underlyingType - > createPatterns ( evaluator ) . front ( ) ;
ON_SCOPE_EXIT { delete underlying ; } ;
pattern - > setSize ( underlying - > getSize ( ) ) ;
pattern - > setEndian ( underlying - > getEndian ( ) ) ;
2021-10-02 15:22:38 +02:00
enumCleanup . release ( ) ;
2021-09-21 21:29:18 +02:00
return { pattern } ;
}
2021-09-11 23:14:22 +02:00
[[nodiscard]] const std : : map < std : : string , ASTNode * > & getEntries ( ) const { return this - > m_entries ; }
2021-01-06 16:28:41 +01:00
void addEntry ( const std : : string & name , ASTNode * expression ) { this - > m_entries . insert ( { name , expression } ) ; }
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
2021-01-10 17:14:38 +01:00
[[nodiscard]] ASTNode * getUnderlyingType ( ) { return this - > m_underlyingType ; }
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
private :
2021-09-11 23:14:22 +02:00
std : : map < std : : string , ASTNode * > m_entries ;
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
ASTNode * m_underlyingType ;
} ;
2021-01-21 17:49:30 +01:00
class ASTNodeBitfield : public ASTNode , public Attributable {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
public :
ASTNodeBitfield ( ) : ASTNode ( ) { }
2021-01-21 17:49:30 +01:00
ASTNodeBitfield ( const ASTNodeBitfield & other ) : ASTNode ( other ) , Attributable ( other ) {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
for ( const auto & [ name , entry ] : other . getEntries ( ) )
this - > m_entries . emplace_back ( name , entry - > clone ( ) ) ;
}
~ ASTNodeBitfield ( ) override {
for ( auto & [ name , expr ] : this - > m_entries )
delete expr ;
}
2020-11-14 14:40:21 +01:00
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
return new ASTNodeBitfield ( * this ) ;
}
[[nodiscard]] const std : : vector < std : : pair < std : : string , ASTNode * > > & getEntries ( ) const { return this - > m_entries ; }
void addEntry ( const std : : string & name , ASTNode * size ) { this - > m_entries . emplace_back ( name , size ) ; }
2020-11-14 14:40:21 +01:00
2021-09-21 21:29:18 +02:00
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
2021-10-02 15:22:38 +02:00
auto pattern = new PatternDataBitfield ( evaluator - > dataOffset ( ) , 0 , evaluator ) ;
2021-09-21 21:29:18 +02:00
size_t bitOffset = 0 ;
std : : vector < PatternData * > fields ;
2021-10-02 15:22:38 +02:00
auto bitfieldCleanup = SCOPE_GUARD {
delete pattern ;
for ( auto field : fields )
delete field ;
} ;
2021-09-21 21:29:18 +02:00
evaluator - > pushScope ( pattern , fields ) ;
for ( auto [ name , bitSizeNode ] : this - > m_entries ) {
auto literal = bitSizeNode - > evaluate ( evaluator ) ;
ON_SCOPE_EXIT { delete literal ; } ;
u8 bitSize = std : : visit ( overloaded {
[ this ] ( std : : string ) - > u8 { LogConsole : : abortEvaluation ( " bitfield field size cannot be a string " , this ) ; } ,
[ this ] ( PatternData * ) - > u8 { LogConsole : : abortEvaluation ( " bitfield field size cannot be a custom type " , this ) ; } ,
[ ] ( auto & & offset ) - > u8 { return static_cast < u8 > ( offset ) ; }
} , dynamic_cast < ASTNodeLiteral * > ( literal ) - > getValue ( ) ) ;
2021-10-14 20:28:13 +02:00
// If a field is named padding, it was created through a padding expression and only advances the bit position
if ( name ! = " padding " ) {
auto field = new PatternDataBitfieldField ( evaluator - > dataOffset ( ) , bitOffset , bitSize , evaluator ) ;
field - > setVariableName ( name ) ;
fields . push_back ( field ) ;
}
2021-09-21 21:29:18 +02:00
bitOffset + = bitSize ;
}
evaluator - > popScope ( ) ;
pattern - > setSize ( ( bitOffset + 7 ) / 8 ) ;
pattern - > setFields ( fields ) ;
evaluator - > dataOffset ( ) + = pattern - > getSize ( ) ;
2021-10-02 15:22:38 +02:00
bitfieldCleanup . release ( ) ;
2021-09-21 21:29:18 +02:00
return { pattern } ;
}
2020-11-14 14:40:21 +01:00
private :
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
std : : vector < std : : pair < std : : string , ASTNode * > > m_entries ;
} ;
class ASTNodeRValue : public ASTNode {
public :
2021-04-21 10:17:42 +02:00
using Path = std : : vector < std : : variant < std : : string , ASTNode * > > ;
explicit ASTNodeRValue ( Path path ) : ASTNode ( ) , m_path ( std : : move ( path ) ) { }
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
ASTNodeRValue ( const ASTNodeRValue & ) = default ;
2021-04-21 10:17:42 +02:00
~ ASTNodeRValue ( ) override {
for ( auto & part : this - > m_path ) {
if ( auto node = std : : get_if < ASTNode * > ( & part ) ; node ! = nullptr )
delete * node ;
}
}
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
return new ASTNodeRValue ( * this ) ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]]
const Path & getPath ( ) const {
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
return this - > m_path ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]] ASTNode * evaluate ( Evaluator * evaluator ) const override {
if ( this - > getPath ( ) . size ( ) = = 1 ) {
if ( auto name = std : : get_if < std : : string > ( & this - > getPath ( ) . front ( ) ) ; name ! = nullptr ) {
if ( * name = = " $ " ) return new ASTNodeLiteral ( u128 ( evaluator - > dataOffset ( ) ) ) ;
}
}
auto pattern = this - > createPatterns ( evaluator ) . front ( ) ;
ON_SCOPE_EXIT { delete pattern ; } ;
auto readValue = [ & evaluator ] ( auto & value , PatternData * pattern ) {
if ( pattern - > isLocal ( ) ) {
auto & literal = evaluator - > getStack ( ) [ pattern - > getOffset ( ) ] ;
std : : visit ( overloaded {
2021-10-04 20:26:34 +02:00
[ & ] ( std : : string & assignmentValue ) { } ,
2021-12-18 22:56:36 +01:00
[ & ] ( PatternData * assignmentValue ) { } ,
[ & ] ( auto & & assignmentValue ) { value = assignmentValue ; }
2021-09-21 21:29:18 +02:00
} , literal ) ;
}
else
evaluator - > getProvider ( ) - > read ( pattern - > getOffset ( ) , & value , pattern - > getSize ( ) ) ;
2021-09-25 22:46:16 +02:00
value = hex : : changeEndianess ( value , pattern - > getSize ( ) , pattern - > getEndian ( ) ) ;
2021-09-21 21:29:18 +02:00
} ;
2021-10-04 20:26:34 +02:00
auto readString = [ & evaluator ] ( std : : string & value , PatternData * pattern ) {
if ( pattern - > isLocal ( ) ) {
auto & literal = evaluator - > getStack ( ) [ pattern - > getOffset ( ) ] ;
std : : visit ( overloaded {
[ & ] ( std : : string & assignmentValue ) { value = assignmentValue ; } ,
[ & ] ( auto & & assignmentValue ) { }
} , literal ) ;
}
else {
value . resize ( pattern - > getSize ( ) ) ;
evaluator - > getProvider ( ) - > read ( pattern - > getOffset ( ) , value . data ( ) , value . size ( ) ) ;
2021-10-07 21:47:39 +02:00
value . erase ( std : : find ( value . begin ( ) , value . end ( ) , ' \0 ' ) , value . end ( ) ) ;
2021-10-04 20:26:34 +02:00
}
} ;
2021-09-21 21:29:18 +02:00
Token : : Literal literal ;
2021-09-25 14:52:17 +02:00
if ( dynamic_cast < PatternDataUnsigned * > ( pattern ) | | dynamic_cast < PatternDataEnum * > ( pattern ) ) {
2021-09-21 21:29:18 +02:00
u128 value = 0 ;
readValue ( value , pattern ) ;
literal = value ;
} else if ( dynamic_cast < PatternDataSigned * > ( pattern ) ) {
s128 value = 0 ;
readValue ( value , pattern ) ;
2021-11-27 14:34:59 +01:00
value = hex : : signExtend ( pattern - > getSize ( ) * 8 , value ) ;
2021-09-21 21:29:18 +02:00
literal = value ;
} else if ( dynamic_cast < PatternDataFloat * > ( pattern ) ) {
if ( pattern - > getSize ( ) = = sizeof ( u16 ) ) {
u16 value = 0 ;
readValue ( value , pattern ) ;
literal = double ( float16ToFloat32 ( value ) ) ;
} else if ( pattern - > getSize ( ) = = sizeof ( float ) ) {
float value = 0 ;
readValue ( value , pattern ) ;
literal = double ( value ) ;
} else if ( pattern - > getSize ( ) = = sizeof ( double ) ) {
double value = 0 ;
readValue ( value , pattern ) ;
literal = value ;
} else LogConsole : : abortEvaluation ( " invalid floating point type access " , this ) ;
} else if ( dynamic_cast < PatternDataCharacter * > ( pattern ) ) {
char value = 0 ;
readValue ( value , pattern ) ;
literal = value ;
} else if ( dynamic_cast < PatternDataBoolean * > ( pattern ) ) {
bool value = false ;
readValue ( value , pattern ) ;
literal = value ;
} else if ( dynamic_cast < PatternDataString * > ( pattern ) ) {
std : : string value ;
if ( pattern - > isLocal ( ) ) {
auto & literal = evaluator - > getStack ( ) [ pattern - > getOffset ( ) ] ;
std : : visit ( overloaded {
2021-10-04 20:26:34 +02:00
[ & ] ( char assignmentValue ) { if ( assignmentValue ! = 0x00 ) value = std : : string ( { assignmentValue } ) ; } ,
[ & ] ( std : : string assignmentValue ) { value = assignmentValue ; } ,
[ & , this ] ( PatternData * const & assignmentValue ) {
if ( ! dynamic_cast < PatternDataString * > ( assignmentValue ) & & ! dynamic_cast < PatternDataCharacter * > ( assignmentValue ) )
LogConsole : : abortEvaluation ( hex : : format ( " cannot assign '{}' to string " , pattern - > getTypeName ( ) ) , this ) ;
readString ( value , assignmentValue ) ;
} ,
2021-09-21 21:29:18 +02:00
[ & , this ] ( auto & & assignmentValue ) { LogConsole : : abortEvaluation ( hex : : format ( " cannot assign '{}' to string " , pattern - > getTypeName ( ) ) , this ) ; }
} , literal ) ;
}
2021-09-25 14:52:34 +02:00
else {
value . resize ( pattern - > getSize ( ) ) ;
evaluator - > getProvider ( ) - > read ( pattern - > getOffset ( ) , value . data ( ) , value . size ( ) ) ;
2021-10-07 21:47:39 +02:00
value . erase ( std : : find ( value . begin ( ) , value . end ( ) , ' \0 ' ) , value . end ( ) ) ;
2021-09-25 14:52:34 +02:00
}
2021-09-21 21:29:18 +02:00
literal = value ;
} else if ( auto bitfieldFieldPattern = dynamic_cast < PatternDataBitfieldField * > ( pattern ) ) {
u64 value = 0 ;
readValue ( value , pattern ) ;
literal = u128 ( hex : : extract ( bitfieldFieldPattern - > getBitOffset ( ) + ( bitfieldFieldPattern - > getBitSize ( ) - 1 ) , bitfieldFieldPattern - > getBitOffset ( ) , value ) ) ;
} else {
literal = pattern - > clone ( ) ;
}
2021-10-03 12:32:58 +02:00
if ( auto transformFunc = pattern - > getTransformFunction ( ) ; transformFunc . has_value ( ) & & pattern - > getEvaluator ( ) ! = nullptr ) {
2021-09-27 18:32:48 +02:00
auto result = transformFunc - > func ( evaluator , { literal } ) ;
if ( ! result . has_value ( ) )
LogConsole : : abortEvaluation ( " transform function did not return a value " , this ) ;
literal = result . value ( ) ;
}
2021-09-21 21:29:18 +02:00
return new ASTNodeLiteral ( literal ) ;
}
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
2021-10-11 22:01:15 +02:00
std : : vector < PatternData * > searchScope ;
PatternData * currPattern = nullptr ;
2021-09-21 21:29:18 +02:00
s32 scopeIndex = 0 ;
2021-10-11 22:01:15 +02:00
if ( ! evaluator - > isGlobalScope ( ) ) {
auto globalScope = evaluator - > getGlobalScope ( ) . scope ;
std : : copy ( globalScope - > begin ( ) , globalScope - > end ( ) , std : : back_inserter ( searchScope ) ) ;
}
{
auto currScope = evaluator - > getScope ( scopeIndex ) . scope ;
std : : copy ( currScope - > begin ( ) , currScope - > end ( ) , std : : back_inserter ( searchScope ) ) ;
}
2021-09-21 21:29:18 +02:00
for ( const auto & part : this - > getPath ( ) ) {
if ( part . index ( ) = = 0 ) {
// Variable access
auto name = std : : get < std : : string > ( part ) ;
if ( name = = " parent " ) {
scopeIndex - - ;
2021-10-17 21:49:33 +02:00
if ( - scopeIndex > = evaluator - > getScopeCount ( ) )
LogConsole : : abortEvaluation ( " cannot access parent of global scope " , this ) ;
2021-09-21 21:29:18 +02:00
searchScope = * evaluator - > getScope ( scopeIndex ) . scope ;
2021-09-27 18:32:48 +02:00
auto currParent = evaluator - > getScope ( scopeIndex ) . parent ;
2021-10-17 21:49:33 +02:00
if ( currParent = = nullptr ) {
currPattern = nullptr ;
} else {
currPattern = currParent - > clone ( ) ;
}
2021-09-27 18:32:48 +02:00
continue ;
2021-09-21 21:29:18 +02:00
} else if ( name = = " this " ) {
searchScope = * evaluator - > getScope ( scopeIndex ) . scope ;
auto currParent = evaluator - > getScope ( 0 ) . parent ;
if ( currParent = = nullptr )
LogConsole : : abortEvaluation ( " invalid use of 'this' outside of struct-like type " , this ) ;
currPattern = currParent - > clone ( ) ;
continue ;
} else {
bool found = false ;
2021-10-09 23:07:58 +02:00
for ( auto iter = searchScope . crbegin ( ) ; iter ! = searchScope . crend ( ) ; + + iter ) {
if ( ( * iter ) - > getVariableName ( ) = = name ) {
auto newPattern = ( * iter ) - > clone ( ) ;
2021-09-21 21:29:18 +02:00
delete currPattern ;
currPattern = newPattern ;
found = true ;
break ;
}
}
if ( name = = " $ " )
LogConsole : : abortEvaluation ( " invalid use of placeholder operator in rvalue " ) ;
if ( ! found )
LogConsole : : abortEvaluation ( hex : : format ( " no variable named '{}' found " , name ) , this ) ;
}
} else {
// Array indexing
auto index = dynamic_cast < ASTNodeLiteral * > ( std : : get < ASTNode * > ( part ) - > evaluate ( evaluator ) ) ;
ON_SCOPE_EXIT { delete index ; } ;
std : : visit ( overloaded {
[ ] ( std : : string ) { throw std : : string ( " cannot use string to index array " ) ; } ,
[ ] ( PatternData * const & ) { throw std : : string ( " cannot use custom type to index array " ) ; } ,
[ & , this ] ( auto & & index ) {
if ( auto dynamicArrayPattern = dynamic_cast < PatternDataDynamicArray * > ( currPattern ) ) {
if ( index > = searchScope . size ( ) | | index < 0 )
LogConsole : : abortEvaluation ( " array index out of bounds " , this ) ;
auto newPattern = searchScope [ index ] - > clone ( ) ;
delete currPattern ;
currPattern = newPattern ;
}
else if ( auto staticArrayPattern = dynamic_cast < PatternDataStaticArray * > ( currPattern ) ) {
if ( index > = staticArrayPattern - > getEntryCount ( ) | | index < 0 )
LogConsole : : abortEvaluation ( " array index out of bounds " , this ) ;
auto newPattern = searchScope . front ( ) - > clone ( ) ;
2021-12-10 18:53:19 +01:00
newPattern - > setOffset ( staticArrayPattern - > getOffset ( ) + index * staticArrayPattern - > getTemplate ( ) - > getSize ( ) ) ;
2021-09-21 21:29:18 +02:00
delete currPattern ;
currPattern = newPattern ;
}
}
} , index - > getValue ( ) ) ;
}
2021-10-17 21:49:33 +02:00
if ( currPattern = = nullptr )
break ;
2021-09-21 21:29:18 +02:00
if ( auto pointerPattern = dynamic_cast < PatternDataPointer * > ( currPattern ) ) {
auto newPattern = pointerPattern - > getPointedAtPattern ( ) - > clone ( ) ;
delete currPattern ;
currPattern = newPattern ;
}
if ( auto structPattern = dynamic_cast < PatternDataStruct * > ( currPattern ) )
searchScope = structPattern - > getMembers ( ) ;
else if ( auto unionPattern = dynamic_cast < PatternDataUnion * > ( currPattern ) )
searchScope = unionPattern - > getMembers ( ) ;
else if ( auto bitfieldPattern = dynamic_cast < PatternDataBitfield * > ( currPattern ) )
searchScope = bitfieldPattern - > getFields ( ) ;
else if ( auto dynamicArrayPattern = dynamic_cast < PatternDataDynamicArray * > ( currPattern ) )
searchScope = dynamicArrayPattern - > getEntries ( ) ;
else if ( auto staticArrayPattern = dynamic_cast < PatternDataStaticArray * > ( currPattern ) )
searchScope = { staticArrayPattern - > getTemplate ( ) } ;
}
2021-10-17 21:49:33 +02:00
if ( currPattern = = nullptr )
LogConsole : : abortEvaluation ( " cannot reference global scope " , this ) ;
2021-09-21 21:29:18 +02:00
return { currPattern } ;
}
Pattern Language rewrite (#111)
* Initial parser rewrite effort
Lexer and Token cleanup, Parser started over
* Greatly improved parser syntax
* Reimplemented using declarations and variable placement parsing
* Added back unions and structs
* Added enums as well as mathematical expressions (+, -, *, /, <<, >>, &, |, ^)
* Code style improvement
* Implemented arrays and fixed memory issues
* Fixed more memory issues in parser, reimplemented validator, evaluator and patterns
* Fixed builtin types, arrays and reimplemented strings
* Improved error messages
* Made character a distinct type, used for chars and strings
* Implemented padding, fixed arrays
* Added bitfields
* Added rvalue parsing, no evaluating yet
* Added .idea folder to gitignore
* Fixed build on MacOS
* Added custom implementation of integral concept if not available
* Rebased onto master
* Fixed array variable decl crash
* Added rvalues and dot syntax
* Lower case all pattern language error messages
* Fixed typo in variable name
* Fixed bug where preprocessor would not ignore commented out directives
* Reimplemented pointers
* Fixed rebase issues
2021-01-02 20:27:11 +01:00
private :
2021-04-21 10:17:42 +02:00
Path m_path ;
2020-11-14 14:40:21 +01:00
} ;
2021-01-05 14:42:08 +01:00
class ASTNodeScopeResolution : public ASTNode {
public :
2021-09-25 14:52:17 +02:00
explicit ASTNodeScopeResolution ( ASTNode * type , std : : string name ) : ASTNode ( ) , m_type ( type ) , m_name ( std : : move ( name ) ) { }
2021-01-05 14:42:08 +01:00
2021-09-25 14:52:17 +02:00
ASTNodeScopeResolution ( const ASTNodeScopeResolution & other ) {
this - > m_type = other . m_type - > clone ( ) ;
this - > m_name = other . m_name ;
}
~ ASTNodeScopeResolution ( ) override {
delete this - > m_type ;
}
2021-01-05 14:42:08 +01:00
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
2021-01-05 14:42:08 +01:00
return new ASTNodeScopeResolution ( * this ) ;
}
2021-09-25 14:52:17 +02:00
[[nodiscard]] ASTNode * evaluate ( Evaluator * evaluator ) const override {
auto type = this - > m_type - > evaluate ( evaluator ) ;
ON_SCOPE_EXIT { delete type ; } ;
if ( auto enumType = dynamic_cast < ASTNodeEnum * > ( type ) ) {
for ( auto & [ name , value ] : enumType - > getEntries ( ) ) {
if ( name = = this - > m_name )
return value - > evaluate ( evaluator ) ;
}
} else {
LogConsole : : abortEvaluation ( " invalid scope resolution. Cannot access this type " ) ;
}
LogConsole : : abortEvaluation ( hex : : format ( " could not find constant '{}' " , this - > m_name ) , this ) ;
2021-01-05 14:42:08 +01:00
}
private :
2021-09-25 14:52:17 +02:00
ASTNode * m_type ;
std : : string m_name ;
2021-01-05 14:42:08 +01:00
} ;
2021-01-07 00:02:51 +01:00
class ASTNodeConditionalStatement : public ASTNode {
public :
explicit ASTNodeConditionalStatement ( ASTNode * condition , std : : vector < ASTNode * > trueBody , std : : vector < ASTNode * > falseBody )
: ASTNode ( ) , m_condition ( condition ) , m_trueBody ( std : : move ( trueBody ) ) , m_falseBody ( std : : move ( falseBody ) ) { }
~ ASTNodeConditionalStatement ( ) override {
delete this - > m_condition ;
for ( auto & statement : this - > m_trueBody )
delete statement ;
for ( auto & statement : this - > m_falseBody )
delete statement ;
}
ASTNodeConditionalStatement ( const ASTNodeConditionalStatement & other ) : ASTNode ( other ) {
this - > m_condition = other . m_condition - > clone ( ) ;
for ( auto & statement : other . m_trueBody )
this - > m_trueBody . push_back ( statement - > clone ( ) ) ;
for ( auto & statement : other . m_falseBody )
this - > m_falseBody . push_back ( statement - > clone ( ) ) ;
}
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
2021-01-07 00:02:51 +01:00
return new ASTNodeConditionalStatement ( * this ) ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
2021-09-26 02:22:50 +02:00
auto & scope = * evaluator - > getScope ( 0 ) . scope ;
2021-09-21 21:29:18 +02:00
auto & body = evaluateCondition ( evaluator ) ? this - > m_trueBody : this - > m_falseBody ;
for ( auto & node : body ) {
auto newPatterns = node - > createPatterns ( evaluator ) ;
2021-09-26 02:22:50 +02:00
for ( auto & pattern : newPatterns )
scope . push_back ( pattern - > clone ( ) ) ;
2021-09-21 21:29:18 +02:00
}
2021-09-26 02:22:50 +02:00
return { } ;
2021-09-21 21:29:18 +02:00
}
2021-01-07 00:02:51 +01:00
[[nodiscard]] ASTNode * getCondition ( ) {
return this - > m_condition ;
}
[[nodiscard]] const std : : vector < ASTNode * > & getTrueBody ( ) const {
return this - > m_trueBody ;
}
[[nodiscard]] const std : : vector < ASTNode * > & getFalseBody ( ) const {
return this - > m_falseBody ;
}
2021-11-27 12:57:59 +01:00
FunctionResult execute ( Evaluator * evaluator ) const override {
2021-09-21 21:29:18 +02:00
auto & body = evaluateCondition ( evaluator ) ? this - > m_trueBody : this - > m_falseBody ;
auto variables = * evaluator - > getScope ( 0 ) . scope ;
u32 startVariableCount = variables . size ( ) ;
ON_SCOPE_EXIT {
s64 stackSize = evaluator - > getStack ( ) . size ( ) ;
for ( u32 i = startVariableCount ; i < variables . size ( ) ; i + + ) {
stackSize - - ;
delete variables [ i ] ;
}
if ( stackSize < 0 ) LogConsole : : abortEvaluation ( " stack pointer underflow! " , this ) ;
evaluator - > getStack ( ) . resize ( stackSize ) ;
} ;
evaluator - > pushScope ( nullptr , variables ) ;
ON_SCOPE_EXIT { evaluator - > popScope ( ) ; } ;
for ( auto & statement : body ) {
auto [ executionStopped , result ] = statement - > execute ( evaluator ) ;
if ( executionStopped ) {
return { true , result } ;
}
}
2021-06-17 23:13:58 +02:00
2021-09-21 21:29:18 +02:00
return { false , { } } ;
2021-06-17 23:13:58 +02:00
}
2021-09-21 21:29:18 +02:00
private :
[[nodiscard]]
bool evaluateCondition ( Evaluator * evaluator ) const {
auto literal = dynamic_cast < ASTNodeLiteral * > ( this - > m_condition - > evaluate ( evaluator ) ) ;
ON_SCOPE_EXIT { delete literal ; } ;
2021-06-17 23:13:58 +02:00
2021-09-21 21:29:18 +02:00
return std : : visit ( overloaded {
[ ] ( std : : string value ) - > bool { return ! value . empty ( ) ; } ,
[ this ] ( PatternData * const & ) - > bool { LogConsole : : abortEvaluation ( " cannot cast custom type to bool " , this ) ; } ,
[ ] ( auto & & value ) - > bool { return value ! = 0 ; }
} , literal - > getValue ( ) ) ;
2021-06-17 23:13:58 +02:00
}
ASTNode * m_condition ;
2021-09-21 21:29:18 +02:00
std : : vector < ASTNode * > m_trueBody , m_falseBody ;
2021-06-17 23:13:58 +02:00
} ;
2021-01-07 15:37:37 +01:00
class ASTNodeFunctionCall : public ASTNode {
public :
2021-09-08 15:18:24 +02:00
explicit ASTNodeFunctionCall ( std : : string functionName , std : : vector < ASTNode * > params )
: ASTNode ( ) , m_functionName ( std : : move ( functionName ) ) , m_params ( std : : move ( params ) ) { }
2021-01-07 15:37:37 +01:00
~ ASTNodeFunctionCall ( ) override {
for ( auto & param : this - > m_params )
delete param ;
}
ASTNodeFunctionCall ( const ASTNodeFunctionCall & other ) : ASTNode ( other ) {
this - > m_functionName = other . m_functionName ;
for ( auto & param : other . m_params )
this - > m_params . push_back ( param - > clone ( ) ) ;
}
2021-01-21 17:49:30 +01:00
[[nodiscard]] ASTNode * clone ( ) const override {
2021-01-07 15:37:37 +01:00
return new ASTNodeFunctionCall ( * this ) ;
}
2021-09-08 15:18:24 +02:00
[[nodiscard]] const std : : string & getFunctionName ( ) {
2021-01-07 15:37:37 +01:00
return this - > m_functionName ;
}
[[nodiscard]] const std : : vector < ASTNode * > & getParams ( ) const {
return this - > m_params ;
}
2021-11-27 12:57:59 +01:00
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
this - > execute ( evaluator ) ;
return { } ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]] ASTNode * evaluate ( Evaluator * evaluator ) const override {
std : : vector < Token : : Literal > evaluatedParams ;
for ( auto param : this - > m_params ) {
auto expression = param - > evaluate ( evaluator ) ;
ON_SCOPE_EXIT { delete expression ; } ;
2021-01-07 15:37:37 +01:00
2021-09-21 21:29:18 +02:00
auto literal = dynamic_cast < ASTNodeLiteral * > ( expression - > evaluate ( evaluator ) ) ;
ON_SCOPE_EXIT { delete literal ; } ;
2021-01-09 21:47:11 +01:00
2021-09-21 21:29:18 +02:00
evaluatedParams . push_back ( literal - > getValue ( ) ) ;
}
2021-01-09 21:47:11 +01:00
2021-09-21 21:29:18 +02:00
auto & customFunctions = evaluator - > getCustomFunctions ( ) ;
auto functions = ContentRegistry : : PatternLanguageFunctions : : getEntries ( ) ;
2021-01-09 21:47:11 +01:00
2021-09-21 21:29:18 +02:00
for ( auto & func : customFunctions )
functions . insert ( func ) ;
2021-01-09 21:47:11 +01:00
2021-09-21 21:29:18 +02:00
if ( ! functions . contains ( this - > m_functionName ) )
LogConsole : : abortEvaluation ( hex : : format ( " call to unknown function '{}' " , this - > m_functionName ) , this ) ;
2021-01-09 21:47:11 +01:00
2021-09-21 21:29:18 +02:00
auto function = functions [ this - > m_functionName ] ;
if ( function . parameterCount = = ContentRegistry : : PatternLanguageFunctions : : UnlimitedParameters ) {
; // Don't check parameter count
}
else if ( function . parameterCount & ContentRegistry : : PatternLanguageFunctions : : LessParametersThan ) {
if ( evaluatedParams . size ( ) > = ( function . parameterCount & ~ ContentRegistry : : PatternLanguageFunctions : : LessParametersThan ) )
LogConsole : : abortEvaluation ( hex : : format ( " too many parameters for function '{0}'. Expected {1} " , this - > m_functionName , function . parameterCount & ~ ContentRegistry : : PatternLanguageFunctions : : LessParametersThan ) , this ) ;
} else if ( function . parameterCount & ContentRegistry : : PatternLanguageFunctions : : MoreParametersThan ) {
if ( evaluatedParams . size ( ) < = ( function . parameterCount & ~ ContentRegistry : : PatternLanguageFunctions : : MoreParametersThan ) )
LogConsole : : abortEvaluation ( hex : : format ( " too few parameters for function '{0}'. Expected {1} " , this - > m_functionName , function . parameterCount & ~ ContentRegistry : : PatternLanguageFunctions : : MoreParametersThan ) , this ) ;
} else if ( function . parameterCount ! = evaluatedParams . size ( ) ) {
LogConsole : : abortEvaluation ( hex : : format ( " invalid number of parameters for function '{0}'. Expected {1} " , this - > m_functionName , function . parameterCount ) , this ) ;
}
2021-01-09 21:47:11 +01:00
2021-09-21 21:29:18 +02:00
try {
auto result = functions [ this - > m_functionName ] . func ( evaluator , evaluatedParams ) ;
2021-01-21 17:49:30 +01:00
2021-09-21 21:29:18 +02:00
if ( result . has_value ( ) )
return new ASTNodeLiteral ( result . value ( ) ) ;
else
return new ASTNodeMathematicalExpression ( nullptr , nullptr , Token : : Operator : : Plus ) ;
} catch ( std : : string & error ) {
LogConsole : : abortEvaluation ( error , this ) ;
}
2021-01-21 17:49:30 +01:00
2021-09-21 21:29:18 +02:00
return nullptr ;
2021-01-21 17:49:30 +01:00
}
2021-11-27 12:57:59 +01:00
FunctionResult execute ( Evaluator * evaluator ) const override {
2021-09-21 21:29:18 +02:00
delete this - > evaluate ( evaluator ) ;
2021-01-21 17:49:30 +01:00
2021-09-21 21:29:18 +02:00
return { false , { } } ;
2021-01-21 17:49:30 +01:00
}
private :
2021-09-21 21:29:18 +02:00
std : : string m_functionName ;
std : : vector < ASTNode * > m_params ;
2021-01-21 17:49:30 +01:00
} ;
2021-01-07 15:37:37 +01:00
2021-04-21 10:17:42 +02:00
class ASTNodeTypeOperator : public ASTNode {
public :
ASTNodeTypeOperator ( Token : : Operator op , ASTNode * expression ) : m_op ( op ) , m_expression ( expression ) {
}
ASTNodeTypeOperator ( const ASTNodeTypeOperator & other ) : ASTNode ( other ) {
this - > m_op = other . m_op ;
this - > m_expression = other . m_expression - > clone ( ) ;
}
[[nodiscard]] ASTNode * clone ( ) const override {
return new ASTNodeTypeOperator ( * this ) ;
}
~ ASTNodeTypeOperator ( ) override {
delete this - > m_expression ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]]
2021-04-21 10:17:42 +02:00
Token : : Operator getOperator ( ) const {
return this - > m_op ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]]
2021-04-21 10:17:42 +02:00
ASTNode * getExpression ( ) const {
return this - > m_expression ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]]
ASTNode * evaluate ( Evaluator * evaluator ) const override {
auto pattern = this - > m_expression - > createPatterns ( evaluator ) . front ( ) ;
ON_SCOPE_EXIT { delete pattern ; } ;
2021-06-20 21:22:31 +02:00
2021-09-21 21:29:18 +02:00
switch ( this - > getOperator ( ) ) {
case Token : : Operator : : AddressOf :
return new ASTNodeLiteral ( u128 ( pattern - > getOffset ( ) ) ) ;
case Token : : Operator : : SizeOf :
return new ASTNodeLiteral ( u128 ( pattern - > getSize ( ) ) ) ;
default :
LogConsole : : abortEvaluation ( " invalid type operator " , this ) ;
2021-06-20 21:22:31 +02:00
}
}
private :
2021-09-21 21:29:18 +02:00
Token : : Operator m_op ;
ASTNode * m_expression ;
2021-06-20 21:22:31 +02:00
} ;
2021-09-21 21:29:18 +02:00
2021-06-20 21:22:31 +02:00
class ASTNodeAssignment : public ASTNode {
public :
ASTNodeAssignment ( std : : string lvalueName , ASTNode * rvalue ) : m_lvalueName ( std : : move ( lvalueName ) ) , m_rvalue ( rvalue ) {
}
ASTNodeAssignment ( const ASTNodeAssignment & other ) : ASTNode ( other ) {
this - > m_lvalueName = other . m_lvalueName ;
this - > m_rvalue = other . m_rvalue - > clone ( ) ;
}
[[nodiscard]] ASTNode * clone ( ) const override {
return new ASTNodeAssignment ( * this ) ;
}
~ ASTNodeAssignment ( ) override {
delete this - > m_rvalue ;
}
2021-09-08 15:18:24 +02:00
[[nodiscard]] const std : : string & getLValueName ( ) const {
2021-06-20 21:22:31 +02:00
return this - > m_lvalueName ;
}
[[nodiscard]] ASTNode * getRValue ( ) const {
return this - > m_rvalue ;
}
2021-11-27 12:57:59 +01:00
FunctionResult execute ( Evaluator * evaluator ) const override {
2021-09-21 21:29:18 +02:00
auto literal = dynamic_cast < ASTNodeLiteral * > ( this - > getRValue ( ) - > evaluate ( evaluator ) ) ;
ON_SCOPE_EXIT { delete literal ; } ;
evaluator - > setVariable ( this - > getLValueName ( ) , literal - > getValue ( ) ) ;
return { false , { } } ;
}
2021-06-20 21:22:31 +02:00
private :
std : : string m_lvalueName ;
ASTNode * m_rvalue ;
} ;
class ASTNodeReturnStatement : public ASTNode {
public :
2021-09-21 21:29:18 +02:00
explicit ASTNodeReturnStatement ( ASTNode * rvalue ) : m_rvalue ( rvalue ) {
2021-06-20 21:22:31 +02:00
}
ASTNodeReturnStatement ( const ASTNodeReturnStatement & other ) : ASTNode ( other ) {
this - > m_rvalue = other . m_rvalue - > clone ( ) ;
}
[[nodiscard]] ASTNode * clone ( ) const override {
return new ASTNodeReturnStatement ( * this ) ;
}
~ ASTNodeReturnStatement ( ) override {
delete this - > m_rvalue ;
}
2021-09-21 21:29:18 +02:00
[[nodiscard]] ASTNode * getReturnValue ( ) const {
2021-06-20 21:22:31 +02:00
return this - > m_rvalue ;
}
2021-11-27 12:57:59 +01:00
FunctionResult execute ( Evaluator * evaluator ) const override {
2021-09-21 21:29:18 +02:00
auto returnValue = this - > getReturnValue ( ) ;
if ( returnValue = = nullptr )
return { true , std : : nullopt } ;
else {
auto literal = dynamic_cast < ASTNodeLiteral * > ( returnValue - > evaluate ( evaluator ) ) ;
ON_SCOPE_EXIT { delete literal ; } ;
return { true , literal - > getValue ( ) } ;
}
}
2021-06-20 21:22:31 +02:00
private :
ASTNode * m_rvalue ;
} ;
2021-09-21 21:29:18 +02:00
class ASTNodeFunctionDefinition : public ASTNode {
public :
2021-09-24 11:34:06 +02:00
ASTNodeFunctionDefinition ( std : : string name , std : : vector < std : : pair < std : : string , ASTNode * > > params , std : : vector < ASTNode * > body )
2021-09-21 21:29:18 +02:00
: m_name ( std : : move ( name ) ) , m_params ( std : : move ( params ) ) , m_body ( std : : move ( body ) ) {
}
ASTNodeFunctionDefinition ( const ASTNodeFunctionDefinition & other ) : ASTNode ( other ) {
this - > m_name = other . m_name ;
this - > m_params = other . m_params ;
for ( const auto & [ name , type ] : other . m_params ) {
2021-09-24 11:34:06 +02:00
this - > m_params . emplace_back ( name , type - > clone ( ) ) ;
2021-09-21 21:29:18 +02:00
}
for ( auto statement : other . m_body ) {
this - > m_body . push_back ( statement - > clone ( ) ) ;
}
}
[[nodiscard]] ASTNode * clone ( ) const override {
return new ASTNodeFunctionDefinition ( * this ) ;
}
~ ASTNodeFunctionDefinition ( ) override {
for ( auto & [ name , type ] : this - > m_params )
delete type ;
for ( auto statement : this - > m_body )
delete statement ;
}
[[nodiscard]] const std : : string & getName ( ) const {
return this - > m_name ;
}
[[nodiscard]] const auto & getParams ( ) const {
return this - > m_params ;
}
[[nodiscard]] const auto & getBody ( ) const {
return this - > m_body ;
}
[[nodiscard]] ASTNode * evaluate ( Evaluator * evaluator ) const override {
evaluator - > addCustomFunction ( this - > m_name , this - > m_params . size ( ) , [ this ] ( Evaluator * ctx , const std : : vector < Token : : Literal > & params ) - > std : : optional < Token : : Literal > {
std : : vector < PatternData * > variables ;
ctx - > pushScope ( nullptr , variables ) ;
2021-10-02 15:22:38 +02:00
ON_SCOPE_EXIT {
for ( auto variable : variables )
delete variable ;
ctx - > popScope ( ) ;
} ;
2021-09-21 21:29:18 +02:00
u32 paramIndex = 0 ;
for ( const auto & [ name , type ] : this - > m_params ) {
2021-09-23 23:43:16 +02:00
ctx - > createVariable ( name , type , params [ paramIndex ] ) ;
2021-09-21 21:29:18 +02:00
ctx - > setVariable ( name , params [ paramIndex ] ) ;
paramIndex + + ;
}
for ( auto statement : this - > m_body ) {
auto [ executionStopped , result ] = statement - > execute ( ctx ) ;
if ( executionStopped ) {
return result ;
}
}
return { } ;
} ) ;
return nullptr ;
}
private :
std : : string m_name ;
2021-09-24 11:34:06 +02:00
std : : vector < std : : pair < std : : string , ASTNode * > > m_params ;
2021-09-21 21:29:18 +02:00
std : : vector < ASTNode * > m_body ;
} ;
2021-10-10 13:05:32 +02:00
class ASTNodeCompoundStatement : public ASTNode {
public :
2021-10-10 13:47:48 +02:00
ASTNodeCompoundStatement ( std : : vector < ASTNode * > statements , bool newScope = false ) : m_statements ( std : : move ( statements ) ) , m_newScope ( newScope ) {
2021-10-10 13:05:32 +02:00
}
ASTNodeCompoundStatement ( const ASTNodeCompoundStatement & other ) : ASTNode ( other ) {
for ( const auto & statement : other . m_statements ) {
this - > m_statements . push_back ( statement - > clone ( ) ) ;
}
}
[[nodiscard]] ASTNode * clone ( ) const override {
return new ASTNodeCompoundStatement ( * this ) ;
}
~ ASTNodeCompoundStatement ( ) override {
for ( const auto & statement : this - > m_statements ) {
delete statement ;
}
}
[[nodiscard]] ASTNode * evaluate ( Evaluator * evaluator ) const override {
ASTNode * result = nullptr ;
for ( const auto & statement : this - > m_statements ) {
delete result ;
result = statement - > evaluate ( evaluator ) ;
}
return result ;
}
[[nodiscard]] std : : vector < PatternData * > createPatterns ( Evaluator * evaluator ) const override {
std : : vector < PatternData * > result ;
for ( const auto & statement : this - > m_statements ) {
auto patterns = statement - > createPatterns ( evaluator ) ;
std : : copy ( patterns . begin ( ) , patterns . end ( ) , std : : back_inserter ( result ) ) ;
}
return result ;
}
2021-11-27 12:57:59 +01:00
FunctionResult execute ( Evaluator * evaluator ) const override {
2021-10-10 13:05:32 +02:00
FunctionResult result ;
2021-10-10 13:47:48 +02:00
auto variables = * evaluator - > getScope ( 0 ) . scope ;
u32 startVariableCount = variables . size ( ) ;
if ( this - > m_newScope ) {
evaluator - > pushScope ( nullptr , variables ) ;
}
2021-10-10 13:05:32 +02:00
for ( const auto & statement : this - > m_statements ) {
result = statement - > execute ( evaluator ) ;
if ( result . first )
return result ;
}
2021-10-10 13:47:48 +02:00
if ( this - > m_newScope ) {
s64 stackSize = evaluator - > getStack ( ) . size ( ) ;
for ( u32 i = startVariableCount ; i < variables . size ( ) ; i + + ) {
stackSize - - ;
delete variables [ i ] ;
}
if ( stackSize < 0 ) LogConsole : : abortEvaluation ( " stack pointer underflow! " , this ) ;
evaluator - > getStack ( ) . resize ( stackSize ) ;
evaluator - > popScope ( ) ;
}
2021-10-10 13:05:32 +02:00
return result ;
}
public :
std : : vector < ASTNode * > m_statements ;
2021-10-10 13:47:48 +02:00
bool m_newScope ;
2021-10-10 13:05:32 +02:00
} ;
} ;