diff options
| author | gingerBill <ginger.bill.22@gmail.com> | 2016-08-15 14:54:45 +0100 |
|---|---|---|
| committer | gingerBill <ginger.bill.22@gmail.com> | 2016-08-15 15:02:45 +0100 |
| commit | dcbb2fcfbdbd3b35ddc44a4c542b7c6375e47214 (patch) | |
| tree | 1670d1ea683c78be063649685c601a17c1dcb025 /src/parser.cpp | |
| parent | 3ed75b22a357292393618fc684b18a1d167f4eb7 (diff) | |
Full Unicode Support
Diffstat (limited to 'src/parser.cpp')
| -rw-r--r-- | src/parser.cpp | 65 |
1 files changed, 59 insertions, 6 deletions
diff --git a/src/parser.cpp b/src/parser.cpp index baa2caccd..088d2072c 100644 --- a/src/parser.cpp +++ b/src/parser.cpp @@ -1605,6 +1605,61 @@ AstNode *parse_body(AstFile *f, AstScope *scope) { return make_block_stmt(f, statement_list, statement_list_count, open, close); } +b32 is_foreign_name_valid(String name) { + // TODO(bill): is_foreign_name_valid + if (name.len == 0) + return false; + isize offset = 0; + while (offset < name.len) { + Rune rune; + isize remaining = name.len - offset; + isize width = gb_utf8_decode(name.text+offset, remaining, &rune); + if (rune == GB_RUNE_INVALID && width == 1) { + return false; + } else if (rune == GB_RUNE_BOM && remaining > 0) { + return false; + } + + if (offset == 0) { + switch (rune) { + case '-': + case '$': + case '.': + case '_': + break; + default: + if (!rune_is_letter(rune)) + return false; + break; + } + } else { + switch (rune) { + case '-': + case '$': + case '.': + case '_': + break; + default: + if (!rune_is_letter(rune) && !rune_is_digit(rune)) { + return false; + } + break; + } + } + + offset += width; + } + + return true; +} + +void check_proc_add_tag(AstFile *f, AstNode *tag_expr, u64 *tags, ProcTag tag, String tag_name) { + if (*tags & tag) { + ast_file_err(f, ast_node_token(tag_expr), "Procedure tag already used: %.*s", LIT(tag_name)); + } + *tags |= tag; +} + AstNode *parse_proc_decl(AstFile *f, Token proc_token, AstNode *name) { AstNode *param_list = NULL; AstNode *result_list = NULL; @@ -1623,20 +1678,20 @@ AstNode *parse_proc_decl(AstFile *f, Token proc_token, AstNode *name) { ast_node(te, TagExpr, tag_expr); String tag_name = te->name.string; if (are_strings_equal(tag_name, make_string("foreign"))) { - tags |= ProcTag_foreign; + check_proc_add_tag(f, tag_expr, &tags, ProcTag_foreign, tag_name); if (f->cursor[0].kind == Token_String) { foreign_name = f->cursor[0].string; // TODO(bill): Check if valid string - if (foreign_name.len == 0) { + if (!is_foreign_name_valid(foreign_name)) { ast_file_err(f, ast_node_token(tag_expr), "Invalid alternative foreign procedure name"); } next_token(f); } } else if (are_strings_equal(tag_name, make_string("inline"))) { - tags |= ProcTag_inline; + check_proc_add_tag(f, tag_expr, &tags, ProcTag_inline, tag_name); } else if (are_strings_equal(tag_name, make_string("no_inline"))) { - tags |= ProcTag_no_inline; + check_proc_add_tag(f, tag_expr, &tags, ProcTag_no_inline, tag_name); } else { ast_file_err(f, ast_node_token(tag_expr), "Unknown procedure tag"); } @@ -2155,8 +2210,6 @@ void parse_file(Parser *p, AstFile *f) { char *path_str = gb_path_get_full_name(gb_heap_allocator(), cast(char *)str); String import_file = make_string(path_str); - gb_printf_err("load path: %.*s\n", LIT(import_file)); - if (!try_add_load_path(p, import_file)) { gb_free(gb_heap_allocator(), import_file.text); } |