From 2ea86eaa3df4727d86306bbfb0f17ec6bd82fa90 Mon Sep 17 00:00:00 2001 From: Zuhaitz Méndez Fernández de Aránguiz Date: Wed, 14 Jan 2026 12:48:37 +0000 Subject: Changed (non-standard) to a more standard approach with . --- src/ast/ast.h | 3 ++- src/codegen/codegen_decl.c | 17 +++++++++---- src/parser/parser_expr.c | 2 +- std/io.zc | 62 +++++++++++++++++++++++++++++++++++----------- 4 files changed, 63 insertions(+), 21 deletions(-) diff --git a/src/ast/ast.h b/src/ast/ast.h index cf082a7..a5d3d0a 100644 --- a/src/ast/ast.h +++ b/src/ast/ast.h @@ -54,7 +54,8 @@ typedef struct Type struct Type **args; // For GENERIC args. int arg_count; int is_const; - union { + union + { int array_size; // For fixed-size arrays [T; N]. int is_varargs; // For function types (...). int is_restrict; // For restrict pointers. diff --git a/src/codegen/codegen_decl.c b/src/codegen/codegen_decl.c index 4979236..42e0ba9 100644 --- a/src/codegen/codegen_decl.c +++ b/src/codegen/codegen_decl.c @@ -93,11 +93,18 @@ void emit_preamble(ParserContext *ctx, FILE *out) "\"Assertion failed: \" " "__VA_ARGS__); exit(1); }\n", out); - fputs("string _z_readln_raw() { char *line = NULL; size_t len = 0; " - "if(getline(&line, &len, " - "stdin) == -1) return NULL; if(strlen(line) > 0 && " - "line[strlen(line)-1] == '\\n') " - "line[strlen(line)-1] = 0; return line; }\n", + fputs("string _z_readln_raw() { " + "size_t cap = 64; size_t len = 0; " + "char *line = z_malloc(cap); " + "if(!line) return NULL; " + "int c; " + "while((c = fgetc(stdin)) != EOF) { " + "if(c == '\\n') break; " + "if(len + 1 >= cap) { cap *= 2; char *n = z_realloc(line, cap); " + "if(!n) { z_free(line); return NULL; } line = n; } " + "line[len++] = c; } " + "if(len == 0 && c == EOF) { z_free(line); return NULL; } " + "line[len] = 0; return line; }\n", out); fputs("int _z_scan_helper(const char *fmt, ...) { char *l = " "_z_readln_raw(); if(!l) return " diff --git a/src/parser/parser_expr.c b/src/parser/parser_expr.c index 9861de6..b9a1c35 100644 --- a/src/parser/parser_expr.c +++ b/src/parser/parser_expr.c @@ -2335,7 +2335,7 @@ ASTNode *parse_expr_prec(ParserContext *ctx, Lexer *l, Precedence min_prec) call->type_info = type_new(TYPE_INT); ASTNode *fmt_node = ast_create(NODE_EXPR_LITERAL); - fmt_node->literal.type_kind = 2; + fmt_node->literal.type_kind = TOK_STRING; fmt_node->literal.string_val = xstrdup(fmt); ASTNode *head = fmt_node, *tail = fmt_node; diff --git a/std/io.zc b/std/io.zc index e7b6300..02018a8 100644 --- a/std/io.zc +++ b/std/io.zc @@ -19,25 +19,59 @@ raw { va_end(args); return buffer; } + + void* _z_get_stdin() + { + return stdin; + } + + int _z_get_eof() + { + return EOF; + } + + int _z_fgetc(void* stream) + { + return fgetc((FILE*)stream); + } } -raw { - char* readln() { - char* line = NULL; - size_t len = 0; - ssize_t read; - - read = getline(&line, &len, stdin); - - if (read != -1) { - // Remove newline if present - if (line[read - 1] == '\n') { - line[read - 1] = '\0'; + + +fn readln() -> char* { + var cap: usize = 64; + var len: usize = 0; + var line: char* = malloc(cap); + if (line == NULL) return NULL; + + var c: int; + var std_in = _z_get_stdin(); + var eof_val = _z_get_eof(); + + while (true) { + c = _z_fgetc(std_in); + if (c == eof_val) break; + if (c == 10) break; // '\n' + + if (len + 1 >= cap) { + cap = cap * 2; + var n = realloc(line, cap); + if (n == NULL) { + free(line); + return NULL; } - return line; + line = n; } - if (line) free(line); + line[len] = c; + len = len + 1; + } + + if (len == 0 && c == eof_val) { + free(line); return NULL; } + + line[len] = 0; + return line; } -- cgit v1.2.3