From bc65c3f4fd80038559d0b7bdfb4b0763c6cabc70 Mon Sep 17 00:00:00 2001 From: nub31 Date: Mon, 16 Mar 2026 18:10:03 +0100 Subject: [PATCH] ... --- compiler/Generator.cs | 35 +++++++++++++++++++++++------------ compiler/ModuleGraph.cs | 3 ++- compiler/NubType.cs | 16 ++++++++++++++++ compiler/Parser.cs | 6 +++++- compiler/Program.cs | 6 +++--- compiler/TypeChecker.cs | 6 +++--- examples/core/sys.nub | 6 +++--- 7 files changed, 55 insertions(+), 23 deletions(-) diff --git a/compiler/Generator.cs b/compiler/Generator.cs index dffe355..61cd584 100644 --- a/compiler/Generator.cs +++ b/compiler/Generator.cs @@ -22,6 +22,19 @@ public class Generator #include #include #include + #include + + static inline void *nub_alloc(size_t size) + { + void *mem = malloc(size); + if (mem == NULL) + { + puts("Out of memory"); + exit(1); + } + + return mem; + } typedef struct { @@ -70,8 +83,8 @@ public class Generator { size_t new_length = left->length + right->length; - string_ptr result = (string_ptr)malloc(sizeof(string)); - result->data = (char*)malloc(new_length + 1); + string_ptr result = (string_ptr)nub_alloc(sizeof(string)); + result->data = (char*)nub_alloc(new_length + 1); memcpy(result->data, left->data, left->length); memcpy(result->data + left->length, right->data, right->length); @@ -88,8 +101,8 @@ public class Generator { size_t len = strlen(cstr); - string_ptr result = (string_ptr)malloc(sizeof(string)); - result->data = (char*)malloc(len + 1); + string_ptr result = (string_ptr)nub_alloc(sizeof(string)); + result->data = (char*)nub_alloc(len + 1); memcpy(result->data, cstr, len + 1); @@ -105,13 +118,9 @@ public class Generator { \ if ((xs)->count >= (xs)->capacity) \ { \ - if ((xs)->capacity == 0) \ - (xs)->capacity = 256; \ - else \ - (xs)->capacity *= 2; \ + (xs)->capacity *= 2; \ (xs)->items = realloc((xs)->items, (xs)->capacity * sizeof(*(xs)->items)); \ } \ - \ (xs)->items[(xs)->count++] = (x); \ } while (0) @@ -405,6 +414,7 @@ public class Generator } writer.WriteLine("}"); writer.WriteLine(); + writer.WriteLine("free(array->items);"); writer.WriteLine("free(array);"); } writer.WriteLine("}"); @@ -416,11 +426,11 @@ public class Generator writer.WriteLine("{"); using (writer.Indent()) { - writer.WriteLine($"{name} array = ({name})malloc(sizeof({backingName}));"); + writer.WriteLine($"{name} array = ({name})nub_alloc(sizeof({backingName}));"); writer.WriteLine("array->ref = 1;"); writer.WriteLine("array->count = 0;"); - writer.WriteLine("array->capacity = 0;"); - writer.WriteLine("array->items = NULL;"); + writer.WriteLine("array->capacity = 10;"); + writer.WriteLine($"array->items = ({TypeName(arrayType.ElementType)}*)nub_alloc(sizeof({TypeName(arrayType.ElementType)}) * array->capacity);"); writer.WriteLine("return array;"); } writer.WriteLine("}"); @@ -856,6 +866,7 @@ public class Generator NubTypeUInt t => $"uint{t.Width}_t", NubTypePointer => Tmp(), NubTypeString => "string_ptr", + NubTypeChar => "char", NubTypeFunc => Tmp(), NubTypeArray => Tmp(), _ => throw new NotImplementedException(), diff --git a/compiler/ModuleGraph.cs b/compiler/ModuleGraph.cs index fb45918..d09013d 100644 --- a/compiler/ModuleGraph.cs +++ b/compiler/ModuleGraph.cs @@ -210,6 +210,7 @@ public class ModuleGraph NodeTypeSInt type => NubTypeSInt.Get(type.Width), NodeTypeUInt type => NubTypeUInt.Get(type.Width), NodeTypeString => NubTypeString.Instance, + NodeTypeChar => NubTypeChar.Instance, NodeTypeVoid => NubTypeVoid.Instance, NodeTypeArray type => NubTypeArray.Get(ResolveType(type.ElementType, currentModule)), _ => throw new ArgumentOutOfRangeException(nameof(node)) @@ -442,4 +443,4 @@ public class Module(string name) public NubType? Type { get; } = type; } } -} \ No newline at end of file +} diff --git a/compiler/NubType.cs b/compiler/NubType.cs index 2fa7f87..bab473c 100644 --- a/compiler/NubType.cs +++ b/compiler/NubType.cs @@ -102,6 +102,17 @@ public class NubTypeString : NubType public override string ToString() => "string"; } +public class NubTypeChar : NubType +{ + public static readonly NubTypeChar Instance = new(); + + private NubTypeChar() + { + } + + public override string ToString() => "char"; +} + public class NubTypeStruct : NubType { private static readonly Dictionary<(string Module, string Name), NubTypeStruct> Cache = new(); @@ -324,6 +335,10 @@ public class TypeEncoder sb.Append('S'); break; + case NubTypeChar: + sb.Append('C'); + break; + case NubTypePointer p: sb.Append("P("); EncodeType(sb, p.To); @@ -420,6 +435,7 @@ public class TypeDecoder 'U' => DecodeUInt(), 'I' => DecodeSInt(), 'S' => NubTypeString.Instance, + 'C' => NubTypeChar.Instance, 'P' => DecodePointer(), 'F' => DecodeFunc(), 'T' => DecodeStruct(), diff --git a/compiler/Parser.cs b/compiler/Parser.cs index a567fed..b82ae2b 100644 --- a/compiler/Parser.cs +++ b/compiler/Parser.cs @@ -561,6 +561,8 @@ public class Parser return new NodeTypeVoid(TokensFrom(startIndex)); case "string": return new NodeTypeString(TokensFrom(startIndex)); + case "char": + return new NodeTypeChar(TokensFrom(startIndex)); case "bool": return new NodeTypeBool(TokensFrom(startIndex)); case "i8": @@ -1060,6 +1062,8 @@ public class NodeTypeBool(List tokens) : NodeType(tokens); public class NodeTypeString(List tokens) : NodeType(tokens); +public class NodeTypeChar(List tokens) : NodeType(tokens); + public class NodeTypeNamed(List tokens, List sections) : NodeType(tokens) { public List Sections { get; } = sections; @@ -1090,4 +1094,4 @@ public class NodeTypeFunc(List tokens, List parameters, NodeTyp { public List Parameters { get; } = parameters; public NodeType ReturnType { get; } = returnType; -} \ No newline at end of file +} diff --git a/compiler/Program.cs b/compiler/Program.cs index 8234f95..38bb364 100644 --- a/compiler/Program.cs +++ b/compiler/Program.cs @@ -151,13 +151,13 @@ var outFile = Generator.Emit(functions, moduleGraph, entryPoint); if (compileLib) { - Process.Start("gcc", ["-Og", "-g", "-fno-builtin", "-c", "-o", ".build/out.o", outFile, .. archivePaths]).WaitForExit(); + Process.Start("gcc", ["-Og", "-g", "-Wall", "-Werror", "-c", "-o", ".build/out.o", outFile, .. archivePaths]).WaitForExit(); Process.Start("ar", ["rcs", ".build/out.a", ".build/out.o"]).WaitForExit(); NubLib.Pack(".build/out.nublib", ".build/out.a", Manifest.Create(moduleGraph)); } else { - Process.Start("gcc", ["-Og", "-g", "-fno-builtin", "-o", ".build/out", outFile, .. archivePaths]).WaitForExit(); + Process.Start("gcc", ["-Og", "-g", "-Wall", "-Werror", "-o", ".build/out", outFile, .. archivePaths]).WaitForExit(); } return 0; @@ -176,4 +176,4 @@ static void CleanDirectory(string dirName) CleanDirectory(subdir.FullName); subdir.Delete(); } -} \ No newline at end of file +} diff --git a/compiler/TypeChecker.cs b/compiler/TypeChecker.cs index fa59e9e..7b20534 100644 --- a/compiler/TypeChecker.cs +++ b/compiler/TypeChecker.cs @@ -494,7 +494,7 @@ public class TypeChecker case "length": return new TypedNodeExpressionStringLength(expression.Tokens, NubTypeUInt.Get(64), target); case "ptr": - return new TypedNodeExpressionStringPointer(expression.Tokens, NubTypePointer.Get(NubTypeUInt.Get(8)), target); + return new TypedNodeExpressionStringPointer(expression.Tokens, NubTypePointer.Get(NubTypeChar.Instance), target); default: throw BasicError($"'{expression.Name.Ident}' is not a member of type {stringType}", expression.Name); } @@ -684,7 +684,7 @@ public class TypeChecker private TypedNodeExpressionStringConstructor CheckExpressionStringConstructor(NodeExpressionStringConstructor expression, NubType? expectedType) { - var stringPoitnerType = NubTypePointer.Get(NubTypeUInt.Get(8)); + var stringPoitnerType = NubTypePointer.Get(NubTypeChar.Instance); var value = CheckExpression(expression.Value, stringPoitnerType); if (!value.Type.IsAssignableTo(stringPoitnerType)) @@ -1103,4 +1103,4 @@ public class TypedNodeExpressionUnary(List tokens, NubType type, TypedNod Negate, Invert, } -} \ No newline at end of file +} diff --git a/examples/core/sys.nub b/examples/core/sys.nub index 1ca9d13..1de4ac4 100644 --- a/examples/core/sys.nub +++ b/examples/core/sys.nub @@ -1,5 +1,5 @@ module sys -export extern func read(fd: u32, buf: ^u8, count: u64): i64 -export extern func write(fd: u32, buf: ^u8, count: u64): i64 -export extern func open(fileName: ^u8, flags: i32, mode: u16): i64 \ No newline at end of file +export extern func read(fd: u32, buf: ^char, count: u64): i64 +export extern func write(fd: u32, buf: ^char, count: u64): i64 +export extern func open(fileName: ^char, flags: i32, mode: u16): i64