Move types to it's own file
This commit is contained in:
parent
ed51ee61ed
commit
ea9bb1fcb9
@ -15,7 +15,7 @@ separate_arguments(LLVM_DEFINITIONS_LIST NATIVE_COMMAND ${LLVM_DEFINITIONS})
|
||||
add_definitions(${LLVM_DEFINITIONS_LIST})
|
||||
|
||||
# Executable
|
||||
add_executable(${PROJECT_NAME} src/main.cpp src/tokens.cpp src/parsing.cpp src/ast.cpp src/codegen.cpp)
|
||||
add_executable(${PROJECT_NAME} src/main.cpp src/tokens.cpp src/parsing.cpp src/ast.cpp src/codegen.cpp src/types.cpp)
|
||||
target_compile_features(${PROJECT_NAME} PRIVATE cxx_std_20)
|
||||
|
||||
# Find the libraries that correspond to the LLVM components
|
||||
|
||||
10
src/ast.cpp
10
src/ast.cpp
@ -81,14 +81,4 @@ namespace AST {
|
||||
out << "}";
|
||||
return out.str();
|
||||
}
|
||||
|
||||
std::string FundamentalType::formatted() {
|
||||
switch (this->m_ty) {
|
||||
case FundamentalTypeKind::Int:
|
||||
return "Int";
|
||||
default:
|
||||
return "Unknown";
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
34
src/ast.h
34
src/ast.h
@ -2,6 +2,7 @@
|
||||
#define AST_H
|
||||
|
||||
#include "codegen.h"
|
||||
#include "types.h"
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
@ -27,13 +28,6 @@ namespace AST {
|
||||
virtual codegen::StackValue codegen(codegen::Builder& builder, codegen::Scope& scope) = 0;
|
||||
};
|
||||
|
||||
class Type {
|
||||
public:
|
||||
virtual ~Type() = default;
|
||||
virtual std::string formatted() = 0;
|
||||
virtual llvm::Type* codegen(codegen::Builder& builder, codegen::Scope& scope) = 0;
|
||||
};
|
||||
|
||||
class Statement : public Node {
|
||||
public:
|
||||
virtual void codegen(codegen::Builder& builder, codegen::Scope& scope) = 0;
|
||||
@ -86,11 +80,11 @@ namespace AST {
|
||||
|
||||
class InitializationStatement : public Statement {
|
||||
private:
|
||||
std::unique_ptr<Type> m_type;
|
||||
std::unique_ptr<types::Type> m_type;
|
||||
std::string m_name;
|
||||
std::optional<std::unique_ptr<Expression>> m_expr;
|
||||
public:
|
||||
InitializationStatement(std::unique_ptr<Type> ty, std::string name, std::optional<std::unique_ptr<Expression>> expr)
|
||||
InitializationStatement(std::unique_ptr<types::Type> ty, std::string name, std::optional<std::unique_ptr<Expression>> expr)
|
||||
: m_type{ std::move(ty) }, m_name{ name }, m_expr{ std::move(expr) } {
|
||||
}
|
||||
virtual ~InitializationStatement() override = default;
|
||||
@ -117,14 +111,14 @@ namespace AST {
|
||||
|
||||
class Function : public TopLevelStatement {
|
||||
private:
|
||||
std::unique_ptr<Type> m_return_ty;
|
||||
std::vector<std::pair<std::string, std::unique_ptr<Type>>> m_params;
|
||||
std::unique_ptr<types::Type> m_return_ty;
|
||||
std::vector<std::pair<std::string, std::unique_ptr<types::Type>>> m_params;
|
||||
std::string m_name;
|
||||
std::vector<std::unique_ptr<Statement>> m_statements;
|
||||
public:
|
||||
Function(
|
||||
std::unique_ptr<Type> return_ty,
|
||||
std::vector<std::pair<std::string, std::unique_ptr<Type>>> params,
|
||||
std::unique_ptr<types::Type> return_ty,
|
||||
std::vector<std::pair<std::string, std::unique_ptr<types::Type>>> params,
|
||||
std::string name,
|
||||
std::vector<std::unique_ptr<Statement>> statements)
|
||||
: m_return_ty{ std::move(return_ty) }
|
||||
@ -136,20 +130,6 @@ namespace AST {
|
||||
virtual std::string formatted() override;
|
||||
virtual void codegen(codegen::Builder& builder, codegen::Scope& scope) override;
|
||||
};
|
||||
|
||||
enum class FundamentalTypeKind {
|
||||
Int,
|
||||
};
|
||||
|
||||
class FundamentalType : public Type {
|
||||
private:
|
||||
FundamentalTypeKind m_ty;
|
||||
public:
|
||||
FundamentalType(FundamentalTypeKind kind) : m_ty{ kind } {}
|
||||
virtual ~FundamentalType() override = default;
|
||||
virtual std::string formatted() override;
|
||||
virtual llvm::Type* codegen(codegen::Builder& builder, codegen::Scope& scope) override;
|
||||
};
|
||||
}
|
||||
|
||||
#endif
|
||||
16
src/builder.h
Normal file
16
src/builder.h
Normal file
@ -0,0 +1,16 @@
|
||||
#ifndef BUILDER_H
|
||||
#define BUILDER_H
|
||||
|
||||
#include <llvm/IR/LLVMContext.h>
|
||||
#include <llvm/IR/IRBuilder.h>
|
||||
|
||||
namespace codegen {
|
||||
struct Builder {
|
||||
std::unique_ptr<llvm::LLVMContext> context;
|
||||
std::unique_ptr<llvm::Module> mod;
|
||||
std::unique_ptr<llvm::IRBuilder<>> builder;
|
||||
llvm::BasicBlock* block;
|
||||
};
|
||||
}
|
||||
|
||||
#endif
|
||||
@ -1,5 +1,6 @@
|
||||
#include "codegen.h"
|
||||
#include "ast.h"
|
||||
#include "types.h"
|
||||
|
||||
#include <llvm/IR/Module.h>
|
||||
#include <llvm/IR/Verifier.h>
|
||||
@ -15,7 +16,13 @@ namespace codegen {
|
||||
namespace AST {
|
||||
codegen::StackValue IntLiteralExpression::codegen(codegen::Builder& builder, codegen::Scope& scope) {
|
||||
auto ty = builder.builder->getInt32Ty();
|
||||
return codegen::StackValue{ llvm::ConstantInt::get(ty, this->m_value), ty };
|
||||
|
||||
auto stack_type = new types::FundamentalType{ types::FundamentalTypeKind::Int };
|
||||
|
||||
return codegen::StackValue{
|
||||
llvm::ConstantInt::get(ty, this->m_value),
|
||||
std::unique_ptr<types::Type>{stack_type}
|
||||
};
|
||||
}
|
||||
|
||||
codegen::StackValue ValueReferenceExpression::codegen(codegen::Builder& builder, codegen::Scope& scope) {
|
||||
@ -26,7 +33,7 @@ namespace AST {
|
||||
}
|
||||
else {
|
||||
return codegen::StackValue{
|
||||
builder.builder->CreateLoad(value->second.ty, value->second.value),
|
||||
builder.builder->CreateLoad(value->second.ty->codegen(builder), value->second.value),
|
||||
value->second.ty
|
||||
};
|
||||
}
|
||||
@ -78,20 +85,20 @@ namespace AST {
|
||||
|
||||
builder.builder->SetInsertPoint(builder.block);
|
||||
|
||||
auto ty = this->m_type->codegen(builder, scope);
|
||||
auto ty = this->m_type->codegen(builder);
|
||||
auto ptr = builder.builder->CreateAlloca(ty);
|
||||
if (this->m_expr.has_value()) {
|
||||
auto value = this->m_expr->get()->codegen(builder, scope);
|
||||
builder.builder->CreateStore(value.value, ptr, false);
|
||||
}
|
||||
|
||||
scope.values[this->m_name] = codegen::StackValue{ ptr, ty };
|
||||
scope.values[this->m_name] = codegen::StackValue{ ptr, std::move(this->m_type) };
|
||||
}
|
||||
|
||||
void Function::codegen(codegen::Builder& builder, codegen::Scope& scope) {
|
||||
codegen::Scope inner_scope{ scope };
|
||||
|
||||
auto ret_ty = this->m_return_ty->codegen(builder, inner_scope);
|
||||
auto ret_ty = this->m_return_ty->codegen(builder);
|
||||
std::vector<llvm::Type*> params{};
|
||||
|
||||
|
||||
@ -113,8 +120,10 @@ namespace AST {
|
||||
|
||||
builder.block = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
llvm::Type* FundamentalType::codegen(codegen::Builder& builder, codegen::Scope& scope) {
|
||||
namespace types {
|
||||
llvm::Type* FundamentalType::codegen(codegen::Builder& builder) {
|
||||
switch (this->m_ty) {
|
||||
case FundamentalTypeKind::Int:
|
||||
return builder.builder->getInt32Ty();
|
||||
|
||||
@ -6,17 +6,13 @@
|
||||
#include <llvm/IR/IRBuilder.h>
|
||||
#include <map>
|
||||
|
||||
namespace codegen {
|
||||
struct Builder {
|
||||
std::unique_ptr<llvm::LLVMContext> context;
|
||||
std::unique_ptr<llvm::Module> mod;
|
||||
std::unique_ptr<llvm::IRBuilder<>> builder;
|
||||
llvm::BasicBlock* block;
|
||||
};
|
||||
#include "builder.h"
|
||||
#include "types.h"
|
||||
|
||||
namespace codegen {
|
||||
struct StackValue {
|
||||
llvm::Value* value;
|
||||
llvm::Type* ty;
|
||||
std::shared_ptr<types::Type> ty;
|
||||
};
|
||||
|
||||
struct Scope {
|
||||
|
||||
@ -1,17 +1,18 @@
|
||||
#include "types.h"
|
||||
#include "parsing.h"
|
||||
|
||||
|
||||
namespace parsing {
|
||||
namespace {
|
||||
Result<std::unique_ptr<AST::Type>, std::string> parse_type(token::TokenStream& stream) {
|
||||
Result<std::unique_ptr<types::Type>, std::string> parse_type(token::TokenStream& stream) {
|
||||
token::TokenStream inner{ stream };
|
||||
try {
|
||||
auto token = inner.expect(token::Type::Ident);
|
||||
|
||||
stream.m_position = inner.m_position;
|
||||
|
||||
auto ty = new AST::FundamentalType{ AST::FundamentalTypeKind::Int };
|
||||
return new std::unique_ptr<AST::Type>{ ty };
|
||||
auto ty = new types::FundamentalType{ types::FundamentalTypeKind::Int };
|
||||
return new std::unique_ptr<types::Type>{ ty };
|
||||
}
|
||||
catch (std::runtime_error error) {
|
||||
return new std::string{ error.what() };
|
||||
|
||||
15
src/types.cpp
Normal file
15
src/types.cpp
Normal file
@ -0,0 +1,15 @@
|
||||
#include "types.h"
|
||||
|
||||
#include <sstream>
|
||||
|
||||
namespace types {
|
||||
std::string FundamentalType::formatted() {
|
||||
switch (this->m_ty) {
|
||||
case FundamentalTypeKind::Int:
|
||||
return "Int";
|
||||
default:
|
||||
return "Unknown";
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
32
src/types.h
Normal file
32
src/types.h
Normal file
@ -0,0 +1,32 @@
|
||||
#ifndef TYPES_H
|
||||
#define TYPES_H
|
||||
|
||||
#include "builder.h"
|
||||
|
||||
#include <string>
|
||||
#include <memory>
|
||||
|
||||
namespace types {
|
||||
enum FundamentalTypeKind {
|
||||
Int,
|
||||
};
|
||||
|
||||
class Type {
|
||||
public:
|
||||
virtual ~Type() = default;
|
||||
virtual std::string formatted() = 0;
|
||||
virtual llvm::Type* codegen(codegen::Builder& builder) = 0;
|
||||
};
|
||||
|
||||
class FundamentalType : public Type {
|
||||
private:
|
||||
FundamentalTypeKind m_ty;
|
||||
public:
|
||||
FundamentalType(FundamentalTypeKind kind) : m_ty{ kind } {}
|
||||
virtual ~FundamentalType() override = default;
|
||||
virtual std::string formatted() override;
|
||||
virtual llvm::Type* codegen(codegen::Builder& builder) override;
|
||||
};
|
||||
}
|
||||
|
||||
#endif
|
||||
Loading…
Reference in New Issue
Block a user