diff --git a/src/Lib/Script/Ast/IrExpression.cc b/src/Lib/Script/Ast/IrExpression.cc index 35979377b7e9bf07aa71d7bda7abcef045ce7dcf..63e95cc233282a2855dc1f8812156e3c7a9deff2 100644 --- a/src/Lib/Script/Ast/IrExpression.cc +++ b/src/Lib/Script/Ast/IrExpression.cc @@ -13,6 +13,15 @@ IrExpression::IrExpression(IrElement *p, Type type) noexcept { } + void IrExpression::setInnerType(IrType *type) + { + if (selfInnerType != nullptr) { + throw std::logic_error("IrExpression: try to set the inner type multiple times"); + } + selfInnerType = type; + selfInnerType->setParent(this); + } + std::string IrExpression::toString() const noexcept { @@ -34,6 +43,13 @@ IrExpression::parse(std::vector<Token> *) throw std::logic_error("Not implemented"); } +void IrExpression::assertType(Type t) const +{ + if (type() != t) { + throw std::runtime_error("Expected type " + std::to_string(static_cast<int>(t)) + " but was type " + std::to_string(static_cast<int>(type()))); + } +} + IrExpression::Type IrExpression::type() const noexcept { @@ -75,17 +91,20 @@ IrEConstExpr::IrEConstExpr(const Token &singleElement) case Token::Type::INTEGER: case Token::Type::FLOATING: case Token::Type::COLORLIT: - case Token::Type::STRINGLIT: + case Token::Type::STRINGLIT: { + throw std::logic_error("IrEConstExpr: not implemented " + singleElement.toString()); + } /* Only handle true or false */ case Token::Type::SIMPLE: { if (singleElement.isSimple(TOKEN_FALSE)) { - selfInnerType = IrElement::create<IrTPrimitive>(this, IrType::PrimitiveType::Bool); + setInnerType(IrElement::create<IrTPrimitive>(this, IrType::PrimitiveType::Bool)); } else if (singleElement.isSimple(TOKEN_TRUE)) { - selfInnerType = IrElement::create<IrTPrimitive>(this, IrType::PrimitiveType::Bool); + setInnerType(IrElement::create<IrTPrimitive>(this, IrType::PrimitiveType::Bool)); } else { throw std::logic_error("IrEConstExpr unexpected simple token: " + singleElement.toString() + ", expected `true` or `false`"); } + return; } case Token::Type::QNAME: @@ -95,38 +114,38 @@ IrEConstExpr::IrEConstExpr(const Token &singleElement) } } -IrTPrimitive *IrTPrimitive::innerType() const noexcept +IrTPrimitive *IrEConstExpr::innerType() const noexcept { - return dynamic_cast<IrTPrimitive*>(IrType::innerType()); + return dynamic_cast<IrTPrimitive*>(IrExpression::innerType()); } bool IrEConstExpr::getInnerBoolean() const { - selfInnerType->assertType(IrType::PrimitiveType::Bool); + innerType()->assertInnerType(IrType::PrimitiveType::Bool); return inner.boolean; } int IrEConstExpr::getInnerInteger() const { - selfInnerType->assertType(IrType::PrimitiveType::Integer); + innerType()->assertInnerType(IrType::PrimitiveType::Int); return inner.integer; } float IrEConstExpr::getInnerFloating() const { - selfInnerType->assertType(IrType::PrimitiveType::Floating); + innerType()->assertInnerType(IrType::PrimitiveType::Float); return inner.floating; } StrV IrEConstExpr::getInnerStringLit() const { - selfInnerType->assertType(IrType::PrimitiveType::String); + innerType()->assertInnerType(IrType::PrimitiveType::String); return inner.string; } StrV IrEConstExpr::getInnerColorLit() const { - selfInnerType->assertType(IrType::PrimitiveType::Color); + innerType()->assertInnerType(IrType::PrimitiveType::Color); return inner.string; } @@ -134,18 +153,18 @@ std::string IrEConstExpr::toString() const noexcept { switch (innerType()->innerType()) { - case IrType::PrimitiveType::Color: return inner.string.toStdStrng(); - case IrType::PrimitiveType::String: return inner.string.toStdStrng(); - case IrType::PrimitiveType::Integer: return std::to_string(inner.integer); - case IrType::PrimitiveType::Floating: return std::to_string(inner.floating); + case IrType::PrimitiveType::Color: return inner.string.toStdString(); + case IrType::PrimitiveType::String: return inner.string.toStdString(); + case IrType::PrimitiveType::Int: return std::to_string(inner.integer); + case IrType::PrimitiveType::Float: return std::to_string(inner.floating); case IrType::PrimitiveType::Bool: return inner.boolean ? std::string("true") : std::string("false"); } } void -IrEConstExpr::parse(std::vector<Token> *tokens) +IrEConstExpr::parse(std::vector<Token> *) { - throw std::logic_error("Not implemented"); + throw std::logic_error("IrEConstExpr::parse Not implemented"); } } diff --git a/src/Lib/Script/Ast/IrExpression.hh b/src/Lib/Script/Ast/IrExpression.hh index 42c151bde7d7222b74f3533f7e252a25b5263c51..ff66f4338cd0d454aa60b36100c56e0ab47d50be 100644 --- a/src/Lib/Script/Ast/IrExpression.hh +++ b/src/Lib/Script/Ast/IrExpression.hh @@ -1,6 +1,8 @@ #pragma once #include "IrElement.hh" +#include "IrType.hh" +#include "Lib/Script/FrontEnd/StrV.hh" namespace Vivy::Script { @@ -17,6 +19,9 @@ private: protected: IrExpression(IrElement *p, Type) noexcept; + void setInnerType(IrType *); + void assertType(Type) const; + public: std::string toString() const noexcept override; void parse(std::vector<Token> *) override; @@ -36,13 +41,13 @@ class IrEConstExpr : public IrExpression { float floating; /* StringLit + ColorLit */ - StrV string; + StrV string = STRV_NULL; } inner; public: std::string toString() const noexcept override; void parse(std::vector<Token> *) override; - IrTPrimitive *innerType() const override noexcept; + virtual IrTPrimitive *innerType() const noexcept override; bool getInnerBoolean() const; int getInnerInteger() const; diff --git a/src/Lib/Script/Ast/IrType.cc b/src/Lib/Script/Ast/IrType.cc index e95b265ee47ac6b7c92fdcf7afc7a09ae09bc2f5..fc45e61ec1e8b58775e1d75d2f35097bb32e07f2 100644 --- a/src/Lib/Script/Ast/IrType.cc +++ b/src/Lib/Script/Ast/IrType.cc @@ -1,6 +1,7 @@ #include "IrType.hh" #include "IrElement.hh" #include "IrVariable.hh" +#include "Lib/Script/FrontEnd/Lexer.cc" namespace Vivy::Script { @@ -8,9 +9,15 @@ void IrType::assertType(Type t) const { if (type() != t) { - throw std::runtime_error("Type differs from asked type, this is " + std::to_string(type()) + " and asked " + std::to_string(t)); + throw std::runtime_error( + "Type differs from asked type, this is " + + std::to_string(static_cast<int>(type())) + + " and asked " + std::to_string(static_cast<int>(t)) + ); } } + +IrType::~IrType() noexcept {} } /* @@ -118,7 +125,15 @@ IrTPrimitive::setSelfInnerTypeFromToken(const Token &name) IrTPrimitive::IrTPrimitive(const Token &name) { - setSelfInnerTypeFromToken(name) + setSelfInnerTypeFromToken(name); +} + +void +IrTPrimitive::assertInnerType(PrimitiveType t) const +{ + if (innerType() != t) { + throw std::runtime_error("Expected inner type " + std::to_string(static_cast<int>(t)) + " but was type " + std::to_string(static_cast<int>(innerType()))); + } } IrType::Type @@ -137,7 +152,7 @@ unsigned int IrTPrimitive::innerTypeCount() const noexcept { /* 0 is same as 1, it's not an array! */ - return selfArraySize <= 1 : 1 : selfArraySize; + return selfArraySize <= 1 ? 1 : selfArraySize; } std::string @@ -159,11 +174,11 @@ IrTPrimitive::parse(std::vector<Token> *tokens) if (tokens->size() == 0) { throw std::runtime_error("Expected at least one token to parse an IrTPrimitive"); } else if (tokens->size() == 1) { - setSelfInnerTypeFromToken(getInnerTokenOpt(tokenListPop(tokens))) + setSelfInnerTypeFromToken(getInnerTokenOpt(tokenListPop(tokens))); } else { const Token primToken = getInnerTokenOpt(tokenListPop(tokens)); setSelfInnerTypeFromToken(primToken); - std::vector<Token> sizeTokens tokenListPopToNextSimpleToken(tokens, TOKEN_BRACKET_RIGHT); + std::vector<Token> sizeTokens = tokenListPopToNextSimpleToken(tokens, TOKEN_BRACKET_RIGHT); if (tokens->size()) { throw std::runtime_error(getInnerTokenOpt(tokenListPeek(tokens)).location().toString() ": Remaining tokens for the array dimensions of the type, this is invalid. To declare an array, use `TYPE_NAME[dim1, dim2, ...]`"); diff --git a/src/Lib/Script/Ast/IrType.hh b/src/Lib/Script/Ast/IrType.hh index c2d537a0e051ae1f5cbabe1e22a96842832d9500..f3b809413c392b556c8c2ba45d4bf5863c1b918a 100644 --- a/src/Lib/Script/Ast/IrType.hh +++ b/src/Lib/Script/Ast/IrType.hh @@ -13,7 +13,8 @@ public: enum struct AssType { Line, Syllabe }; enum struct PrimitiveType { Int, Float, Bool, Color, String }; -public: + virtual ~IrType() noexcept override; + virtual Type type() const noexcept = 0; void assertType(Type) const; }; @@ -57,13 +58,15 @@ class IrTPrimitive final : public IrType { IrTPrimitive(const PrimitiveType) noexcept; IrTPrimitive(const PrimitiveType, unsigned int) noexcept; - void IrTPrimitive::setSelfInnerTypeFromToken(const Token &name); + void setSelfInnerTypeFromToken(const Token &name); public: Type type() const noexcept override; PrimitiveType innerType() const noexcept; unsigned int innerTypeCount() const noexcept; + void assertInnerType(PrimitiveType) const; + std::string toString() const noexcept override; void parse(std::vector<Token> *) override; };