#pragma once #include #include #include #include "instruction.hpp" #include "llvm_context.hpp" #include "type_env.hpp" struct ast; using ast_ptr = std::unique_ptr; struct constructor { std::string name; std::vector types; int8_t tag; constructor(std::string n, std::vector ts) : name(std::move(n)), types(std::move(ts)) {} }; using constructor_ptr = std::unique_ptr; struct definition_defn { std::string name; std::vector params; ast_ptr body; type_env_ptr env; type_env_ptr var_env; std::set free_variables; type_ptr full_type; type_ptr return_type; std::vector instructions; llvm::Function* generated_function; definition_defn(std::string n, std::vector p, ast_ptr b) : name(std::move(n)), params(std::move(p)), body(std::move(b)) { } void find_free(type_mgr& mgr, type_env_ptr& env); void insert_types(type_mgr& mgr); void typecheck(type_mgr& mgr); void compile(); void declare_llvm(llvm_context& ctx); void generate_llvm(llvm_context& ctx); }; using definition_defn_ptr = std::unique_ptr; struct definition_data { std::string name; std::vector constructors; type_env_ptr env; definition_data(std::string n, std::vector cs) : name(std::move(n)), constructors(std::move(cs)) {} void insert_types(type_mgr& mgr, type_env_ptr& env); void insert_constructors() const; void generate_llvm(llvm_context& ctx); }; using definition_data_ptr = std::unique_ptr;