From: Mike Lowis Date: Mon, 17 Jun 2024 18:41:41 +0000 (-0400) Subject: implemented object and string functions. Still need array and dict functions X-Git-Url: https://git.mdlowis.com/?a=commitdiff_plain;h=6b05e5bd3540a2f276f61d5a85f87b8468eb7adc;p=proto%2Fcerise-c.git implemented object and string functions. Still need array and dict functions --- diff --git a/build.sh b/build.sh index 59796c2..a9d571c 100755 --- a/build.sh +++ b/build.sh @@ -2,8 +2,9 @@ for f in runtime/*.c; do printf "CC %s\n" "$f" - gcc -c -I. -O2 -o "${f%.c}.o" "$f" + gcc -c -I. -O2 -o "${f%.c}.o" "$f" & done +wait printf "LIB %s\n" libruntime.a ar rcs libruntime.a runtime/*.o @@ -11,4 +12,3 @@ printf "\n" ./cerise-c.rb > cerise-c.c \ && gcc -I. -O2 -o cerise-c cerise-c.c libruntime.a \ && ./cerise-c - diff --git a/cerise-c.rb b/cerise-c.rb index 113f15a..9fec3fe 100755 --- a/cerise-c.rb +++ b/cerise-c.rb @@ -1160,10 +1160,10 @@ module Codegen end elsif v.value.is_a? Hash - putln state, "Value #{var} = MakeHash(#{v.value.length});" + putln state, "Value #{var} = MakeDict(#{v.value.length});" v.value.each do |k, v| val = emit(state, v) - putln state, "Hash_Set(#{var}, MakeString(#{k.value}), #{val});" + putln state, "Dict_Set(#{var}, MakeString(#{k.value}), #{val});" end else raise "code emitting constants of this type not implemented" diff --git a/runtime.h b/runtime.h index 92b118f..c18c973 100644 --- a/runtime.h +++ b/runtime.h @@ -26,7 +26,7 @@ //#define VALUE_TRUE 0x3llu //#define NAN_TAG_RECORD 0x0000000000000000llu -//#define NAN_TAG_ARRAY 0x0001000000000000llu +#define NAN_TAG_ARRAY 0x0001000000000000llu #define NAN_TAG_STRING 0x0002000000000000llu //#define NAN_TAG_BLOCK 0x0003000000000000llu //#define NAN_TAG_NATIVE 0x0004000000000000llu @@ -52,8 +52,8 @@ typedef union { typedef struct { uint64_t length; - char bytes[]; -} String; + Value values[]; +} Array; /* Value Tests @@ -91,6 +91,14 @@ static inline bool IsString(Value val) { return (val.as_uint64 & HIGH16_TAG) == NAN_TAG_STRING; } +static inline bool IsArray(Value val) { + return (val.as_uint64 & HIGH16_TAG) == NAN_TAG_STRING; +} + +static inline bool IsDict(Value val) { + return (val.as_uint64 & HIGH16_TAG) == NAN_TAG_STRING; +} + /* C Type Conversions *************************************************/ @@ -161,34 +169,9 @@ static inline Value MakeReal(double d) { return val; } -static inline Value MakeString(char* s) { - size_t sz = strlen(s); - String* str = calloc(sizeof(String) + sz + 1, 1); - str->length = sz; - strncpy(str->bytes, s, sz+1); - return (Value){ - .as_uint64 = (NAN_TAG_STRING | (uint64_t)str) - }; -} - -static inline Value MakeArray(int32_t nslots) { -// Value* record = calloc(2,sizeof(Value)); -// record[0] = MakeInt(1); -// record[1] = MakeInt(nslots); // -// record[2] = MakeInt(nslots); // -// return (Value){ .as_uint64 = (NAN_TAG_ARRAY | (uintptr_t)record) }; - return MakeNil(); -} - - -static inline Value MakeHash(int32_t nslots) { -// Value* record = calloc(2,sizeof(Value)); -// record[0] = MakeInt(1); -// record[1] = MakeInt(nslots); // -// record[2] = MakeInt(nslots); // -// return (Value){ .as_uint64 = (NAN_TAG_ARRAY | (uintptr_t)record) }; - return MakeNil(); -} +Value MakeString(char* s); +Value MakeArray(int32_t nslots); +Value MakeDict(int32_t nslots); /* Value Type Conversions @@ -222,11 +205,14 @@ Value OpNeq(Value left, Value right); /* Arrays And Hashes *************************************************/ +void String_Set(Value array, int index, Value value); +Value String_Get(Value array, int index); + void Array_Set(Value array, int index, Value value); Value Array_Get(Value array, int index); -void Hash_Set(Value hash, Value key, Value value); -Value Hash_Get(Value hash, Value key); +void Dict_Set(Value hash, Value key, Value value); +Value Dict_Get(Value hash, Value key); Value Object_Get(Value object, Value key); -Value Object_Set(Value object, Value key, Value value); +void Object_Set(Value object, Value key, Value value); diff --git a/runtime/Array.c b/runtime/Array.c index 7b92b95..b92f5e5 100644 --- a/runtime/Array.c +++ b/runtime/Array.c @@ -1,5 +1,14 @@ #include "runtime.h" +Value MakeArray(int32_t nslots) { +// Value* record = calloc(2,sizeof(Value)); +// record[0] = MakeInt(1); +// record[1] = MakeInt(nslots); // +// record[2] = MakeInt(nslots); // +// return (Value){ .as_uint64 = (NAN_TAG_ARRAY | (uintptr_t)record) }; + return MakeNil(); +} + void Array_Set(Value array, int index, Value value) { } diff --git a/runtime/Hash.c b/runtime/Hash.c index b644ae5..28b031e 100644 --- a/runtime/Hash.c +++ b/runtime/Hash.c @@ -1,10 +1,19 @@ #include "runtime.h" -void Hash_Set(Value hash, Value key, Value value) +Value MakeDict(int32_t nslots) { +// Value* record = calloc(2,sizeof(Value)); +// record[0] = MakeInt(1); +// record[1] = MakeInt(nslots); // +// record[2] = MakeInt(nslots); // +// return (Value){ .as_uint64 = (NAN_TAG_ARRAY | (uintptr_t)record) }; + return MakeNil(); +} + +void Dict_Set(Value hash, Value key, Value value) { } -Value Hash_Get(Value hash, Value key) +Value Dict_Get(Value hash, Value key) { return MakeNil(); } diff --git a/runtime/Object.c b/runtime/Object.c index 0e0318f..153416d 100644 --- a/runtime/Object.c +++ b/runtime/Object.c @@ -2,10 +2,26 @@ Value Object_Get(Value object, Value key) { - return MakeNil(); + Value result = MakeNil(); + if (IsDict(object)) { + result = Dict_Get(object, key); + } else if (IsArray(object)) { + result = Array_Get(object, ValueAsInt(key)); + } else if (IsString(object)) { + result = String_Get(object, ValueAsInt(key)); + } else { + Error(MakeString("object is not indexable")); + } + return result; } -Value Object_Set(Value object, Value key, Value value) +void Object_Set(Value object, Value key, Value value) { - return MakeNil(); + if (IsDict(object)) { + Dict_Set(object, key, value); + } else if (IsArray(object)) { + Array_Set(object, ValueAsInt(key), value); + } else { + Error(MakeString("object is not assignable")); + } } diff --git a/runtime/String.c b/runtime/String.c new file mode 100644 index 0000000..3fea402 --- /dev/null +++ b/runtime/String.c @@ -0,0 +1,20 @@ +#include "runtime.h" + +Value MakeString(char* s) { + size_t sz = strlen(s); + String* str = calloc(sizeof(String) + sz + 1, 1); + str->length = sz; + strncpy(str->bytes, s, sz+1); + return (Value){ + .as_uint64 = (NAN_TAG_STRING | (uint64_t)str) + }; +} + +Value String_Get(Value hash, int index) +{ + String* str = ValueAsString(hash); + if (index >= str->length) { + Error(MakeString("string index out of bounds")); + } + return MakeInt( str->bytes[index] ); +}