Skip to content

Commit

Permalink
Fix more tests
Browse files Browse the repository at this point in the history
  • Loading branch information
marcauberer committed Dec 4, 2022
1 parent 353e917 commit 7b6fa45
Show file tree
Hide file tree
Showing 11 changed files with 46 additions and 43 deletions.
20 changes: 6 additions & 14 deletions media/test-project/os-test.spice
Original file line number Diff line number Diff line change
@@ -1,19 +1,11 @@
//import "std/type/int" as unused;
//import "os-test2" as s1;

f<double> calledFunction(int mandatoryArg, dyn optionalArg = true) {
printf("Mandatory: %d\n", mandatoryArg);
printf("Optional: %d\n", optionalArg);
return 0.1;
}

f<double> calledFunction(string testString) {
printf("String: %s", testString);
return 0.3;
}
import "os-test2" as s1;

f<int> main() {
dyn res = calledFunction(1, false);
printf("Result: %f\n", res);
calledFunction("test");
dyn v = s1::Vector<int>{};
v.setData(12);
printf("Data: %d\n", v.data);
v.setData(1.5);
printf("Data: %d\n", v.data);
}
12 changes: 5 additions & 7 deletions media/test-project/os-test2.spice
Original file line number Diff line number Diff line change
@@ -1,11 +1,9 @@
public type Vector1 struct {
public int i2
}
type T int|double;

public type Vector struct {
public Vector1 i1
public type Vector<T> struct {
public T data
}

public p Vector1.ctor() {

public p Vector.setData<T>(T data) {
this.data = data;
}
20 changes: 13 additions & 7 deletions src/scope/Scope.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -112,7 +112,9 @@ std::vector<SymbolTableEntry *> Scope::getVarsGoingOutOfScope() { // NOLINT(misc
*
* @param genericType Generic type itself
*/
void Scope::insertGenericType(const GenericType &genericType) { genericTypes.insert({genericType.getName(), genericType}); }
void Scope::insertGenericType(const std::string &typeName, const GenericType &genericType) {
genericTypes.insert({typeName, genericType});
}

/**
* Search for a generic type by its name. If it was not found, the parent scopes will be searched.
Expand Down Expand Up @@ -265,7 +267,7 @@ Function *Scope::matchFunction(const std::string &callFunctionName, const Symbol
// Insert symbols for generic type names with concrete types into the child block
Scope *childBlock = getChildScope(newFunction.getSignature());
for (const auto &[typeName, symbolType] : concreteGenericTypes)
childBlock->insertGenericType(GenericType(symbolType));
childBlock->insertGenericType(typeName, GenericType(symbolType));

// Replace this type with concrete one
if ((f.isMethodFunction() || f.isMethodProcedure()) && !fctThisType.getTemplateTypes().empty()) {
Expand All @@ -276,8 +278,10 @@ Function *Scope::matchFunction(const std::string &callFunctionName, const Symbol
}
}

assert(functions.contains(defCodeLocStr) && functions.at(defCodeLocStr).contains(newFunction.getMangledName()));
matches.push_back(&functions.at(defCodeLocStr).at(newFunction.getMangledName()));
assert(functions.contains(defCodeLocStr));
std::unordered_map<std::string, Function> &manifestations = functions.at(defCodeLocStr);
assert(manifestations.contains(newFunction.getMangledName()));
matches.push_back(&manifestations.at(newFunction.getMangledName()));
break;
}
}
Expand Down Expand Up @@ -385,16 +389,18 @@ Struct *Scope::matchStruct(Scope *currentScope, const std::string &structName, /
if (differentTemplateTypes)
continue;

// Duplicate function
// Duplicate struct
Scope *structScope = getChildScope(STRUCT_SCOPE_PREFIX + structName);
Struct newStruct = s.substantiateGenerics(concreteTemplateTypes, structScope);
if (!getChildScope(STRUCT_SCOPE_PREFIX + newStruct.getSignature())) { // Insert struct
insertSubstantiatedStruct(newStruct, s.declNode);
copyChildScope(STRUCT_SCOPE_PREFIX + structName, STRUCT_SCOPE_PREFIX + newStruct.getSignature());
}

assert(structs.contains(defCodeLocStr) && structs.at(defCodeLocStr).contains(newStruct.getMangledName()));
matches.push_back(&structs.at(defCodeLocStr).at(newStruct.getMangledName()));
assert(structs.contains(defCodeLocStr));
std::unordered_map<std::string, Struct> &manifestations = structs.at(defCodeLocStr);
assert(manifestations.contains(newStruct.getMangledName()));
matches.push_back(&manifestations.at(newStruct.getMangledName()));
break;
}
}
Expand Down
3 changes: 1 addition & 2 deletions src/scope/Scope.h
Original file line number Diff line number Diff line change
Expand Up @@ -50,13 +50,12 @@ class Scope {
Scope *createChildScope(const std::string &scopeName, const ScopeType &scopeType, const CodeLoc *codeLoc);
void renameChildScope(const std::string &oldName, const std::string &newName);
void copyChildScope(const std::string &oldName, const std::string &newName);
[[nodiscard]] Scope *getGlobalScope();
[[nodiscard]] Scope *getFunctionScope();
[[nodiscard]] Scope *getChildScope(const std::string &scopeName) const;
[[nodiscard]] std::vector<SymbolTableEntry *> getVarsGoingOutOfScope();

// Generic types
void insertGenericType(const GenericType &genericType);
void insertGenericType(const std::string &typeName, const GenericType &genericType);
GenericType *lookupGenericType(const std::string &typeName);

// Functions
Expand Down
14 changes: 11 additions & 3 deletions src/typechecker/TypeChecker.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1181,6 +1181,7 @@ std::any TypeChecker::visitConstant(ConstantNode *node) {

std::any TypeChecker::visitFunctionCall(FunctionCallNode *node) {
// Visit template type hints
node->concreteTemplateTypes.clear();
if (node->hasTemplateTypes) {
node->concreteTemplateTypes.reserve(node->templateTypeLst()->dataTypes().size());
for (DataTypeNode *templateTypeNode : node->templateTypeLst()->dataTypes()) {
Expand All @@ -1195,6 +1196,7 @@ std::any TypeChecker::visitFunctionCall(FunctionCallNode *node) {
}

// Visit args
node->argTypes.clear();
if (node->hasArgs) {
node->argTypes.reserve(node->argLst()->args().size());
for (AssignExprNode *arg : node->argLst()->args()) {
Expand All @@ -1211,8 +1213,10 @@ std::any TypeChecker::visitFunctionCall(FunctionCallNode *node) {
if (node->functionNameFragments.size() == 1 && node->fqFunctionName == STROBJ_NAME && !isStringRt)
sourceFile->requestRuntimeModule(STRING_RT);

// Check if this is a method call or a normal function call
// Retrieve entry of the first fragment
SymbolTableEntry *firstFragmentEntry = currentScope->lookup(node->functionNameFragments.front());

// Check if this is a method call or a normal function call
Scope *functionParentScope;
SymbolType returnType(TY_DYN);
SymbolType thisType(TY_DYN);
Expand Down Expand Up @@ -1253,6 +1257,10 @@ std::any TypeChecker::visitFunctionCall(FunctionCallNode *node) {
throw SemanticError(node, REFERENCED_UNDEFINED_FUNCTION, "Function/procedure '" + f.getSignature() + "' could not be found");
}

// Check if we need to request a re-visit, because the function body was not type-checked yet
if (!node->calledFunction->alreadyTypeChecked)
reVisitRequested = true;

// Retrieve return type
if (node->isConstructorCall) {
// Add anonymous symbol to keep track of de-allocation
Expand Down Expand Up @@ -1523,8 +1531,8 @@ std::any TypeChecker::visitCustomDataType(CustomDataTypeNode *node) {
sourceFile->requestRuntimeModule(STRING_RT);

// Check if it is a generic type
if (!isImported && currentScope->lookupGenericType(firstFragment)) {
const SymbolType *genericType = currentScope->lookupGenericType(firstFragment);
if (!isImported && rootScope->lookupGenericType(firstFragment)) {
const SymbolType *genericType = rootScope->lookupGenericType(firstFragment);
assert(genericType != nullptr);
return node->setEvaluatedSymbolType(*genericType);
}
Expand Down
8 changes: 4 additions & 4 deletions src/typechecker/TypeCheckerPrepare.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@ std::any TypeChecker::visitFctDefPrepare(FctDefNode *node) {
if (!templateType.is(TY_GENERIC))
throw SemanticError(dataType, EXPECTED_GENERIC_TYPE, "A template list can only contain generic types");
// Convert generic symbol type to generic type
GenericType *genericType = node->structScope->lookupGenericType(templateType.getSubType());
GenericType *genericType = node->fctScope->lookupGenericType(templateType.getSubType());
assert(genericType != nullptr);
usedGenericTypes.push_back(*genericType);
}
Expand Down Expand Up @@ -124,7 +124,7 @@ std::any TypeChecker::visitFctDefPrepare(FctDefNode *node) {

// Build function object
const Function spiceFunc(node->functionName, functionEntry, thisType, returnType, paramTypes, usedGenericTypes, node,
/*external=*/true);
/*external=*/false);
currentScope->insertFunction(spiceFunc, &node->fctManifestations);

// Rename / duplicate the original child scope to reflect the substantiated versions of the function
Expand Down Expand Up @@ -219,7 +219,7 @@ std::any TypeChecker::visitProcDefPrepare(ProcDefNode *node) {

// Build procedure object
const Function spiceProc(node->procedureName, procedureEntry, thisType, SymbolType(TY_DYN), paramTypes, usedGenericTypes, node,
/*external=*/true);
/*external=*/false);
currentScope->insertFunction(spiceProc, &node->procManifestations);

// Rename / duplicate the original child block to reflect the substantiated versions of the procedure
Expand Down Expand Up @@ -410,7 +410,7 @@ std::any TypeChecker::visitGenericTypeDefPrepare(GenericTypeDefNode *node) {

// Add generic type to the scope
const GenericType genericType(node->typeName, typeConditions);
currentScope->insertGenericType(genericType);
rootScope->insertGenericType(node->typeName, genericType);

return nullptr;
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
[Error|Semantic] ./test-files/typechecker/generics/error-failing-type-condition/source.spice:8:16:
Referenced undefined function: Function/Procedure 'max(short,short)' could not be found
Referenced undefined function: Function/procedure 'max(short,short)' could not be found

8 dyn test = max(1s, 2s);
^^^^^^^^^^^

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
[Error|Semantic] ./test-files/typechecker/generics/error-generic-method-not-found/source.spice:7:5:
Referenced undefined function: Function/procedure 's1::Vector.setData(double)' could not be found

7 v.setData(1.5);
^^^^^^^^^^^^^^

0 comments on commit 7b6fa45

Please sign in to comment.