404 lines
7.5 KiB
C++
404 lines
7.5 KiB
C++
#ifndef AST_NODE_H
|
|
#define AST_NODE_H
|
|
|
|
#include "token.h"
|
|
#include <optional>
|
|
#include <vector>
|
|
|
|
/**
|
|
* 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
|
|
};
|
|
|
|
|
|
private:
|
|
ValueType type;
|
|
std::optional<long long> intValue;
|
|
std::optional<std::string> stringValue;
|
|
std::optional<bool> boolValue;
|
|
std::optional<std::string> 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<bool>(_value);
|
|
return value;
|
|
}
|
|
|
|
static ValueNode ofInt(long long _value) {
|
|
ValueNode value;
|
|
value.type = INT;
|
|
value.intValue = std::optional<long long>(_value);
|
|
return value;
|
|
}
|
|
|
|
static ValueNode ofString(std::string _value) {
|
|
ValueNode value;
|
|
value.type = STRING;
|
|
value.stringValue = std::optional<std::string>(_value);
|
|
return value;
|
|
}
|
|
|
|
static ValueNode ofIdentifier(std::string _value) {
|
|
ValueNode value;
|
|
value.type = IDENTIFIER;
|
|
value.identifierValue = std::optional<std::string>(_value);
|
|
return value;
|
|
}
|
|
|
|
static ValueNode ofWire(std::string _value) {
|
|
ValueNode value;
|
|
value.type = WIRE;
|
|
value.identifierValue = std::optional<std::string>(_value);
|
|
return value;
|
|
}
|
|
};
|
|
|
|
struct ConditionNode
|
|
{
|
|
bool negated;
|
|
IdentifierNode functionName;
|
|
std::vector<ValueNode> 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<IfStatementNode> statements;
|
|
};
|
|
|
|
|
|
|
|
struct EnumerationNode: AstNode
|
|
{
|
|
StringNode key;
|
|
ValueNode value;
|
|
};
|
|
|
|
struct PopupNode: AstNode
|
|
{
|
|
enum PopupType {
|
|
AUTOMATIC,
|
|
ON_DEMAND
|
|
};
|
|
|
|
std::optional<PopupType> type;
|
|
std::optional<StringNode> title;
|
|
std::optional<StringNode> text;
|
|
|
|
bool enumerated;
|
|
std::vector<EnumerationNode> enumeration;
|
|
|
|
std::vector<RuleNode> rules;
|
|
};
|
|
|
|
struct PropertyNode: public AstNode
|
|
{
|
|
IdentifierNode key;
|
|
ValueNode value;
|
|
};
|
|
|
|
|
|
struct DisplayItemNode: AstNode
|
|
{
|
|
IdentifierNode type;
|
|
std::vector<PropertyNode> values;
|
|
};
|
|
|
|
|
|
struct DisplayNode: AstNode
|
|
{
|
|
std::vector<DisplayItemNode> 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<StringNode> tooltip;
|
|
std::optional<PinConnectionNode> connection;
|
|
std::optional<DisplayNode> 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<ValueNode> defaultValue;
|
|
std::optional<PopupNode> popup;
|
|
};
|
|
|
|
struct ConnectionNode: AstNode
|
|
{
|
|
IdentifierNode component;
|
|
IdentifierNode pin;
|
|
IdentifierNode bus;
|
|
std::vector<AttributeNode> attributes;
|
|
std::vector<IdentifierNode> wires;
|
|
};
|
|
|
|
|
|
struct ComponentNode: AstNode
|
|
{
|
|
enum ComponentType {
|
|
OTHER,
|
|
PROCESSOR,
|
|
MEMORY
|
|
};
|
|
|
|
IdentifierNode name;
|
|
std::optional<StringNode> tooltip;
|
|
std::optional<StringNode> source;
|
|
ComponentType type;
|
|
std::vector<RuleNode> rules;
|
|
std::optional<StringNode> instanceName;
|
|
std::optional<CountNode> count;
|
|
std::optional<DisplayNode> display;
|
|
std::vector<PinNode> pins;
|
|
std::vector<AttributeNode> attributes;
|
|
};
|
|
|
|
|
|
struct BusNode: AstNode
|
|
{
|
|
enum BusType {
|
|
AUTOMATIC,
|
|
REGULAR
|
|
};
|
|
|
|
BusType type;
|
|
IdentifierNode name;
|
|
std::optional<StringNode> tooltip;
|
|
std::optional<CountNode> count;
|
|
std::optional<DisplayNode> display;
|
|
|
|
std::vector<WireNode> wires;
|
|
};
|
|
|
|
struct LibraryNode: AstNode
|
|
{
|
|
std::optional<StringNode> name;
|
|
std::optional<StringNode> libraryInfo;
|
|
std::optional<StringNode> header;
|
|
std::optional<StringNode> componentDirectory;
|
|
|
|
std::vector<AddressSpaceNode> addressSpaces;
|
|
|
|
std::vector<ComponentNode> components;
|
|
std::vector<BusNode> buses;
|
|
std::vector<ConnectionNode> connections;
|
|
|
|
std::vector<PropertyNode> messages;
|
|
};
|
|
|
|
// SCHEMA models
|
|
|
|
|
|
struct WireInstanceNode: AstNode
|
|
{
|
|
IdentifierNode name;
|
|
std::optional<CountNode> position;
|
|
std::optional<DisplayNode> display;
|
|
};
|
|
|
|
struct InstanceAttributeNode: AstNode
|
|
{
|
|
IdentifierNode name;
|
|
ValueNode value;
|
|
};
|
|
|
|
struct InstanceNode: AstNode
|
|
{
|
|
IdentifierNode name;
|
|
IdentifierNode component;
|
|
|
|
std::optional<CountNode> position;
|
|
std::vector<InstanceAttributeNode> attributes;
|
|
|
|
std::optional<NumberNode> size;
|
|
};
|
|
|
|
|
|
struct ConnectionInstanceNode: AstNode
|
|
{
|
|
IdentifierNode instance;
|
|
IdentifierNode pin;
|
|
IdentifierNode bus;
|
|
std::optional<IdentifierNode> wire;
|
|
|
|
std::vector<InstanceAttributeNode> attributes;
|
|
};
|
|
|
|
|
|
struct SchemaNode: AstNode
|
|
{
|
|
std::optional<StringNode> source;
|
|
|
|
std::vector<InstanceNode> instances;
|
|
std::vector<WireInstanceNode> wires;
|
|
std::vector<ConnectionInstanceNode> connections;
|
|
|
|
std::optional<LibraryNode> library;
|
|
};
|
|
|
|
#endif // AST_NODE_H
|