ext libs can define generics

This commit is contained in:
2026-07-01 17:29:00 +10:00
parent b9077d75ed
commit 5e8c300111
9 changed files with 91 additions and 7 deletions

View File

@@ -1,3 +0,0 @@
1. [X] Parse generic types
2. [X] Declare generic types when we see a struct def
3. [ ] Whenever we see a `new`, if its for a generic struct we create a new struct with the given types, and cache it if we need to

View File

@@ -50,8 +50,11 @@ API_EXPORT float cometArgFloat(int64_t argVal);
API_EXPORT double cometArgDouble(int64_t argVal);
API_EXPORT bool cometArgBool(int64_t argVal);
API_EXPORT char* cometArgString(int64_t argVal);
API_EXPORT uintptr_t cometArgPointer(int64_t argVal);
API_EXPORT int64_t cometSerializeString(char* cString);
API_EXPORT CometType cometGenericType(char* name);
API_EXPORT CometFunction* cometDefineFunc(
CometEnvironment* env,
char* name,
@@ -75,6 +78,7 @@ API_EXPORT StructField cometCreateField(char* name, CometType type);
API_EXPORT void cometSetStructFieldsAndMethods(CometStruct* cometStruct, List(StructField) fields, List(cometFuncPtr) methods);
API_EXPORT CometStruct* cometDefineStruct(CometEnvironment* env, char* name, CometStruct* parent);
API_EXPORT CometStruct* cometDefineGenericStruct(CometEnvironment* env, char* name, CometStruct* parent, List(charptr) genericTypeNames);
API_EXPORT void cometDefineConstructor(
CometEnvironment* env,

View File

@@ -7,6 +7,9 @@
#define MAX_ARRAY_DEPTH 8
typedef char* charptr;
UseList(charptr);
typedef enum {
COMET_VOID,
COMET_SMALL,
@@ -83,6 +86,7 @@ extern CometType cometTypeDouble;
extern CometType cometTypeBool;
extern CometType cometTypeVoid;
extern CometType cometTypeString;
extern CometType cometTypePointer;
bool typesAreEqual(CometType a, CometType b);

View File

@@ -32,6 +32,17 @@ char* cometArgString(int64_t argVal) {
CometOperand stringArr = cometDeserializeValue(argVal, cometTypeString);
return cometArrayToCArray(stringArr, cometTypeSmall);
}
uintptr_t cometArgPointer(int64_t argVal) {
#if INTPTR_MAX == INT64_MAX
// 64-bit pointers
return cometDeserializeValue(argVal, cometTypeBig).imm.bigVal;
#elif INTPTR_MAX == INT32_MAX
// 32-bit pointers
return cometDeserializeValue(argVal, cometTypeint).imm.intVal;
#else
#error "Unsupported pointer size"
#endif
}
int64_t cometSerializeString(char* cString) {
CometOperand cometArray = CArrayToCometArray(cString, strlen(cString) + 1, cometTypeSmall);
return cometSerializeValue(cometArray);
@@ -62,6 +73,13 @@ CometStruct* cometGetExceptionStruct(CometEnvironment* env) {
return exceptStruct;
}
CometType cometGenericType(char* name) {
return (CometType){
.typeKind = COMET_GENERIC,
.genericParamName = strdup(name)
};
}
void cometSetStructFieldsAndMethods(CometStruct* cometStruct, List(StructField) fields, List(cometFuncPtr) methods) {
size_t fieldCount = cometStruct->parent == NULL ? fields.count : fields.count + cometStruct->parent->fieldCount;
size_t methodCount = cometStruct->parent == NULL ? methods.count : methods.count + cometStruct->parent->numMethods;
@@ -99,6 +117,19 @@ void cometSetStructFieldsAndMethods(CometStruct* cometStruct, List(StructField)
cometStruct->vtable = (CometMethod**)methodsArr;
}
CometStruct* cometDefineGenericStruct(CometEnvironment* env, char* name, CometStruct* parent, List(charptr) genericTypeNames) {
CometStruct* baseStruct = cometDefineStruct(env, name, parent);
for (size_t i = 0; i < genericTypeNames.count; i++) {
genericTypeNames.pointer[i] = strdup(genericTypeNames.pointer[i]);
}
baseStruct->genericTypeNames = genericTypeNames.pointer;
baseStruct->numGenericTypes = genericTypeNames.count;
return baseStruct;
}
CometStruct* cometDefineStruct(CometEnvironment* env, char* name, CometStruct* parent) {
CometStruct* newStruct = malloc(sizeof(CometStruct));

View File

@@ -10,6 +10,16 @@ CometType cometTypeDouble = (CometType){.typeKind = COMET_DOUBLE};
CometType cometTypeBool = (CometType){.typeKind = COMET_BOOL };
CometType cometTypeVoid = (CometType){.typeKind = COMET_VOID };
#if INTPTR_MAX == INT64_MAX
// 64-bit pointers
CometType cometTypePointer = (CometType){.typeKind = COMET_BIG };
#elif INTPTR_MAX == INT32_MAX
// 32-bit pointers
CometType cometTypePointer = (CometType){.typeKind = COMET_INT };
#else
#error "Unsupported pointer size"
#endif
static CometArrayType stringArray = {
.elem = &cometTypeSmall,
.isFixedSize = {false},

View File

@@ -163,6 +163,7 @@ bool methodIsGeneric(CometCompiler* c, CometMethod* method) {
CometType* resolveGenericType(char* genericValTypeName, List(GenericTypeMapping) resolvedGenericTypes) {
for (size_t genericIdx = 0; genericIdx < resolvedGenericTypes.count; genericIdx++) {
GenericTypeMapping* resolvedGeneric = get(resolvedGenericTypes, genericIdx);
printf("%s, %s\n", resolvedGeneric->genericTypeName, genericValTypeName);
if (strcmp(resolvedGeneric->genericTypeName, genericValTypeName) == 0) {
return &resolvedGeneric->newType;
@@ -208,7 +209,9 @@ CometStruct* getGenericStruct(CometCompiler* c, CometStruct* cometStruct, List(G
if (cometStruct->fieldTypes[fieldIdx].typeKind != COMET_GENERIC)
continue; // dont replace type of a field that doesnt use a generic type
newFieldTypes[fieldIdx] = *resolveGenericType(cometStruct->fieldTypes[fieldIdx].genericParamName, resolvedGenericTypes);
CometType* resolvedGenericType = resolveGenericType(cometStruct->fieldTypes[fieldIdx].genericParamName, resolvedGenericTypes);
printf("%p\n", resolvedGenericType);
newFieldTypes[fieldIdx] = *resolvedGenericType;
}
// fill in generic methods

View File

@@ -21,7 +21,6 @@ struct Block {
};
UseList(charptr);
UseList(uint64_t);
UseList(Block);

View File

@@ -1,5 +1,6 @@
func main() -> int {
ptr myPointer
import testlib
func main() -> int {
testlib.Pointer<int> x = new testlib.Pointer<int>(10, 4)
return 0
}

35
testlib.c Normal file
View File

@@ -0,0 +1,35 @@
#include "include/cometlib.h"
ResultType(int64_t, objectPtr) impl_Pointer_INIT(int64_t* args, CometVM* vm) {
CometObject* self = (CometObject*)args[0];
printf("%p\n", self);
printf("%p\n", args[1]);
printf("%p\n", args[2]);
self->fields[0] = args[1];
printf("a\n");
self->fields[1] = args[2];
printf("b\n");
return Success(int64_t, objectPtr, (int64_t)self);
}
on_import {
CometType genericType = cometGenericType("T");
List(charptr) genericTypeNames = newList(charptr);
append(genericTypeNames, "T");
CometStruct* ptrStruct = cometDefineGenericStruct(env, "Pointer", NULL, genericTypeNames);
List(StructField) fields = newList(StructField);
append(fields, cometCreateField("value", genericType));
append(fields, cometCreateField("size", cometTypeBig));
List(cometFuncPtr) methods = newList(cometFuncPtr);
//append(methods, cometDefineMethod(env, "resize", ptrStruct, cometTypeVoid, 1, false, cometTypeBig));
cometSetStructFieldsAndMethods(ptrStruct, fields, methods);
cometDefineConstructor(env, ptrStruct, 2, false, genericType, cometTypeBig);
}