#ifndef AST_NODE_H #define AST_NODE_H #include "token.h" #include #include /** * AST base class, all AST node classes extend this class. Class contains basic * information about nodes location in file. */ class AstNode { public: Span span; AstNode() = default; virtual ~AstNode(); // this is defined in Ast.cpp just so that the // compiler doesn't complain about not knowing which // object file to include the vtable in AstNode(AstNode&&) = default; AstNode& operator=(AstNode&&) = default; AstNode(const AstNode&) = default; AstNode& operator=(const AstNode&) = default; }; struct StringNode: public AstNode { std::string value; std::string asString() { return value.substr(1, value.length() - 2); } }; struct IdentifierNode: public AstNode { std::string value; }; struct NumberNode: public AstNode { long long int value; NumberNode(std::string expression); NumberNode(): value(0) {} }; struct CountNode: public AstNode { NumberNode first; NumberNode second; CountNode(NumberNode first, NumberNode second): first(first), second(second) {} CountNode() {} }; struct AddressSpaceNode: public AstNode { IdentifierNode name; NumberNode start; NumberNode end; }; class ValueNode: public AstNode { public: enum ValueType { INT, STRING, BOOL, WIRE, IDENTIFIER, NIL, }; private: ValueType type; std::optional intValue; std::optional stringValue; std::optional boolValue; std::optional identifierValue; public: ValueNode() {}; ValueType getType() { return type; } long long asInt() { if(is(INT)) { return intValue.value(); } throw "cannot convert type to int"; } std::string asString() { if(is(STRING)) { return stringValue.value(); } throw "cannot convert type to string"; } std::string asIdentifier() { if(is(IDENTIFIER) || is(WIRE)) { return identifierValue.value(); } throw "cannot convert type to identifier"; } bool asBool() { if(is(BOOL)) { return boolValue.value(); } throw "cannot convert type to bool"; } bool is(ValueType type) { return this->type == type; } static ValueNode ofBool(bool _value) { ValueNode value; value.type = BOOL; value.boolValue = std::optional(_value); return value; } static ValueNode ofInt(long long _value) { ValueNode value; value.type = INT; value.intValue = std::optional(_value); return value; } static ValueNode ofString(std::string _value) { ValueNode value; value.type = STRING; value.stringValue = std::optional(_value); return value; } static ValueNode ofIdentifier(std::string _value) { ValueNode value; value.type = IDENTIFIER; value.identifierValue = std::optional(_value); return value; } static ValueNode ofNull() { ValueNode value; value.type = NIL; return value; } static ValueNode ofWire(std::string _value) { ValueNode value; value.type = WIRE; value.identifierValue = std::optional(_value); return value; } }; struct ConditionNode { bool negated; IdentifierNode functionName; std::vector params; }; class ActionNode: AstNode { public: enum ActionType { ERROR, WARNING }; ActionType type; StringNode message; }; struct IfStatementNode: AstNode { ConditionNode condition; ActionNode action; }; struct RuleNode: AstNode { std::vector statements; }; struct EnumerationNode: AstNode { StringNode key; ValueNode value; }; struct PopupNode: AstNode { enum PopupType { AUTOMATIC, ON_DEMAND }; std::optional type; std::optional title; std::optional text; bool enumerated; std::vector enumeration; std::vector rules; }; struct PropertyNode: public AstNode { IdentifierNode key; ValueNode value; }; struct DisplayItemNode: AstNode { IdentifierNode type; std::vector values; }; struct DisplayNode: AstNode { std::vector items; }; struct PinConnectionNode: AstNode { enum ConnectionType { CHECK_ONLY, AUTOMATICALLY }; StringNode message; ConnectionType type; }; struct PinNode: AstNode { enum PinType { IN_OUT, IN, OUT }; IdentifierNode name; PinType type; std::optional tooltip; std::optional connection; std::optional display; }; struct WireNode: public AstNode { enum WireType { WIRE, WIRED_AND, WIRED_OR, R_WIRE }; WireType type; IdentifierNode name; NumberNode size; bool hidden; bool hasTermination; long long isUnterminated; }; struct AttributeNode: AstNode { ValueNode::ValueType type; IdentifierNode name; std::optional defaultValue; std::optional popup; }; struct ConnectionNode: AstNode { IdentifierNode component; IdentifierNode pin; IdentifierNode bus; std::vector attributes; std::vector wires; }; struct ComponentNode: AstNode { enum ComponentType { OTHER, PROCESSOR, MEMORY }; IdentifierNode name; std::optional tooltip; std::optional source; ComponentType type; std::vector rules; std::optional instanceName; std::optional count; std::optional display; std::vector pins; std::vector attributes; }; struct BusNode: AstNode { enum BusType { AUTOMATIC, REGULAR }; BusType type; IdentifierNode name; std::optional tooltip; std::optional count; std::optional display; std::vector wires; }; struct LibraryNode: AstNode { std::optional name; std::optional libraryInfo; std::optional header; std::optional componentDirectory; std::vector addressSpaces; std::vector components; std::vector buses; std::vector connections; std::vector messages; }; // SCHEMA models struct WireInstanceNode: AstNode { IdentifierNode name; std::optional position; std::optional display; }; struct InstanceAttributeNode: AstNode { IdentifierNode name; ValueNode value; }; struct InstanceNode: AstNode { IdentifierNode name; IdentifierNode component; std::optional position; std::vector attributes; std::optional size; }; struct ConnectionInstanceNode: AstNode { IdentifierNode instance; IdentifierNode pin; IdentifierNode bus; std::optional wire; std::vector attributes; }; struct SchemaNode: AstNode { std::optional source; std::vector instances; std::vector wires; std::vector connections; std::optional library; }; #endif // AST_NODE_H