Skip to content

Commit

Permalink
Move logic from Type to QualType where possible (#540)
Browse files Browse the repository at this point in the history
  • Loading branch information
marcauberer authored May 9, 2024
1 parent ff52fdc commit 9a79c00
Show file tree
Hide file tree
Showing 50 changed files with 1,107 additions and 670 deletions.
2 changes: 1 addition & 1 deletion src/CompilerPass.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@

#pragma once

#include <string>
#include <cstdint>
#include <string>

namespace spice::compiler {

Expand Down
3 changes: 1 addition & 2 deletions src/SourceFile.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -458,8 +458,7 @@ void SourceFile::runObjectEmitter() {
objectEmitter.emit(objectFilePath);

// Save assembly string in the compiler output
if (cliOptions.isNativeTarget &&
(cliOptions.dumpSettings.dumpAssembly || cliOptions.testMode))
if (cliOptions.isNativeTarget && (cliOptions.dumpSettings.dumpAssembly || cliOptions.testMode))
objectEmitter.getASMString(compilerOutput.asmString);

// Dump assembly code
Expand Down
2 changes: 1 addition & 1 deletion src/ast/ASTNodes.h
Original file line number Diff line number Diff line change
Expand Up @@ -159,7 +159,7 @@ class ASTNode {
ASTNode *parent = nullptr;
std::vector<ASTNode *> children;
const CodeLoc codeLoc;
std::vector<QualType> symbolTypes;
QualTypeList symbolTypes;
bool unreachable = false;
};

Expand Down
12 changes: 6 additions & 6 deletions src/cmake/ExternalAntlr4Cpp.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ if (NOT DEFINED ANTLR4_WITH_STATIC_CRT)
endif ()

if (ANTLR4_ZIP_REPOSITORY)
if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
if (CMAKE_SYSTEM_NAME STREQUAL "Linux")
ExternalProject_Add(
antlr4_runtime
PREFIX antlr4_runtime
Expand All @@ -100,7 +100,7 @@ if (ANTLR4_ZIP_REPOSITORY)
INSTALL_COMMAND ""
EXCLUDE_FROM_ALL 1
DOWNLOAD_EXTRACT_TIMESTAMP 0)
else()
else ()
ExternalProject_Add(
antlr4_runtime
PREFIX antlr4_runtime
Expand All @@ -118,9 +118,9 @@ if (ANTLR4_ZIP_REPOSITORY)
INSTALL_COMMAND ""
EXCLUDE_FROM_ALL 1
DOWNLOAD_EXTRACT_TIMESTAMP 0)
endif()
endif ()
else ()
if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
if (CMAKE_SYSTEM_NAME STREQUAL "Linux")
ExternalProject_Add(
antlr4_runtime
PREFIX antlr4_runtime
Expand All @@ -143,7 +143,7 @@ else ()
INSTALL_COMMAND ""
EXCLUDE_FROM_ALL 1
DOWNLOAD_EXTRACT_TIMESTAMP 0)
else()
else ()
ExternalProject_Add(
antlr4_runtime
PREFIX antlr4_runtime
Expand All @@ -162,7 +162,7 @@ else ()
INSTALL_COMMAND ""
EXCLUDE_FROM_ALL 1
DOWNLOAD_EXTRACT_TIMESTAMP 0)
endif()
endif ()
endif ()

# Separate build step as rarely people want both
Expand Down
15 changes: 5 additions & 10 deletions src/driver/Driver.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -321,18 +321,13 @@ void Driver::addCompileSubcommandOptions(CLI::App *subCmd) {
// Opt levels
subCmd->add_flag_callback(
"-O0", [&]() { cliOptions.optLevel = OptLevel::O0; }, "Disable optimization for the output executable.");
subCmd->add_flag_callback(
"-O1", [&]() { cliOptions.optLevel = OptLevel::O1; }, "Only basic optimization is executed.");
subCmd->add_flag_callback(
"-O2", [&]() { cliOptions.optLevel = OptLevel::O2; }, "More advanced optimization is applied.");
subCmd->add_flag_callback("-O1", [&]() { cliOptions.optLevel = OptLevel::O1; }, "Only basic optimization is executed.");
subCmd->add_flag_callback("-O2", [&]() { cliOptions.optLevel = OptLevel::O2; }, "More advanced optimization is applied.");
subCmd->add_flag_callback(
"-O3", [&]() { cliOptions.optLevel = OptLevel::O3; }, "Aggressive optimization for best performance.");
subCmd->add_flag_callback(
"-Os", [&]() { cliOptions.optLevel = OptLevel::Os; }, "Size optimization for output executable.");
subCmd->add_flag_callback(
"-Oz", [&]() { cliOptions.optLevel = OptLevel::Oz; }, "Aggressive optimization for best size.");
subCmd->add_flag_callback(
"-lto", [&]() { cliOptions.useLTO = true; }, "Enable link time optimization (LTO)");
subCmd->add_flag_callback("-Os", [&]() { cliOptions.optLevel = OptLevel::Os; }, "Size optimization for output executable.");
subCmd->add_flag_callback("-Oz", [&]() { cliOptions.optLevel = OptLevel::Oz; }, "Aggressive optimization for best size.");
subCmd->add_flag_callback("-lto", [&]() { cliOptions.useLTO = true; }, "Enable link time optimization (LTO)");

// --debug-output
subCmd->add_flag<bool>("--debug-output,-d", cliOptions.printDebugOutput, "Enable debug output");
Expand Down
6 changes: 2 additions & 4 deletions src/global/TypeRegistry.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
namespace spice::compiler {

// Static member initialization
std::unordered_map<std::string, std::unique_ptr<Type>>TypeRegistry::types = {};
std::unordered_map<std::string, std::unique_ptr<Type>> TypeRegistry::types = {};

const Type *TypeRegistry::get(const std::string &name) {
const auto it = types.find(name);
Expand All @@ -27,8 +27,6 @@ const Type *TypeRegistry::getOrInsert(Type type) {
return insertedElement.first->second.get();
}

const Type *TypeRegistry::getOrInsert(SuperType superType) {
return getOrInsert(Type(superType));
}
const Type *TypeRegistry::getOrInsert(SuperType superType) { return getOrInsert(Type(superType)); }

} // namespace spice::compiler
10 changes: 5 additions & 5 deletions src/irgenerator/DebugInfoGenerator.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -176,7 +176,7 @@ llvm::DICompositeType *DebugInfoGenerator::generateCaptureStructDebugInfo(const
// Get LLVM type for struct
std::vector<llvm::Type *> fieldTypes;
std::vector<SymbolTableEntry *> fieldEntries;
std::vector<QualType> fieldSymbolTypes;
QualTypeList fieldSymbolTypes;
for (const auto &[_, capture] : captures) {
QualType captureType = capture.capturedEntry->getQualType();

Expand All @@ -186,7 +186,7 @@ llvm::DICompositeType *DebugInfoGenerator::generateCaptureStructDebugInfo(const

fieldEntries.push_back(capture.capturedEntry);
fieldSymbolTypes.push_back(captureType);
fieldTypes.push_back(captureType.getType().toLLVMType(irGenerator->context, irGenerator->currentScope));
fieldTypes.push_back(captureType.toLLVMType(irGenerator->context, irGenerator->currentScope));
}
llvm::StructType *structType = llvm::StructType::get(irGenerator->context, fieldTypes, CAPTURES_PARAM_NAME);
const llvm::StructLayout *structLayout = irGenerator->module->getDataLayout().getStructLayout(structType);
Expand Down Expand Up @@ -291,7 +291,7 @@ llvm::DIType *DebugInfoGenerator::getDITypeForQualType(const ASTNode *node, cons
// Array ty
if (ty.isArray()) {
llvm::DIType *itemTy = getDITypeForQualType(node, ty.getContained());
const size_t size = ty.getType().getArraySize();
const size_t size = ty.getArraySize();
llvm::DINodeArray subscripts = diBuilder->getOrCreateArray({});
return diBuilder->createArrayType(size, 0, itemTy, subscripts);
}
Expand Down Expand Up @@ -324,7 +324,7 @@ llvm::DIType *DebugInfoGenerator::getDITypeForQualType(const ASTNode *node, cons
baseDiType = boolTy;
break;
case TY_STRUCT: {
Struct *spiceStruct = ty.getType().getStruct(node);
Struct *spiceStruct = ty.getStruct(node);
assert(spiceStruct != nullptr);

// Check if we already know the DI ty
Expand Down Expand Up @@ -373,7 +373,7 @@ llvm::DIType *DebugInfoGenerator::getDITypeForQualType(const ASTNode *node, cons
break;
}
case TY_INTERFACE: {
Interface *spiceInterface = ty.getType().getInterface(node);
Interface *spiceInterface = ty.getInterface(node);
assert(spiceInterface != nullptr);

// Check if we already know the DI ty
Expand Down
14 changes: 7 additions & 7 deletions src/irgenerator/GenBuiltinFunctions.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -25,11 +25,11 @@ std::any IRGenerator::visitPrintfCall(const PrintfCallNode *node) {
if (argSymbolType.isArray()) {
llvm::Value *argValPtr = resolveAddress(arg);
llvm::Value *indices[2] = {builder.getInt32(0), builder.getInt32(0)};
llvm::Type *argType = argSymbolType.getType().toLLVMType(context, currentScope);
llvm::Type *argType = argSymbolType.toLLVMType(context, currentScope);
argVal = insertInBoundsGEP(argType, argValPtr, indices);
} else if (argSymbolType.getBase().getType().isStringObj()) {
} else if (argSymbolType.getBase().isStringObj()) {
llvm::Value *argValPtr = resolveAddress(arg);
llvm::Type *argBaseType = argSymbolType.getBase().getType().toLLVMType(context, currentScope);
llvm::Type *argBaseType = argSymbolType.getBase().toLLVMType(context, currentScope);
argValPtr = insertStructGEP(argBaseType, argValPtr, 0);
argVal = insertLoad(builder.getPtrTy(), argValPtr);
} else {
Expand Down Expand Up @@ -61,7 +61,7 @@ std::any IRGenerator::visitSizeofCall(const SizeofCallNode *node) {
if (node->isType) { // Size of type
type = any_cast<llvm::Type *>(visit(node->dataType()));
} else { // Size of value
type = node->assignExpr()->getEvaluatedSymbolType(manIdx).getType().toLLVMType(context, currentScope);
type = node->assignExpr()->getEvaluatedSymbolType(manIdx).toLLVMType(context, currentScope);
}
// Calculate size at compile-time
const llvm::TypeSize sizeInBits = module->getDataLayout().getTypeSizeInBits(type);
Expand All @@ -76,7 +76,7 @@ std::any IRGenerator::visitAlignofCall(const AlignofCallNode *node) {
if (node->isType) { // Align of type
type = any_cast<llvm::Type *>(visit(node->dataType()));
} else { // Align of value
type = node->assignExpr()->getEvaluatedSymbolType(manIdx).getType().toLLVMType(context, currentScope);
type = node->assignExpr()->getEvaluatedSymbolType(manIdx).toLLVMType(context, currentScope);
}
// Calculate size at compile-time
const llvm::Align align = module->getDataLayout().getABITypeAlign(type);
Expand All @@ -96,9 +96,9 @@ std::any IRGenerator::visitLenCall(const LenCallNode *node) {
llvm::Function *getRawLengthFct = stdFunctionManager.getStringGetRawLengthStringFct();
lengthValue = builder.CreateCall(getRawLengthFct, resolveValue(node->assignExpr()));
} else {
assert(symbolType.isArray() && symbolType.getType().getArraySize() != ARRAY_SIZE_UNKNOWN);
assert(symbolType.isArray() && symbolType.getArraySize() != ARRAY_SIZE_UNKNOWN);
// Return length value
lengthValue = builder.getInt64(symbolType.getType().getArraySize());
lengthValue = builder.getInt64(symbolType.getArraySize());
}
return LLVMExprResult{.value = lengthValue};
}
Expand Down
8 changes: 4 additions & 4 deletions src/irgenerator/GenControlStructures.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@ std::any IRGenerator::visitForeachLoop(const ForeachLoopNode *node) {
if (!node->getIteratorFct->isMethod() && node->getIteratorFct->getParamTypes().front().isArray()) { // Array as iterable
// Call iterate() function from std/iterator/array-iterator
llvm::Function *iterateFct = stdFunctionManager.getIterateFct(node->getIteratorFct);
const size_t arraySize = iteratorAssignNode->getEvaluatedSymbolType(manIdx).getType().getArraySize();
const size_t arraySize = iteratorAssignNode->getEvaluatedSymbolType(manIdx).getArraySize();
assert(arraySize > 0);
iterator = builder.CreateCall(iterateFct, {iterablePtr, builder.getInt64(arraySize)});
} else { // Struct as iterable
Expand All @@ -127,10 +127,10 @@ std::any IRGenerator::visitForeachLoop(const ForeachLoopNode *node) {
iteratorPtr = resolveAddress(iteratorAssignNode);
}

const QualType &itemSTy = iteratorType.getType().getTemplateTypes().front();
const QualType &itemSTy = iteratorType.getTemplateTypes().front();
const QualType itemRefSTy = itemSTy.toRef(node);
assert(!node->getFct || itemRefSTy == node->getFct->returnType);
assert(!node->getIdxFct || itemRefSTy == node->getIdxFct->returnType.getType().getTemplateTypes().back());
assert(!node->getIdxFct || itemRefSTy == node->getIdxFct->returnType.getTemplateTypes().back());

// Visit idx variable declaration if required
const DeclStmtNode *idxDeclNode = node->idxVarDecl();
Expand Down Expand Up @@ -170,7 +170,7 @@ std::any IRGenerator::visitForeachLoop(const ForeachLoopNode *node) {
// Get the current iterator values
if (hasIdx) {
// Allocate space to save pair
llvm::Type *pairTy = node->getIdxFct->returnType.getType().toLLVMType(context, currentScope);
llvm::Type *pairTy = node->getIdxFct->returnType.toLLVMType(context, currentScope);
llvm::Value *pairPtr = insertAlloca(pairTy, "pair_addr");
// Call .getIdx() on iterator
assert(node->getIdxFct);
Expand Down
14 changes: 7 additions & 7 deletions src/irgenerator/GenExpressions.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -102,8 +102,8 @@ std::any IRGenerator::visitTernaryExpr(const TernaryExprNode *node) {
} else {
const QualType &op1Type = node->operands()[1]->getEvaluatedSymbolType(manIdx);
const QualType &op2Type = node->operands()[2]->getEvaluatedSymbolType(manIdx);
llvm::Type *op1Ty = op1Type.getType().toLLVMType(context, currentScope);
llvm::Type *op2Ty = op2Type.getType().toLLVMType(context, currentScope);
llvm::Type *op1Ty = op1Type.toLLVMType(context, currentScope);
llvm::Type *op2Ty = op2Type.toLLVMType(context, currentScope);
trueValue = resolveValue(node->operands()[1]);
falseValue = resolveValue(node->operands()[2]);
}
Expand Down Expand Up @@ -664,13 +664,13 @@ std::any IRGenerator::visitPostfixUnaryExpr(const PostfixUnaryExprNode *node) {
lhsSTy = lhsSTy.removeReferenceWrapper();

// Get the LLVM type of the operand
llvm::Type *lhsTy = lhsSTy.getType().toLLVMType(context, currentScope);
llvm::Type *lhsTy = lhsSTy.toLLVMType(context, currentScope);

// Get the index value
AssignExprNode *indexExpr = node->assignExpr();
llvm::Value *indexValue = resolveValue(indexExpr);
// Come up with the address
if (lhsSTy.isArray() && lhsSTy.getType().getArraySize() != ARRAY_SIZE_UNKNOWN) { // Array
if (lhsSTy.isArray() && lhsSTy.getArraySize() != ARRAY_SIZE_UNKNOWN) { // Array
// Make sure the address is present
resolveAddress(lhs);

Expand Down Expand Up @@ -706,7 +706,7 @@ std::any IRGenerator::visitPostfixUnaryExpr(const PostfixUnaryExprNode *node) {

// Retrieve struct scope
const std::string &fieldName = node->identifier;
Scope *structScope = lhsSTy.getType().getBodyScope();
Scope *structScope = lhsSTy.getBodyScope();

// Retrieve field entry
std::vector<size_t> indexPath;
Expand All @@ -719,7 +719,7 @@ std::any IRGenerator::visitPostfixUnaryExpr(const PostfixUnaryExprNode *node) {
for (size_t index : indexPath)
indices.push_back(builder.getInt32(index));
const std::string name = fieldName + "_addr";
llvm::Value *memberAddr = insertInBoundsGEP(lhsSTy.getType().toLLVMType(context, structScope->parent), lhs.ptr, indices, name);
llvm::Value *memberAddr = insertInBoundsGEP(lhsSTy.toLLVMType(context, structScope->parent), lhs.ptr, indices, name);

// Set as ptr or refPtr, depending on the type
if (fieldSymbolType.isRef()) {
Expand Down Expand Up @@ -826,7 +826,7 @@ std::any IRGenerator::visitAtomicExpr(const AtomicExprNode *node) {
Scope *accessScope = data.accessScope;
assert(accessScope != nullptr);
QualType varSymbolType = varEntry->getQualType();
llvm::Type *varType = varSymbolType.getType().toLLVMType(context, accessScope);
llvm::Type *varType = varSymbolType.toLLVMType(context, accessScope);

// Check if external global variable
if (varEntry->global && accessScope->isImportedBy(rootScope)) {
Expand Down
22 changes: 11 additions & 11 deletions src/irgenerator/GenImplicit.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -26,18 +26,18 @@ llvm::Value *IRGenerator::doImplicitCast(llvm::Value *src, QualType dstSTy, Qual
// Unpack the pointers until a pointer of another type is met
size_t loadCounter = 0;
while (srcSTy.isPtr()) {
src = insertLoad(srcSTy.getType().toLLVMType(context, currentScope), src);
src = insertLoad(srcSTy.toLLVMType(context, currentScope), src);
srcSTy = srcSTy.getContained();
dstSTy = dstSTy.getContained();
loadCounter++;
}
// GEP or bit-cast
if (dstSTy.isArray() && srcSTy.isArray()) { // Special case that is used for passing arrays as pointer to functions
llvm::Value *indices[2] = {builder.getInt32(0), builder.getInt32(0)};
src = insertInBoundsGEP(srcSTy.getType().toLLVMType(context, currentScope), src, indices);
src = insertInBoundsGEP(srcSTy.toLLVMType(context, currentScope), src, indices);
} else {
src = insertLoad(srcSTy.getType().toLLVMType(context, currentScope), src);
src = builder.CreateBitCast(src, dstSTy.getType().toLLVMType(context, currentScope));
src = insertLoad(srcSTy.toLLVMType(context, currentScope), src);
src = builder.CreateBitCast(src, dstSTy.toLLVMType(context, currentScope));
}
// Pack the pointers together again
for (; loadCounter > 0; loadCounter--) {
Expand Down Expand Up @@ -124,7 +124,7 @@ llvm::Function *IRGenerator::generateImplicitFunction(const std::function<void(v
return nullptr;

// Retrieve return type
llvm::Type *returnType = spiceFunc->returnType.getType().toLLVMType(context, currentScope);
llvm::Type *returnType = spiceFunc->returnType.toLLVMType(context, currentScope);

// Get 'this' entry
std::vector<std::pair<std::string, SymbolTableEntry *>> paramInfoList;
Expand All @@ -140,7 +140,7 @@ llvm::Function *IRGenerator::generateImplicitFunction(const std::function<void(v
// Get parameter types
for (const Param &param : spiceFunc->paramList) {
assert(!param.isOptional);
paramTypes.push_back(param.type.getType().toLLVMType(context, currentScope));
paramTypes.push_back(param.type.toLLVMType(context, currentScope));
}

// Get function linkage
Expand Down Expand Up @@ -231,7 +231,7 @@ llvm::Function *IRGenerator::generateImplicitProcedure(const std::function<void(
// Get parameter types
for (const Param &param : spiceProc->paramList) {
assert(!param.isOptional);
paramTypes.push_back(param.type.getType().toLLVMType(context, currentScope));
paramTypes.push_back(param.type.toLLVMType(context, currentScope));
}

// Get function linkage
Expand Down Expand Up @@ -317,7 +317,7 @@ void IRGenerator::generateCtorBodyPreamble(Scope *bodyScope) {
llvm::Type *structType = structSymbolType.toLLVMType(context, structScope);

// Store VTable to first struct field if required
Struct *spiceStruct = structSymbolType.getType().getStruct(nullptr);
Struct *spiceStruct = structSymbolType.getStruct(nullptr);
assert(spiceStruct != nullptr);
if (spiceStruct->vTableData.vtable != nullptr) {
assert(spiceStruct->vTableData.vtableType != nullptr);
Expand All @@ -340,7 +340,7 @@ void IRGenerator::generateCtorBodyPreamble(Scope *bodyScope) {
auto fieldNode = spice_pointer_cast<FieldNode *>(fieldSymbol->declNode);
if (fieldType.is(TY_STRUCT)) {
// Lookup ctor function and call if available
Scope *matchScope = fieldType.getType().getBodyScope();
Scope *matchScope = fieldType.getBodyScope();
const Function *ctorFunction = FunctionManager::lookupFunction(matchScope, CTOR_FUNCTION_NAME, fieldType, {}, false);
if (ctorFunction)
generateCtorOrDtorCall(fieldSymbol, ctorFunction, {});
Expand Down Expand Up @@ -403,7 +403,7 @@ void IRGenerator::generateCopyCtorBodyPreamble(const Function *copyCtorFunction)
const QualType &fieldType = fieldSymbol->getQualType();
if (fieldType.is(TY_STRUCT)) {
// Lookup copy ctor function and call if available
Scope *matchScope = fieldType.getType().getBodyScope();
Scope *matchScope = fieldType.getBodyScope();
const ArgList args = {{fieldType.toConstRef(nullptr), false /* we have the field as storage */}};
const Function *ctorFct = FunctionManager::lookupFunction(matchScope, CTOR_FUNCTION_NAME, fieldType, args, false);
if (ctorFct) {
Expand Down Expand Up @@ -449,7 +449,7 @@ void IRGenerator::generateDtorBodyPreamble(const Function *dtorFunction) {
if (fieldType.is(TY_STRUCT)) {
// Lookup dtor function and generate call if found
const Function *dtorFct =
FunctionManager::lookupFunction(fieldType.getType().getBodyScope(), DTOR_FUNCTION_NAME, fieldType, {}, false);
FunctionManager::lookupFunction(fieldType.getBodyScope(), DTOR_FUNCTION_NAME, fieldType, {}, false);
if (dtorFct)
generateCtorOrDtorCall(fieldSymbol, dtorFct, {});
continue;
Expand Down
4 changes: 2 additions & 2 deletions src/irgenerator/GenStatements.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,8 @@ std::any IRGenerator::visitDeclStmt(const DeclStmtNode *node) {
// Get LLVM type of variable
Scope *accessScope = currentScope;
if (varSymbolType.is(TY_STRUCT))
accessScope = varSymbolType.getType().getBodyScope()->parent;
llvm::Type *varTy = varSymbolType.getType().toLLVMType(context, accessScope);
accessScope = varSymbolType.getBodyScope()->parent;
llvm::Type *varTy = varSymbolType.toLLVMType(context, accessScope);

// Check if right side is dyn array. If this is the case we have an empty array initializer and need the default value
const bool rhsIsDynArray = node->hasAssignment && node->assignExpr()->getEvaluatedSymbolType(manIdx).isArrayOf(TY_DYN);
Expand Down
Loading

0 comments on commit 9a79c00

Please sign in to comment.