aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorBruce Hill <bruce@bruce-hill.com>2025-04-16 00:09:57 -0400
committerBruce Hill <bruce@bruce-hill.com>2025-04-16 00:09:57 -0400
commita2d2916e3220ec333122afb9cdef0f5c1eda84f7 (patch)
treed06b95f8d7bec5439eb804a3ff3045907a218d31 /src
parente5420471a7364a92521575e7abd3a29a9318001b (diff)
Fixes to get the compiler to build with -O3
Diffstat (limited to 'src')
-rw-r--r--src/compile.c12
-rw-r--r--src/parse.c12
-rw-r--r--src/stdlib/lists.c8
-rw-r--r--src/stdlib/tables.c2
-rw-r--r--src/typecheck.c13
5 files changed, 27 insertions, 20 deletions
diff --git a/src/compile.c b/src/compile.c
index 0a847093..5c153f87 100644
--- a/src/compile.c
+++ b/src/compile.c
@@ -1396,8 +1396,8 @@ static CORD _compile_statement(env_t *env, ast_t *ast)
static int defer_id = 0;
env_t *defer_env = fresh_scope(env);
CORD code = CORD_EMPTY;
- for (int64_t i = 1; i <= Table$length(closed_vars); i++) {
- struct { const char *name; binding_t *b; } *entry = Table$entry(closed_vars, i);
+ for (int64_t i = 0; i < closed_vars.entries.length; i++) {
+ struct { const char *name; binding_t *b; } *entry = closed_vars.entries.data + closed_vars.entries.stride*i;
if (entry->b->type->tag == ModuleType)
continue;
if (CORD_ncmp(entry->b->code, 0, "userdata->", 0, strlen("userdata->")) == 0) {
@@ -2995,8 +2995,8 @@ CORD compile(env_t *env, ast_t *ast)
Table_t closed_vars = get_closed_vars(env, lambda->args, ast);
if (Table$length(closed_vars) > 0) { // Create a typedef for the lambda's closure userdata
CORD def = "typedef struct {";
- for (int64_t i = 1; i <= Table$length(closed_vars); i++) {
- struct { const char *name; binding_t *b; } *entry = Table$entry(closed_vars, i);
+ for (int64_t i = 0; i < closed_vars.entries.length; i++) {
+ struct { const char *name; binding_t *b; } *entry = closed_vars.entries.data + closed_vars.entries.stride*i;
if (has_stack_memory(entry->b->type))
code_err(ast, "This function is holding onto a reference to ", type_to_str(entry->b->type),
" stack memory in the variable `", entry->name, "`, but the function may outlive the stack memory");
@@ -3021,8 +3021,8 @@ CORD compile(env_t *env, ast_t *ast)
userdata = "NULL";
} else {
userdata = CORD_all("new(", name, "$userdata_t");
- for (int64_t i = 1; i <= Table$length(closed_vars); i++) {
- struct { const char *name; binding_t *b; } *entry = Table$entry(closed_vars, i);
+ for (int64_t i = 0; i < closed_vars.entries.length; i++) {
+ struct { const char *name; binding_t *b; } *entry = closed_vars.entries.data + closed_vars.entries.stride*i;
if (entry->b->type->tag == ModuleType)
continue;
binding_t *b = get_binding(env, entry->name);
diff --git a/src/parse.c b/src/parse.c
index 93a2dcdd..4eae21e5 100644
--- a/src/parse.c
+++ b/src/parse.c
@@ -309,7 +309,9 @@ PUREFUNC static INLINE int64_t get_indent(parse_ctx_t *ctx, const char *pos)
{
int64_t line_num = get_line_number(ctx->file, pos);
const char *line = get_line(ctx->file, line_num);
- if (*line == ' ') {
+ if (line == NULL) {
+ return 0;
+ } else if (*line == ' ') {
int64_t spaces = (int64_t)strspn(line, " ");
if (line[spaces] == '\t')
parser_err(ctx, line + spaces, line + spaces + 1, "This is a tab following spaces, and you can't mix tabs and spaces");
@@ -873,8 +875,8 @@ PARSER(parse_reduction) {
);
if (progress) key = new_term;
}
- if (key->tag == Var) key = NULL;
- else pos = key->end;
+ if (key && key->tag == Var) key = NULL;
+ else if (key) pos = key->end;
whitespace(&pos);
if (!match(&pos, ":")) return NULL;
@@ -1662,8 +1664,8 @@ static ast_t *parse_infix_expr(parse_ctx_t *ctx, const char *pos, int min_tightn
);
if (progress) key = new_term;
}
- if (key->tag == Var) key = NULL;
- else pos = key->end;
+ if (key && key->tag == Var) key = NULL;
+ else if (key) pos = key->end;
}
whitespace(&pos);
diff --git a/src/stdlib/lists.c b/src/stdlib/lists.c
index af0d1e0a..f5be09e9 100644
--- a/src/stdlib/lists.c
+++ b/src/stdlib/lists.c
@@ -76,11 +76,15 @@ public void List$insert(List_t *list, const void *item, Int_t int_index, int64_t
list->data_refcount = 0;
list->stride = padded_item_size;
} else {
- if (index != list->length+1)
+ if (index != list->length+1) {
+ assert(list->length >= index);
+ size_t size = (size_t)((list->length - index + 1)*padded_item_size);
+ assert(size < SIZE_MAX);
memmove(
list->data + index*padded_item_size,
list->data + (index-1)*padded_item_size,
- (size_t)((list->length - index + 1)*padded_item_size));
+ size);
+ }
}
assert(list->free > 0);
--list->free;
diff --git a/src/stdlib/tables.c b/src/stdlib/tables.c
index c01ac25e..c26fd798 100644
--- a/src/stdlib/tables.c
+++ b/src/stdlib/tables.c
@@ -556,7 +556,7 @@ PUREFUNC public uint64_t Table$hash(const void *obj, const TypeInfo_t *type)
keys_hash ^= generic_hash(t->entries.data + i*t->entries.stride, table.key);
}
- struct {
+ volatile struct {
int64_t length;
uint64_t keys_hash, values_hash;
Table_t *fallback;
diff --git a/src/typecheck.c b/src/typecheck.c
index 42f37224..8f47433c 100644
--- a/src/typecheck.c
+++ b/src/typecheck.c
@@ -479,8 +479,9 @@ void bind_statement(env_t *env, ast_t *statement)
env_t *module_env = load_module(env, statement);
if (!module_env) break;
for (Table_t *bindings = module_env->locals; bindings != module_env->globals; bindings = bindings->fallback) {
- for (int64_t i = 1; i <= Table$length(*bindings); i++) {
- struct {const char *name; binding_t *binding; } *entry = Table$entry(*bindings, i);
+ List_t entries = bindings->entries;
+ for (int64_t i = 0; i < entries.length; i++) {
+ struct { const char *name; binding_t *binding; } *entry = entries.data + entries.stride*i;
if (entry->name[0] == '_' || streq(entry->name, "main"))
continue;
binding_t *b = Table$str_get(*env->locals, entry->name);
@@ -490,8 +491,8 @@ void bind_statement(env_t *env, ast_t *statement)
code_err(statement, "This module imports a symbol called '", entry->name, "', which would clobber another variable");
}
}
- for (int64_t i = 1; i <= Table$length(*module_env->types); i++) {
- struct {const char *name; type_t *type; } *entry = Table$entry(*module_env->types, i);
+ for (int64_t i = 0; i < module_env->types->entries.length; i++) {
+ struct { const char *name; type_t *type; } *entry = module_env->types->entries.data + module_env->types->entries.stride*i;
if (entry->name[0] == '_')
continue;
if (Table$str_get(*env->types, entry->name))
@@ -689,7 +690,7 @@ type_t *get_type(env_t *env, ast_t *ast)
binding_t *b = get_binding(env, lang);
if (!b || b->type->tag != TypeInfoType || Match(b->type, TypeInfoType)->type->tag != TextType)
code_err(ast, "There is no text language called '", lang, "'");
- return Match(get_binding(env, lang)->type, TypeInfoType)->type;
+ return Match(b->type, TypeInfoType)->type;
} else {
return TEXT_TYPE;
}
@@ -1393,7 +1394,7 @@ type_t *get_type(env_t *env, ast_t *ast)
}
if (when->else_body)
t = type_or_type(t, get_type(env, when->else_body));
- else if (t->tag != OptionalType)
+ else if (t && t->tag != OptionalType)
t = Type(OptionalType, .type=t);
return t;
}