summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--eval.c2
-rw-r--r--package.c28
-rw-r--r--parse.c7
-rwxr-xr-xpkg.sh11
-rw-r--r--std/arr.c23
-rw-r--r--std/arr.toc (renamed from a.toc)2
-rw-r--r--std/io.c42
-rw-r--r--std/io.toc14
-rw-r--r--test.toc15
-rw-r--r--types.c51
-rw-r--r--types.h11
11 files changed, 134 insertions, 72 deletions
diff --git a/eval.c b/eval.c
index e53f0e1..085e3f8 100644
--- a/eval.c
+++ b/eval.c
@@ -1556,7 +1556,7 @@ static bool eval_expr(Evaluator *ev, Expression *e, Value *v) {
*v = e->val;
break;
case EXPR_PKG:
- v->pkg = e->pkg.name_ident->pkg;
+ assert(0);
break;
}
return true;
diff --git a/package.c b/package.c
index bacd70e..38f8e26 100644
--- a/package.c
+++ b/package.c
@@ -15,7 +15,9 @@ static void import_expr(Importer *im, Expression *e);
static void import_block(Importer *im, Block *b);
static inline Expression *import_expr_(Importer *im);
+
static void exptr_create(Exporter *ex, FILE *out) {
+ /* construct full filename */
ex->out = out;
ex->ident_id = 0;
ex->exported_fns = NULL;
@@ -203,7 +205,7 @@ static void exptr_start(Exporter *ex, const char *pkg_name, size_t pkg_name_len)
}
/* where = where was this imported. don't free fname while imported stuff is in use. */
-static bool import_pkg(Allocator *allocr, Package *p, FILE *f, const char *fname, Identifiers *parent_idents, ErrCtx *parent_ctx, Location where) {
+static bool import_pkg(Allocator *allocr, Package *p, FILE *f, const char *fname, ErrCtx *parent_ctx, Location where) {
Importer i = {0};
ErrCtx *err_ctx = i.err_ctx = allocr_malloc(allocr, sizeof *i.err_ctx);
idents_create(&p->idents);
@@ -235,7 +237,10 @@ static bool import_pkg(Allocator *allocr, Package *p, FILE *f, const char *fname
U64 footer_offset = import_u64(&i);
size_t pkg_name_len = import_len(&i);
char *pkg_name = import_str(&i, pkg_name_len);
- p->name = ident_get(parent_idents, pkg_name);
+ p->name = allocr_malloc(allocr, pkg_name_len + 1);
+ p->c.prefix = p->name;
+ memcpy(p->name, pkg_name, pkg_name_len);
+ p->name[pkg_name_len] = 0;
bool has_code = import_bool(&i);
if (has_code) {
size_t code_len = import_len(&i);
@@ -438,10 +443,9 @@ static bool export_val_ptr(Exporter *ex, void *v, Type *type, Location where) {
if (!export_type(ex, *(Type **)v, where))
return false;
break;
- case BUILTIN_PKG: {
- Package *pkg = *(Package **)v;
- export_ident(ex, pkg->name);
- } break;
+ case BUILTIN_PKG:
+ /* TODO */
+ break;
}
break;
case TYPE_TUPLE: {
@@ -736,12 +740,9 @@ static bool export_expr(Exporter *ex, Expression *e) {
return false;
} break;
case EXPR_PKG:
- if (found_type) {
- export_ident(ex, e->pkg.name_ident);
- } else {
- if (!export_expr(ex, e->pkg.name_expr))
- return false;
- }
+ assert(!found_type);
+ if (!export_expr(ex, e->pkg.name_expr))
+ return false;
break;
case EXPR_SLICE: {
SliceExpr *s = &e->slice;
@@ -886,7 +887,8 @@ static void import_expr(Importer *im, Expression *e) {
import_block(im, &w->body);
} break;
case EXPR_PKG:
- /* TODO (see also: val) */
+ assert(!found_type);
+ e->pkg.name_expr = import_expr_(im);
break;
case EXPR_SLICE: {
SliceExpr *s = &e->slice;
diff --git a/parse.c b/parse.c
index cb105ab..6cd14ed 100644
--- a/parse.c
+++ b/parse.c
@@ -2247,11 +2247,8 @@ static void fprint_expr(FILE *out, Expression *e) {
break;
case EXPR_PKG:
fprintf(out, "(pkg ");
- if (found_type) {
- fprint_ident(out, e->pkg.name_ident);
- } else {
- fprint_expr(out, e->pkg.name_expr);
- }
+ assert(!found_type);
+ fprint_expr(out, e->pkg.name_expr);
fprintf(out, ")");
break;
}
diff --git a/pkg.sh b/pkg.sh
index b86c1ca..5f1d847 100755
--- a/pkg.sh
+++ b/pkg.sh
@@ -1,5 +1,10 @@
#!/bin/sh
-valgrind -q ./toc $1.toc -o $1.c || exit 1
-valgrind -q ./toc test.toc || exit 1
-gcc out.c $1.c || exit 1
+std_things="io arr"
+cd std
+for thing in $std_things; do
+ valgrind --track-origins=yes --exit-on-first-error=yes --error-exitcode=1 -q ../toc $thing.toc -o $thing.c || exit 1
+done
+cd ..
+valgrind --track-origins=yes --exit-on-first-error=yes --error-exitcode=1 -q ./toc test.toc || exit 1
+gcc out.c std/*.c || exit 1
./a.out
diff --git a/std/arr.c b/std/arr.c
new file mode 100644
index 0000000..2d2c03a
--- /dev/null
+++ b/std/arr.c
@@ -0,0 +1,23 @@
+#include <stdint.h>
+#include <stdio.h>
+typedef int8_t i8;
+typedef int16_t i16;
+typedef int32_t i32;
+typedef int64_t i64;
+typedef uint8_t u8;
+typedef uint16_t u16;
+typedef uint32_t u32;
+typedef uint64_t u64;
+typedef float f32;
+typedef double f64;
+typedef u8 bool;
+typedef struct { void *data; i64 n; } slice_;
+#define false ((bool)0)
+#define true ((bool)1)
+static slice_ mkslice_(void *data, i64 n) { slice_ ret; ret.data = data; ret.n = n; return ret; }
+static void free_(void *data) { extern void free(void *data); free(data); }
+static void *e__calloc(size_t n, size_t sz) { extern void *calloc(size_t n, size_t size); extern void abort(void); void *ret = calloc(n, sz); if (n && sz && !ret) { fprintf(stderr, "Out of memory.\n"); abort(); } return ret; }
+
+
+/* declarations */
+/* code */
diff --git a/a.toc b/std/arr.toc
index b282224..fcf6a45 100644
--- a/a.toc
+++ b/std/arr.toc
@@ -1,5 +1,5 @@
// array package
-pkg "a";
+pkg "arr";
#export Arr ::= fn (t :: Type) Type {
struct {
diff --git a/std/io.c b/std/io.c
new file mode 100644
index 0000000..97d5d43
--- /dev/null
+++ b/std/io.c
@@ -0,0 +1,42 @@
+#include <stdint.h>
+#include <stdio.h>
+typedef int8_t i8;
+typedef int16_t i16;
+typedef int32_t i32;
+typedef int64_t i64;
+typedef uint8_t u8;
+typedef uint16_t u16;
+typedef uint32_t u32;
+typedef uint64_t u64;
+typedef float f32;
+typedef double f64;
+typedef u8 bool;
+typedef struct { void *data; i64 n; } slice_;
+#define false ((bool)0)
+#define true ((bool)1)
+static slice_ mkslice_(void *data, i64 n) { slice_ ret; ret.data = data; ret.n = n; return ret; }
+static void free_(void *data) { extern void free(void *data); free(data); }
+static void *e__calloc(size_t n, size_t sz) { extern void *calloc(size_t n, size_t size); extern void abort(void); void *ret = calloc(n, sz); if (n && sz && !ret) { fprintf(stderr, "Out of memory.\n"); abort(); } return ret; }
+
+
+/* declarations */
+void io__puti(i64 x);
+void io__putf(f32 x);
+void io__puts(slice_ x);
+/* code */
+void io__puti(i64 x) {
+ printf("%ld\n", (long)x);
+}
+
+
+void io__putf(f32 x) {
+ printf("%f\n", (double)x);
+}
+
+
+void io__puts(slice_ x) {
+ fwrite(x.data, 1, x.n, stdout);
+ printf("\n");
+}
+
+
diff --git a/std/io.toc b/std/io.toc
new file mode 100644
index 0000000..68e9744
--- /dev/null
+++ b/std/io.toc
@@ -0,0 +1,14 @@
+pkg "io";
+
+#export puti ::= fn(x: int) {
+ #C("printf(\"%ld\\n\", (long)x)");
+};
+
+#export putf ::= fn(x: float) {
+ #C("printf(\"%f\\n\", (double)x)");
+};
+
+#export puts ::= fn(x: []char) {
+ #C("fwrite(x.data, 1, x.n, stdout)");
+ #C("printf(\"\\n\")");
+}; \ No newline at end of file
diff --git a/test.toc b/test.toc
index 759f19b..2770b9e 100644
--- a/test.toc
+++ b/test.toc
@@ -1,19 +1,12 @@
-puti ::= fn(x: int) {
- #C("printf(\"%ld\\n\", (long)x);
-");
-};
-putf ::= fn(x: float) {
- #C("printf(\"%f\\n\", (double)x);
-");
-};
-
-arr ::= pkg "a";
+arr ::= pkg "std/arr";
+io ::= pkg "std/io";
putptri ::= fn(x: &int) {
- puti(*x);
+ io.puti(*x);
};
main ::= fn() {
+ io.puts("Hello, world!");
x : arr.Arr(int);
arr.arr_add(&x, 10);
arr.arr_add(&x, 20);
diff --git a/types.c b/types.c
index dba9820..c6ab0d3 100644
--- a/types.c
+++ b/types.c
@@ -981,33 +981,23 @@ static bool types_expr(Typer *tr, Expression *e) {
char *name_cstr = typer_malloc(tr, name_str_len + 1);
memcpy(name_cstr, name_str.data, name_str_len);
name_cstr[name_str.n] = '\0';
- char *name_ptr = name_cstr;
- Identifier name_ident = ident_insert(tr->idents, &name_ptr);
- if (*name_ptr) {
- err_print(name_expr->where, "Package name (\"%s\") is not a valid identifier.",
- name_cstr);
+ /* TODO: only import packages once */
+ Package *pkg = arr_add(&tr->pkgs);
+ char *filename = typer_malloc(tr, name_str_len + 6);
+ memcpy(filename, name_str.data, name_str_len);
+ strcpy(filename + name_str.n, ".top");
+ /* TODO: package paths */
+ FILE *fp = fopen(filename, "rb");
+ if (!fp) {
+ err_print(e->where, "Could not open package: %s (does this file exist?)", filename);
return false;
}
- e->pkg.name_ident = name_ident;
- if (!name_ident->pkg) {
- char *filename = typer_malloc(tr, name_str_len + 5);
- Package *pkg = name_ident->pkg = err_calloc(1, sizeof *pkg);
- pkg->c.prefix = name_cstr;
- memcpy(filename, name_str.data, name_str_len);
- strcpy(filename + name_str.n, ".top");
- /* TODO: library paths */
- FILE *fp = fopen(filename, "rb");
- if (!fp) {
- err_print(e->where, "Could not open package: %s (does this file exist?)", filename);
- free(filename);
- return false;
- }
- if (!import_pkg(tr->allocr, pkg, fp, filename, tr->idents, tr->err_ctx, e->where)) {
- return false;
- }
- *(Package **)arr_add(&tr->pkgs) = pkg;
- fclose(fp);
+ if (!import_pkg(tr->allocr, pkg, fp, filename, tr->err_ctx, e->where)) {
+ return false;
}
+ e->kind = EXPR_VAL;
+ e->val.pkg = pkg;
+ fclose(fp);
} break;
case EXPR_EACH: {
EachExpr *ea = e->each;
@@ -1923,6 +1913,7 @@ static bool types_expr(Typer *tr, Expression *e) {
case BINARY_DOT: {
if (!types_expr(tr, lhs)) return false;
Type *struct_type = lhs_type;
+ if (struct_type->kind == TYPE_UNKNOWN) return true;
if (type_is_builtin(struct_type, BUILTIN_PKG)) {
if (rhs->kind != EXPR_IDENT) {
err_print(rhs->where, "Expected identifier for package access, but got %s.",
@@ -1936,12 +1927,10 @@ static bool types_expr(Typer *tr, Expression *e) {
lhs->val = pkg_val;
e->binary.dot.pkg_ident = ident_translate(rhs->ident, &pkg_val.pkg->idents);
if (!e->binary.dot.pkg_ident) {
- char *ident_name = ident_to_str(rhs->ident),
- *pkg_name = ident_to_str(pkg_val.pkg->name);
+ char *ident_name = ident_to_str(rhs->ident);
- err_print(e->where, "%s was not imported from package %s.", ident_name, pkg_name);
+ err_print(e->where, "%s was not imported from package %s.", ident_name, pkg_val.pkg->name);
free(ident_name);
- free(pkg_name);
return false;
}
if (!type_of_ident(tr, e->where, e->binary.dot.pkg_ident, t)) {
@@ -2367,10 +2356,8 @@ static bool types_file(Typer *tr, ParsedFile *f) {
}
static void typer_free(Typer *tr) {
- typedef Package *PackagePtr;
- arr_foreach(tr->pkgs, PackagePtr, pkg) {
- package_free(*pkg);
- free(*pkg);
+ arr_foreach(tr->pkgs, Package, pkg) {
+ package_free(pkg);
}
arr_clear(&tr->pkgs);
}
diff --git a/types.h b/types.h
index ff80575..6fb68c2 100644
--- a/types.h
+++ b/types.h
@@ -660,10 +660,9 @@ typedef struct Expression {
struct {
Type type;
} del;
- union {
- struct Expression *name_expr; /* before typing */
- Identifier name_ident; /* after typing */
- } pkg;
+ struct {
+ struct Expression *name_expr;
+ } pkg; /* only can exist before typing */
IfExpr if_;
WhileExpr while_;
EachExpr *each;
@@ -769,7 +768,7 @@ typedef struct Evaluator {
} Evaluator;
typedef struct Package {
- Identifier name;
+ char *name; /* package name, not file name */
Identifiers idents;
Statement *stmts;
struct {
@@ -791,7 +790,7 @@ typedef struct Typer {
ErrCtx *err_ctx;
/* for checking for problematic struct circular dependencies */
bool *is_reference_stack;
- Package **pkgs; /* all packages which have been imported */
+ Package *pkgs; /* all packages which have been imported */
} Typer;
typedef struct Exporter {