Various fixes, including for Null values

This commit is contained in:
Bruce Hill 2024-02-17 23:43:55 -05:00
parent 2345c8c5c9
commit fbf39cd7e9
6 changed files with 27 additions and 25 deletions

View File

@ -7,6 +7,15 @@
#include "functions.h"
#include "types.h"
// Convert negative indices to back-indexed without branching: index0 = index + (index < 0)*(len+1)) - 1
#define $index(x, i) _Generic(x, array_t: ({ __typeof(x) $obj; int64_t $offset = i; $offset += ($offset < 0) * ($obj.length + 1) - 1; assert($offset >= 0 && offset < $obj.length); $obj.data + $obj.stride * $offset;}))
#define $safe_index(x, i) _Generic(x, array_t: ({ __typeof(x) $obj; int64_t $offset = i - 1; $obj.data + $obj.stride * $offset;}))
#define $array(x, ...) ({ __typeof(x) $items[] = {x, __VA_ARGS__}; \
(array_t){.length=sizeof($items)/sizeof($items[0]), \
.stride=(int64_t)&$items[1] - (int64_t)&$items[0], \
.data=memcpy(GC_MALLOC(sizeof($items)), $items, sizeof($items)), \
.copy_on_write=1}; })
void Array__insert(array_t *arr, const void *item, int64_t index, const TypeInfo *type);
void Array__insert_all(array_t *arr, array_t to_insert, int64_t index, const TypeInfo *type);
void Array__remove(array_t *arr, int64_t index, int64_t count, const TypeInfo *type);

View File

@ -10,6 +10,7 @@ int32_t Pointer__compare(const void *x, const void *y, const TypeInfo *type);
bool Pointer__equal(const void *x, const void *y, const TypeInfo *type);
uint32_t Pointer__hash(const void *x, const TypeInfo *type);
#define $Null(t) (t*)NULL
#define POINTER_TYPE(_sigil, _pointed) (&(TypeInfo){\
.size=sizeof(void*), .align=alignof(void*), .tag=PointerInfo, .PointerInfo.sigil=_sigil, .PointerInfo.pointed=_pointed})

View File

@ -10,7 +10,7 @@
#include "typecheck.h"
#include "util.h"
CORD compile_type(env_t *env, type_ast_t *t)
CORD compile_type_ast(env_t *env, type_ast_t *t)
{
(void)env;
switch (t->tag) {
@ -31,8 +31,9 @@ CORD compile_statement(env_t *env, ast_t *ast)
stmt = CORD_asprintf("(void)%r;", compile(env, ast));
break;
}
int64_t line = get_line_number(ast->file, ast->start);
return stmt ? CORD_asprintf("#line %ld\n%r", line, stmt) : stmt;
// int64_t line = get_line_number(ast->file, ast->start);
// return stmt ? CORD_asprintf("#line %ld\n%r", line, stmt) : stmt;
return stmt;
}
CORD expr_as_string(env_t *env, CORD expr, type_t *t, CORD color)
@ -63,7 +64,7 @@ CORD compile_string(env_t *env, ast_t *ast, CORD color)
CORD compile(env_t *env, ast_t *ast)
{
switch (ast->tag) {
case Nil: return CORD_asprintf("(%r)NULL", compile_type(env, Match(ast, Nil)->type));
case Nil: return CORD_asprintf("$Null(%r)", compile_type_ast(env, Match(ast, Nil)->type));
case Bool: return Match(ast, Bool)->b ? "yes" : "no";
case Var: return Match(ast, Var)->name;
case Int: return CORD_asprintf("I%ld(%ld)", Match(ast, Int)->bits, Match(ast, Int)->i);
@ -300,6 +301,7 @@ CORD compile(env_t *env, ast_t *ast)
case Declare: {
auto decl = Match(ast, Declare);
return CORD_asprintf("$var(%r, %r);", compile(env, decl->var), compile(env, decl->value));
// return CORD_asprintf("auto %r = %r;", compile(env, decl->var), compile(env, decl->value));
}
case Assign: {
auto assign = Match(ast, Assign);
@ -339,20 +341,20 @@ CORD compile(env_t *env, ast_t *ast)
case FunctionDef: {
auto fndef = Match(ast, FunctionDef);
CORD name = compile(env, fndef->name);
CORD_appendf(&env->code->staticdefs, "static %r %r_(", fndef->ret_type ? compile_type(env, fndef->ret_type) : "void", name);
CORD_appendf(&env->code->staticdefs, "static %r %r_(", fndef->ret_type ? compile_type_ast(env, fndef->ret_type) : "void", name);
for (arg_ast_t *arg = fndef->args; arg; arg = arg->next) {
CORD_appendf(&env->code->staticdefs, "%r %s", compile_type(env, arg->type), arg->name);
CORD_appendf(&env->code->staticdefs, "%r %s", compile_type_ast(env, arg->type), arg->name);
if (arg->next) env->code->staticdefs = CORD_cat(env->code->staticdefs, ", ");
}
env->code->staticdefs = CORD_cat(env->code->staticdefs, ");\n");
CORD kwargs = CORD_asprintf("#define %r(...) ({ struct {", name);
CORD passed_args = CORD_EMPTY;
CORD_appendf(&env->code->funcs, "%r %r_(", fndef->ret_type ? compile_type(env, fndef->ret_type) : "void", name);
CORD_appendf(&env->code->funcs, "%r %r_(", fndef->ret_type ? compile_type_ast(env, fndef->ret_type) : "void", name);
env_t *body_scope = fresh_scope(env);
body_scope->locals->fallback = env->globals;
for (arg_ast_t *arg = fndef->args; arg; arg = arg->next) {
CORD arg_type = compile_type(env, arg->type);
CORD arg_type = compile_type_ast(env, arg->type);
CORD_appendf(&env->code->funcs, "%r %s", arg_type, arg->name);
if (arg->next) env->code->funcs = CORD_cat(env->code->funcs, ", ");
CORD_appendf(&kwargs, "%r %s; ", arg_type, arg->name);
@ -401,7 +403,7 @@ CORD compile(env_t *env, ast_t *ast)
CORD index = for_->index ? compile(env, for_->index) : "$i";
return CORD_asprintf("{\n"
"$var($iter, %r);\n"
"for (int64_t %r = 1, $len = $length($iter); %r <= $len; ++%r) {\n"
"for (int64_t %r = 1, $len = ($iter).length; %r <= $len; ++%r) {\n"
"$var(%r, $safe_index($iter, %s));\n"
"%r\n"
"}\n}",
@ -433,7 +435,7 @@ CORD compile(env_t *env, ast_t *ast)
CORD_appendf(&env->code->typecode, "struct %s_s {\n", def->name);
for (arg_ast_t *field = def->fields; field; field = field->next) {
CORD type = compile_type(env, field->type);
CORD type = compile_type_ast(env, field->type);
CORD_appendf(&env->code->typecode, "%r %s%s;\n", type, field->name,
CORD_cmp(type, "Bool_t") ? "" : ":1");
}
@ -484,7 +486,7 @@ CORD compile(env_t *env, ast_t *ast)
for (tag_ast_t *tag = def->tags; tag; tag = tag->next) {
env->code->typecode = CORD_cat(env->code->typecode, "struct {\n");
for (arg_ast_t *field = tag->fields; field; field = field->next) {
CORD type = compile_type(env, field->type);
CORD type = compile_type_ast(env, field->type);
CORD_appendf(&env->code->typecode, "%r %s%s;\n", type, field->name,
CORD_cmp(type, "Bool_t") ? "" : ":1");
}
@ -500,9 +502,9 @@ CORD compile(env_t *env, ast_t *ast)
if (test->expr->tag == Declare) {
auto decl = Match(test->expr, Declare);
return CORD_asprintf(
"$var(%r, %r);\n"
"%r\n"
"__doctest(&%r, %r, %r, %r, %ld, %ld);",
compile(env, decl->var), compile(env, decl->value),
compile(env, test->expr),
compile(env, decl->var),
compile_type_info(env, get_type(env, decl->value)),
compile(env, WrapAST(test->expr, StringLiteral, .cord=test->output)),

View File

@ -7,7 +7,7 @@
#include "util.h"
#include "environment.h"
CORD compile_type(env_t *env, type_ast_t *t);
CORD compile_type_ast(env_t *env, type_ast_t *t);
CORD compile(env_t *env, ast_t *ast);
CORD compile_statement(env_t *env, ast_t *ast);
CORD compile_type_info(env_t *env, type_t *t);

View File

@ -56,9 +56,8 @@ int main(int argc, char *argv[])
bind_statement(env, stmt->ast);
}
CORD fileinfo = CORD_asprintf("#line 0 %r\n", Str__quoted(f->filename, false));
CORD program = CORD_all(
fileinfo,
// CORD_asprintf("#line 0 %r\n", Str__quoted(f->filename, false)),
"// Generated code:\n",
env->code->imports, "\n",
env->code->typedefs, "\n",

View File

@ -40,15 +40,6 @@ CORD as_cord(void *x, bool use_color, const char *fmt, ...);
default: "???")
#define $heap(x) (__typeof(x)*)memcpy(GC_MALLOC(sizeof(x)), (__typeof(x)[1]){x}, sizeof(x))
#define $stack(x) (__typeof(x)*)((__typeof(x)[1]){x})
#define $length(x) _Generic(x, default: (x).length)
// Convert negative indices to back-indexed without branching: index0 = index + (index < 0)*(len+1)) - 1
#define $index(x, i) _Generic(x, array_t: ({ __typeof(x) $obj; int64_t $offset = i; $offset += ($offset < 0) * ($obj.length + 1) - 1; assert($offset >= 0 && offset < $obj.length); $obj.data + $obj.stride * $offset;}))
#define $safe_index(x, i) _Generic(x, array_t: ({ __typeof(x) $obj; int64_t $offset = i - 1; $obj.data + $obj.stride * $offset;}))
#define $array(x, ...) ({ __typeof(x) $items[] = {x, __VA_ARGS__}; \
(array_t){.length=sizeof($items)/sizeof($items[0]), \
.stride=(int64_t)&$items[1] - (int64_t)&$items[0], \
.data=memcpy(GC_MALLOC(sizeof($items)), $items, sizeof($items)), \
.copy_on_write=1}; })
#define not(x) _Generic(x, bool: (bool)!(x), default: ~(x))
#define and(x, y) _Generic(x, bool: (bool)((x) && (y)), default: ((x) & (y)))