diff options
| -rw-r--r-- | CHANGES.md | 20 | ||||
| -rw-r--r-- | src/ast.c | 5 | ||||
| -rw-r--r-- | src/ast.h | 5 | ||||
| -rw-r--r-- | src/compile/expressions.c | 1 | ||||
| -rw-r--r-- | src/compile/files.c | 15 | ||||
| -rw-r--r-- | src/compile/functions.c | 5 | ||||
| -rw-r--r-- | src/compile/headers.c | 17 | ||||
| -rw-r--r-- | src/compile/statements.c | 1 | ||||
| -rw-r--r-- | src/formatter/formatter.c | 5 | ||||
| -rw-r--r-- | src/formatter/utils.c | 6 | ||||
| -rw-r--r-- | src/parse/files.c | 5 | ||||
| -rw-r--r-- | src/parse/typedefs.c | 27 | ||||
| -rw-r--r-- | src/parse/typedefs.h | 1 | ||||
| -rw-r--r-- | src/parse/utils.c | 7 | ||||
| -rw-r--r-- | src/typecheck.c | 61 |
15 files changed, 24 insertions, 157 deletions
@@ -11,15 +11,17 @@ - Syntax for text literals and inline C code has been simplified somewhat. - Syntax for tables has changed to use colons (`{k: v}`) instead of equals (`{k=v}`). -- Deprecated sets. - - Instead of sets, use tables. - - Tables now have `and`, `or`, `xor`, and `-` (minus) metamethods. -- Deprecated `extern` keyword for declaring external symbols from C. - - Use `C_code` instead. -- Deprecated the postfix `?` to make values optional. - - Explicitly optional values can be declared as `my_var : T? = value`. -- Deprecated `>> ... = ...` form of doctests. They are now called "debug logs" - and you can specify multiple values: `>> a, b, c` +- Deprecated: + - Sets + - Instead of sets, use tables. + - Tables now have `and`, `or`, `xor`, and `-` (minus) metamethods. + - `extern` keyword for declaring external symbols from C. + - Use `C_code` instead. + - Postfix `?` to make values optional. + - Explicitly optional values can be declared as `my_var : T? = value`. + - `>> ... = ...` form of doctests. They are now called "debug logs" and you + can specify multiple values: `>> a, b, c` + - `extend` blocks - Struct fields that start with underscores can be accessed again and function arguments that start with underscore can be passed (but only as keyword arguments). @@ -275,7 +275,6 @@ Text_t ast_to_sexp(ast_t *ast) { T(Use, "(Use ", optional_sexp("var", data.var), " ", quoted_text(data.path), ")"); T(InlineCCode, "(InlineCCode ", ast_list_to_sexp(data.chunks), optional_type_sexp("type", data.type_ast), ")"); T(Deserialize, "(Deserialize ", type_ast_to_sexp(data.type), " ", ast_to_sexp(data.value), ")"); - T(Extend, "(Extend \"", data.name, "\" ", ast_to_sexp(data.body), ")"); default: errx(1, "S-expressions are not implemented for this AST"); #undef T } @@ -681,10 +680,6 @@ void ast_visit(ast_t *ast, void (*visitor)(ast_t *, void *), void *userdata) { ast_visit(Match(ast, Deserialize)->value, visitor, userdata); return; } - case Extend: { - ast_visit(Match(ast, Extend)->body, visitor, userdata); - return; - } default: errx(1, "Visiting is not supported for this AST: %s", Text$as_c_string(ast_to_sexp(ast))); #undef T } @@ -275,7 +275,6 @@ typedef enum { Use, InlineCCode, Deserialize, - Extend, ExplicitlyTyped, } ast_e; #define NUM_AST_TAGS (ExplicitlyTyped + 1) @@ -459,10 +458,6 @@ struct ast_s { type_ast_t *type; } Deserialize; struct { - const char *name; - ast_t *body; - } Extend; - struct { ast_t *ast; struct type_s *type; } ExplicitlyTyped; diff --git a/src/compile/expressions.c b/src/compile/expressions.c index b9fafeb8..098ed4ca 100644 --- a/src/compile/expressions.c +++ b/src/compile/expressions.c @@ -241,7 +241,6 @@ Text_t compile(env_t *env, ast_t *ast) { case Repeat: case StructDef: case LangDef: - case Extend: case EnumDef: case FunctionDef: case ConvertDef: diff --git a/src/compile/files.c b/src/compile/files.c index f331a50a..a4cc07fe 100644 --- a/src/compile/files.c +++ b/src/compile/files.c @@ -48,8 +48,6 @@ void initialize_vars_and_statics(env_t *env, ast_t *ast) { initialize_namespace(env, Match(stmt->ast, EnumDef)->name, Match(stmt->ast, EnumDef)->namespace); } else if (stmt->ast->tag == LangDef) { initialize_namespace(env, Match(stmt->ast, LangDef)->name, Match(stmt->ast, LangDef)->namespace); - } else if (stmt->ast->tag == Extend) { - initialize_namespace(env, Match(stmt->ast, Extend)->name, Match(stmt->ast, Extend)->body); } else if (stmt->ast->tag == Use) { continue; } else { @@ -137,19 +135,6 @@ Text_t compile_top_level_code(env_t *env, ast_t *ast) { ", .metamethods=Text$metamethods, .tag=TextInfo, .TextInfo={", quoted_str(def->name), "}};\n"); return Texts(code, compile_namespace(env, def->name, def->namespace)); } - case Extend: { - DeclareMatch(extend, ast, Extend); - binding_t *b = get_binding(env, extend->name); - if (!b || b->type->tag != TypeInfoType) - code_err(ast, "'", extend->name, "' is not the name of any type I recognize."); - env_t *ns_env = Match(b->type, TypeInfoType)->env; - env_t *extended = new (env_t); - *extended = *ns_env; - extended->locals = new (Table_t, .fallback = env->locals); - extended->namespace_bindings = new (Table_t, .fallback = env->namespace_bindings); - extended->id_suffix = env->id_suffix; - return compile_top_level_code(extended, extend->body); - } case Block: { Text_t code = EMPTY_TEXT; for (ast_list_t *stmt = Match(ast, Block)->statements; stmt; stmt = stmt->next) { diff --git a/src/compile/functions.c b/src/compile/functions.c index 40e16e48..ab267e2c 100644 --- a/src/compile/functions.c +++ b/src/compile/functions.c @@ -580,10 +580,7 @@ static void add_closed_vars(Table_t *closed_vars, env_t *enclosing_scope, env_t case ConvertDef: case StructDef: case EnumDef: - case LangDef: - case Extend: { - errx(1, "Definitions should not be reachable in a closure."); - } + case LangDef: errx(1, "Definitions should not be reachable in a closure."); default: break; } } diff --git a/src/compile/headers.c b/src/compile/headers.c index 1865905c..bc0156ad 100644 --- a/src/compile/headers.c +++ b/src/compile/headers.c @@ -25,20 +25,6 @@ Text_t compile_statement_namespace_header(env_t *env, Path_t header_path, ast_t block = def->namespace; break; } - case Extend: { - DeclareMatch(extend, ast, Extend); - ns_env = namespace_env(env, extend->name); - - env_t *extended = new (env_t); - *extended = *ns_env; - extended->locals = new (Table_t, .fallback = env->locals); - extended->namespace_bindings = new (Table_t, .fallback = env->namespace_bindings); - extended->id_suffix = env->id_suffix; - ns_env = extended; - - block = extend->body; - break; - } case StructDef: { DeclareMatch(def, ast, StructDef); ns_env = namespace_env(env, def->name); @@ -251,9 +237,6 @@ Text_t compile_statement_type_header(env_t *env, Path_t header_path, ast_t *ast) "extern const TypeInfo_t ", namespace_name(env, env->namespace, Texts(def->name, Text("$$info"))), ";\n"); } - case Extend: { - return EMPTY_TEXT; - } default: return EMPTY_TEXT; } } diff --git a/src/compile/statements.c b/src/compile/statements.c index 156cc8c0..a9ec4327 100644 --- a/src/compile/statements.c +++ b/src/compile/statements.c @@ -76,7 +76,6 @@ static Text_t _compile_statement(env_t *env, ast_t *ast) { case StructDef: case EnumDef: case LangDef: - case Extend: case FunctionDef: case ConvertDef: { return EMPTY_TEXT; diff --git a/src/formatter/formatter.c b/src/formatter/formatter.c index 9ff328d0..41b1c4aa 100644 --- a/src/formatter/formatter.c +++ b/src/formatter/formatter.c @@ -116,7 +116,6 @@ OptionalText_t format_inline_code(ast_t *ast, Table_t comments) { /*inline*/ case StructDef: /*inline*/ case EnumDef: /*inline*/ case LangDef: - /*inline*/ case Extend: /*inline*/ case FunctionDef: /*inline*/ case ConvertDef: /*inline*/ case DebugLog: @@ -571,10 +570,6 @@ Text_t format_code(ast_t *ast, Table_t comments, Text_t indent) { DeclareMatch(def, ast, LangDef); return Texts("lang ", Text$from_str(def->name), format_namespace(def->namespace, comments, indent)); } - /*multiline*/ case Extend: { - DeclareMatch(extend, ast, Extend); - return Texts("lang ", Text$from_str(extend->name), format_namespace(extend->body, comments, indent)); - } /*multiline*/ case Defer: return Texts("defer ", format_namespace(Match(ast, Defer)->body, comments, indent)); /*multiline*/ case List: { diff --git a/src/formatter/utils.c b/src/formatter/utils.c index 9829df4b..ce2d30b5 100644 --- a/src/formatter/utils.c +++ b/src/formatter/utils.c @@ -70,8 +70,7 @@ CONSTFUNC int suggested_blank_lines(ast_t *first, ast_t *second) { case Lambda: case StructDef: case EnumDef: - case LangDef: - case Extend: return 1; + case LangDef: return 1; case Use: { if (second->tag != Use) return 1; break; @@ -104,8 +103,7 @@ CONSTFUNC int suggested_blank_lines(ast_t *first, ast_t *second) { case Lambda: case StructDef: case EnumDef: - case LangDef: - case Extend: return 1; + case LangDef: return 1; default: break; } return 0; diff --git a/src/parse/files.c b/src/parse/files.c index 5e0dc29c..2dbe0e8f 100644 --- a/src/parse/files.c +++ b/src/parse/files.c @@ -41,9 +41,8 @@ ast_t *parse_file_body(parse_ctx_t *ctx, const char *pos) { ast_t *stmt; if ((stmt = optional(ctx, &pos, parse_struct_def)) || (stmt = optional(ctx, &pos, parse_func_def)) || (stmt = optional(ctx, &pos, parse_enum_def)) || (stmt = optional(ctx, &pos, parse_lang_def)) - || (stmt = optional(ctx, &pos, parse_extend)) || (stmt = optional(ctx, &pos, parse_convert_def)) - || (stmt = optional(ctx, &pos, parse_use)) || (stmt = optional(ctx, &pos, parse_inline_c)) - || (stmt = optional(ctx, &pos, parse_top_declaration))) { + || (stmt = optional(ctx, &pos, parse_convert_def)) || (stmt = optional(ctx, &pos, parse_use)) + || (stmt = optional(ctx, &pos, parse_inline_c)) || (stmt = optional(ctx, &pos, parse_top_declaration))) { statements = new (ast_list_t, .ast = stmt, .next = statements); pos = stmt->end; whitespace(ctx, &pos); // TODO: check for newline diff --git a/src/parse/typedefs.c b/src/parse/typedefs.c index fe48cb2c..56bb687f 100644 --- a/src/parse/typedefs.c +++ b/src/parse/typedefs.c @@ -26,9 +26,8 @@ ast_t *parse_namespace(parse_ctx_t *ctx, const char *pos) { ast_t *stmt; if ((stmt = optional(ctx, &pos, parse_struct_def)) || (stmt = optional(ctx, &pos, parse_func_def)) || (stmt = optional(ctx, &pos, parse_enum_def)) || (stmt = optional(ctx, &pos, parse_lang_def)) - || (stmt = optional(ctx, &pos, parse_extend)) || (stmt = optional(ctx, &pos, parse_convert_def)) - || (stmt = optional(ctx, &pos, parse_use)) || (stmt = optional(ctx, &pos, parse_inline_c)) - || (stmt = optional(ctx, &pos, parse_declaration))) { + || (stmt = optional(ctx, &pos, parse_convert_def)) || (stmt = optional(ctx, &pos, parse_use)) + || (stmt = optional(ctx, &pos, parse_inline_c)) || (stmt = optional(ctx, &pos, parse_declaration))) { statements = new (ast_list_t, .ast = stmt, .next = statements); pos = stmt->end; whitespace(ctx, &pos); // TODO: check for newline @@ -182,25 +181,3 @@ ast_t *parse_lang_def(parse_ctx_t *ctx, const char *pos) { return NewAST(ctx->file, start, pos, LangDef, .name = name, .namespace = namespace); } - -ast_t *parse_extend(parse_ctx_t *ctx, const char *pos) { - const char *start = pos; - // extend Name: body... - if (!match_word(&pos, "extend")) return NULL; - int64_t starting_indent = get_indent(ctx, pos); - spaces(&pos); - const char *name = get_id(&pos); - if (!name) parser_err(ctx, start, pos, "I expected a name for this lang"); - - ast_t *body = NULL; - const char *ns_pos = pos; - whitespace(ctx, &ns_pos); - int64_t ns_indent = get_indent(ctx, ns_pos); - if (ns_indent > starting_indent) { - pos = ns_pos; - body = optional(ctx, &pos, parse_namespace); - } - if (!body) body = NewAST(ctx->file, pos, pos, Block, .statements = NULL); - - return NewAST(ctx->file, start, pos, Extend, .name = name, .body = body); -} diff --git a/src/parse/typedefs.h b/src/parse/typedefs.h index 1a746cff..1bdb92e6 100644 --- a/src/parse/typedefs.h +++ b/src/parse/typedefs.h @@ -7,5 +7,4 @@ ast_t *parse_lang_def(parse_ctx_t *ctx, const char *pos); ast_t *parse_enum_def(parse_ctx_t *ctx, const char *pos); ast_t *parse_struct_def(parse_ctx_t *ctx, const char *pos); -ast_t *parse_extend(parse_ctx_t *ctx, const char *pos); ast_t *parse_namespace(parse_ctx_t *ctx, const char *pos); diff --git a/src/parse/utils.c b/src/parse/utils.c index 2048a3ff..28cf0964 100644 --- a/src/parse/utils.c +++ b/src/parse/utils.c @@ -12,10 +12,9 @@ #include "utils.h" static const char *keywords[] = { - "C_code", "_max_", "_min_", "and", "assert", "break", "continue", "defer", "deserialize", "do", - "else", "enum", "extend", "for", "func", "if", "in", "lang", "mod", "mod1", - "no", "none", "not", "or", "pass", "return", "skip", "skip", "stop", "struct", - "then", "unless", "use", "when", "while", "xor", "yes", + "C_code", "_max_", "_min_", "and", "assert", "break", "continue", "defer", "deserialize", "do", "else", "enum", + "for", "func", "if", "in", "lang", "mod", "mod1", "no", "none", "not", "or", "pass", + "return", "skip", "skip", "stop", "struct", "then", "unless", "use", "when", "while", "xor", "yes", }; CONSTFUNC bool is_keyword(const char *word) { diff --git a/src/typecheck.c b/src/typecheck.c index 21eb7b3f..b21fa40f 100644 --- a/src/typecheck.c +++ b/src/typecheck.c @@ -321,31 +321,6 @@ void prebind_statement(env_t *env, ast_t *statement) { prebind_statement(ns_env, stmt->ast); break; } - case Extend: { - DeclareMatch(extend, statement, Extend); - env_t *ns_env = namespace_env(env, extend->name); - env_t *extended = new (env_t); - *extended = *ns_env; - extended->locals = new (Table_t, .fallback = env->locals); - extended->namespace_bindings = new (Table_t, .fallback = env->namespace_bindings); - extended->id_suffix = env->id_suffix; - for (ast_list_t *stmt = extend->body ? Match(extend->body, Block)->statements : NULL; stmt; stmt = stmt->next) - prebind_statement(extended, stmt->ast); - List_t new_bindings = extended->locals->entries; - for (int64_t i = 0; i < (int64_t)new_bindings.length; i++) { - struct { - const char *name; - binding_t *binding; - } *entry = new_bindings.data + i * new_bindings.stride; - binding_t *clobbered = Table$str_get(*ns_env->locals, entry->name); - if (clobbered && !type_eq(clobbered->type, entry->binding->type)) - code_err(statement, "This `extend` block overwrites the binding for ", quoted(entry->name), - " in the original namespace (with type ", type_to_text(clobbered->type), - ") with a new binding with type ", type_to_text(entry->binding->type)); - Table$str_set(ns_env->locals, entry->name, entry->binding); - } - break; - } default: break; } } @@ -551,31 +526,6 @@ void bind_statement(env_t *env, ast_t *statement) { bind_statement(ns_env, stmt->ast); break; } - case Extend: { - DeclareMatch(extend, statement, Extend); - env_t *ns_env = namespace_env(env, extend->name); - env_t *extended = new (env_t); - *extended = *ns_env; - extended->locals = new (Table_t, .fallback = env->locals); - extended->namespace_bindings = new (Table_t, .fallback = env->namespace_bindings); - extended->id_suffix = env->id_suffix; - for (ast_list_t *stmt = extend->body ? Match(extend->body, Block)->statements : NULL; stmt; stmt = stmt->next) - bind_statement(extended, stmt->ast); - List_t new_bindings = extended->locals->entries; - for (int64_t i = 0; i < (int64_t)new_bindings.length; i++) { - struct { - const char *name; - binding_t *binding; - } *entry = new_bindings.data + i * new_bindings.stride; - binding_t *clobbered = Table$str_get(*ns_env->locals, entry->name); - if (clobbered && !type_eq(clobbered->type, entry->binding->type)) - code_err(statement, "This `extend` block overwrites the binding for ", quoted(entry->name), - " in the original namespace (with type ", type_to_text(clobbered->type), - ") with a new binding with type ", type_to_text(entry->binding->type)); - Table$str_set(ns_env->locals, entry->name, entry->binding); - } - break; - } case Use: { env_t *module_env = load_module(env, statement); if (!module_env) break; @@ -1074,8 +1024,7 @@ type_t *get_type(env_t *env, ast_t *ast) { case ConvertDef: case StructDef: case EnumDef: - case LangDef: - case Extend: return Type(VoidType); + case LangDef: return Type(VoidType); default: break; } @@ -1421,10 +1370,7 @@ type_t *get_type(env_t *env, ast_t *ast) { case ConvertDef: case StructDef: case EnumDef: - case LangDef: - case Extend: { - return Type(VoidType); - } + case LangDef: return Type(VoidType); case If: { DeclareMatch(if_, ast, If); @@ -1580,8 +1526,7 @@ PUREFUNC bool is_discardable(env_t *env, ast_t *ast) { case StructDef: case EnumDef: case LangDef: - case Use: - case Extend: return true; + case Use: return true; default: break; } type_t *t = get_type(env, ast); |
