From 3742d9e7e9fbb02058c7da9030a0abb023e7b244 Mon Sep 17 00:00:00 2001 From: gingerBill Date: Sat, 20 Oct 2018 10:44:02 +0100 Subject: [PATCH] Move atomic intrinsics to the new built-in package intrinsics --- core/sync/atomic.odin | 124 ++++++++++++++-------------- src/check_expr.cpp | 5 +- src/check_stmt.cpp | 4 +- src/check_type.cpp | 4 +- src/checker.cpp | 37 ++++++--- src/checker.hpp | 182 ++++++++++++++++++++++-------------------- src/entity.cpp | 7 +- src/parser.cpp | 20 +++-- 8 files changed, 209 insertions(+), 174 deletions(-) diff --git a/core/sync/atomic.odin b/core/sync/atomic.odin index abb3e5dc9..fc7255372 100644 --- a/core/sync/atomic.odin +++ b/core/sync/atomic.odin @@ -1,5 +1,7 @@ package sync +import "intrinsics" + Ordering :: enum { Relaxed, // Monotonic Release, @@ -11,10 +13,10 @@ Ordering :: enum { strongest_failure_ordering :: inline proc "contextless" (order: Ordering) -> Ordering { using Ordering; #complete switch order { - case Relaxed: return Relaxed; - case Release: return Relaxed; - case Acquire: return Acquire; - case Acquire_Release: return Acquire; + case Relaxed: return Relaxed; + case Release: return Relaxed; + case Acquire: return Acquire; + case Acquire_Release: return Acquire; case Sequentially_Consistent: return Sequentially_Consistent; } return Relaxed; @@ -23,11 +25,11 @@ strongest_failure_ordering :: inline proc "contextless" (order: Ordering) -> Ord fence :: proc "contextless" (order: Ordering) { using Ordering; #complete switch order { - case Relaxed: panic("there is no such thing as a relaxed fence"); - case Release: __atomic_fence_rel(); - case Acquire: __atomic_fence_acq(); - case Acquire_Release: __atomic_fence_acqrel(); - case Sequentially_Consistent: __atomic_fence(); + case Relaxed: panic("there is no such thing as a relaxed fence"); + case Release: intrinsics.atomic_fence_rel(); + case Acquire: intrinsics.atomic_fence_acq(); + case Acquire_Release: intrinsics.atomic_fence_acqrel(); + case Sequentially_Consistent: intrinsics.atomic_fence(); case: panic("unknown order"); } } @@ -36,10 +38,10 @@ fence :: proc "contextless" (order: Ordering) { atomic_store :: proc "contextless" (dst: ^$T, val: T, order: Ordering) { using Ordering; #complete switch order { - case Relaxed: __atomic_store_relaxed(dst, val); - case Release: __atomic_store_rel(dst, val); - case Sequentially_Consistent: __atomic_store(dst, val); - case Acquire: panic("there is not such thing as an acquire store"); + case Relaxed: intrinsics.atomic_store_relaxed(dst, val); + case Release: intrinsics.atomic_store_rel(dst, val); + case Sequentially_Consistent: intrinsics.atomic_store(dst, val); + case Acquire: panic("there is not such thing as an acquire store"); case Acquire_Release: panic("there is not such thing as an acquire/release store"); case: panic("unknown order"); } @@ -48,10 +50,10 @@ atomic_store :: proc "contextless" (dst: ^$T, val: T, order: Ordering) { atomic_load :: proc "contextless" (dst: ^$T, order: Ordering) -> T { using Ordering; #complete switch order { - case Relaxed: return __atomic_load_relaxed(dst); - case Acquire: return __atomic_load_acq(dst); - case Sequentially_Consistent: return __atomic_load(dst); - case Release: panic("there is no such thing as a release load"); + case Relaxed: return intrinsics.atomic_load_relaxed(dst); + case Acquire: return intrinsics.atomic_load_acq(dst); + case Sequentially_Consistent: return intrinsics.atomic_load(dst); + case Release: panic("there is no such thing as a release load"); case Acquire_Release: panic("there is no such thing as an acquire/release load"); } panic("unknown order"); @@ -61,11 +63,11 @@ atomic_load :: proc "contextless" (dst: ^$T, order: Ordering) -> T { atomic_swap :: proc "contextless" (dst: ^$T, val: T, order: Ordering) -> T { using Ordering; #complete switch order { - case Relaxed: return __atomic_xchg_relaxed(dst, val); - case Release: return __atomic_xchg_rel(dst, val); - case Acquire: return __atomic_xchg_acq(dst, val); - case Acquire_Release: return __atomic_xchg_acqrel(dst, val); - case Sequentially_Consistent: return __atomic_xchg(dst, val); + case Relaxed: return intrinsics.atomic_xchg_relaxed(dst, val); + case Release: return intrinsics.atomic_xchg_rel(dst, val); + case Acquire: return intrinsics.atomic_xchg_acq(dst, val); + case Acquire_Release: return intrinsics.atomic_xchg_acqrel(dst, val); + case Sequentially_Consistent: return intrinsics.atomic_xchg(dst, val); } panic("unknown order"); return T{}; @@ -76,23 +78,23 @@ atomic_compare_exchange :: proc "contextless" (dst: ^$T, old, new: T, success, f switch failure { case Relaxed: switch success { - case Release: return __atomic_cxchg_rel_failrelaxed(dst, old, new); - case Relaxed: return __atomic_cxchg_relaxed(dst, old, new); - case Acquire: return __atomic_cxchg_acq_failrelaxed(dst, old, new); - case Acquire_Release: return __atomic_cxchg_acqrel_failrelaxed(dst, old, new); - case Sequentially_Consistent: return __atomic_cxchg_failrelaxed(dst, old, new); + case Release: return intrinsics.atomic_cxchg_rel_failrelaxed(dst, old, new); + case Relaxed: return intrinsics.atomic_cxchg_relaxed(dst, old, new); + case Acquire: return intrinsics.atomic_cxchg_acq_failrelaxed(dst, old, new); + case Acquire_Release: return intrinsics.atomic_cxchg_acqrel_failrelaxed(dst, old, new); + case Sequentially_Consistent: return intrinsics.atomic_cxchg_failrelaxed(dst, old, new); case: panic("an unknown ordering combination"); } case Acquire: switch success { - case Acquire: return __atomic_cxchg_acq(dst, old, new); - case Acquire_Release: return __atomic_cxchg_acqrel_failacq(dst, old, new); - case Sequentially_Consistent: return __atomic_acqrel_failacq(dst, old, new); + case Acquire: return intrinsics.atomic_cxchg_acq(dst, old, new); + case Acquire_Release: return intrinsics.atomic_cxchg_acqrel_failacq(dst, old, new); + case Sequentially_Consistent: return intrinsics.atomic_acqrel_failacq(dst, old, new); case: panic("an unknown ordering combination"); } case Sequentially_Consistent: switch success { - case Sequentially_Consistent: return __atomic_cxchg(dst, old, new); + case Sequentially_Consistent: return intrinsics.atomic_cxchg(dst, old, new); case: panic("an unknown ordering combination"); } case Acquire_Release: @@ -108,11 +110,11 @@ atomic_compare_exchange :: proc "contextless" (dst: ^$T, old, new: T, success, f atomic_add :: proc "contextless" (dst: ^$T, val: T, order: Ordering) -> T { using Ordering; #complete switch order { - case Relaxed: return __atomic_add_relaxed(dst, val); - case Release: return __atomic_add_rel(dst, val); - case Acquire: return __atomic_add_acq(dst, val); - case Acquire_Release: return __atomic_add_acqrel(dst, val); - case Sequentially_Consistent: return __atomic_add(dst, val); + case Relaxed: return intrinsics.atomic_add_relaxed(dst, val); + case Release: return intrinsics.atomic_add_rel(dst, val); + case Acquire: return intrinsics.atomic_add_acq(dst, val); + case Acquire_Release: return intrinsics.atomic_add_acqrel(dst, val); + case Sequentially_Consistent: return intrinsics.atomic_add(dst, val); } panic("unknown order"); return T{}; @@ -121,11 +123,11 @@ atomic_add :: proc "contextless" (dst: ^$T, val: T, order: Ordering) -> T { atomic_sub :: proc "contextless" (dst: ^$T, val: T, order: Ordering) -> T { using Ordering; #complete switch order { - case Relaxed: return __atomic_sub_relaxed(dst, val); - case Release: return __atomic_sub_rel(dst, val); - case Acquire: return __atomic_sub_acq(dst, val); - case Acquire_Release: return __atomic_sub_acqrel(dst, val); - case Sequentially_Consistent: return __atomic_sub(dst, val); + case Relaxed: return intrinsics.atomic_sub_relaxed(dst, val); + case Release: return intrinsics.atomic_sub_rel(dst, val); + case Acquire: return intrinsics.atomic_sub_acq(dst, val); + case Acquire_Release: return intrinsics.atomic_sub_acqrel(dst, val); + case Sequentially_Consistent: return intrinsics.atomic_sub(dst, val); } panic("unknown order"); return T{}; @@ -134,11 +136,11 @@ atomic_sub :: proc "contextless" (dst: ^$T, val: T, order: Ordering) -> T { atomic_and :: proc "contextless" (dst: ^$T, val: T, order: Ordering) -> T { using Ordering; #complete switch order { - case Relaxed: return __atomic_and_relaxed(dst, val); - case Release: return __atomic_and_rel(dst, val); - case Acquire: return __atomic_and_acq(dst, val); - case Acquire_Release: return __atomic_and_acqrel(dst, val); - case Sequentially_Consistent: return __atomic_and(dst, val); + case Relaxed: return intrinsics.atomic_and_relaxed(dst, val); + case Release: return intrinsics.atomic_and_rel(dst, val); + case Acquire: return intrinsics.atomic_and_acq(dst, val); + case Acquire_Release: return intrinsics.atomic_and_acqrel(dst, val); + case Sequentially_Consistent: return intrinsics.atomic_and(dst, val); } panic("unknown order"); return T{}; @@ -147,11 +149,11 @@ atomic_and :: proc "contextless" (dst: ^$T, val: T, order: Ordering) -> T { atomic_nand :: proc "contextless" (dst: ^$T, val: T, order: Ordering) -> T { using Ordering; #complete switch order { - case Relaxed: return __atomic_nand_relaxed(dst, val); - case Release: return __atomic_nand_rel(dst, val); - case Acquire: return __atomic_nand_acq(dst, val); - case Acquire_Release: return __atomic_nand_acqrel(dst, val); - case Sequentially_Consistent: return __atomic_nand(dst, val); + case Relaxed: return intrinsics.atomic_nand_relaxed(dst, val); + case Release: return intrinsics.atomic_nand_rel(dst, val); + case Acquire: return intrinsics.atomic_nand_acq(dst, val); + case Acquire_Release: return intrinsics.atomic_nand_acqrel(dst, val); + case Sequentially_Consistent: return intrinsics.atomic_nand(dst, val); } panic("unknown order"); return T{}; @@ -160,11 +162,11 @@ atomic_nand :: proc "contextless" (dst: ^$T, val: T, order: Ordering) -> T { atomic_or :: proc "contextless" (dst: ^$T, val: T, order: Ordering) -> T { using Ordering; #complete switch order { - case Relaxed: return __atomic_or_relaxed(dst, val); - case Release: return __atomic_or_rel(dst, val); - case Acquire: return __atomic_or_acq(dst, val); - case Acquire_Release: return __atomic_or_acqrel(dst, val); - case Sequentially_Consistent: return __atomic_or(dst, val); + case Relaxed: return intrinsics.atomic_or_relaxed(dst, val); + case Release: return intrinsics.atomic_or_rel(dst, val); + case Acquire: return intrinsics.atomic_or_acq(dst, val); + case Acquire_Release: return intrinsics.atomic_or_acqrel(dst, val); + case Sequentially_Consistent: return intrinsics.atomic_or(dst, val); } panic("unknown order"); return T{}; @@ -173,11 +175,11 @@ atomic_or :: proc "contextless" (dst: ^$T, val: T, order: Ordering) -> T { atomic_xor :: proc "contextless" (dst: ^$T, val: T, order: Ordering) -> T { using Ordering; #complete switch order { - case Relaxed: return __atomic_xor_relaxed(dst, val); - case Release: return __atomic_xor_rel(dst, val); - case Acquire: return __atomic_xor_acq(dst, val); - case Acquire_Release: return __atomic_xor_acqrel(dst, val); - case Sequentially_Consistent: return __atomic_xor(dst, val); + case Relaxed: return intrinsics.atomic_xor_relaxed(dst, val); + case Release: return intrinsics.atomic_xor_rel(dst, val); + case Acquire: return intrinsics.atomic_xor_acq(dst, val); + case Acquire_Release: return intrinsics.atomic_xor_acqrel(dst, val); + case Sequentially_Consistent: return intrinsics.atomic_xor(dst, val); } panic("unknown order"); return T{}; diff --git a/src/check_expr.cpp b/src/check_expr.cpp index 60e5d2649..0e4833ef1 100644 --- a/src/check_expr.cpp +++ b/src/check_expr.cpp @@ -2704,11 +2704,12 @@ Entity *check_selector(CheckerContext *c, Operand *operand, Ast *node, Type *typ check_op_expr = false; entity = scope_lookup_current(import_scope, entity_name); bool is_declared = entity != nullptr; + bool allow_builtin = false; if (is_declared) { if (entity->kind == Entity_Builtin) { // NOTE(bill): Builtin's are in the universal scope which is part of every scopes hierarchy // This means that we should just ignore the found result through it - is_declared = false; + allow_builtin = entity->scope == import_scope; } else if ((entity->scope->flags&ScopeFlag_Global) == ScopeFlag_Global && (import_scope->flags&ScopeFlag_Global) == 0) { is_declared = false; } @@ -2723,7 +2724,7 @@ Entity *check_selector(CheckerContext *c, Operand *operand, Ast *node, Type *typ check_entity_decl(c, entity, nullptr, nullptr); GB_ASSERT(entity->type != nullptr); - if (!is_entity_exported(entity)) { + if (!is_entity_exported(entity, allow_builtin)) { gbString sel_str = expr_to_string(selector); error(op_expr, "'%s' is not exported by '%.*s'", sel_str, LIT(import_name)); gb_string_free(sel_str); diff --git a/src/check_stmt.cpp b/src/check_stmt.cpp index 0ae83f1ed..7854081aa 100644 --- a/src/check_stmt.cpp +++ b/src/check_stmt.cpp @@ -1484,7 +1484,7 @@ void check_stmt_internal(CheckerContext *ctx, Ast *node, u32 flags) { } if (entity == nullptr) { - entity = alloc_entity_dummy_variable(builtin_scope, ast_token(name)); + entity = alloc_entity_dummy_variable(builtin_pkg->scope, ast_token(name)); } entities[entity_count++] = entity; @@ -1663,7 +1663,7 @@ void check_stmt_internal(CheckerContext *ctx, Ast *node, u32 flags) { } } if (entity == nullptr) { - entity = alloc_entity_dummy_variable(builtin_scope, ast_token(name)); + entity = alloc_entity_dummy_variable(builtin_pkg->scope, ast_token(name)); } entity->parent_proc_decl = ctx->curr_proc_decl; entities[entity_count++] = entity; diff --git a/src/check_type.cpp b/src/check_type.cpp index f1c9875a1..f38826a25 100644 --- a/src/check_type.cpp +++ b/src/check_type.cpp @@ -2096,7 +2096,7 @@ void init_map_entry_type(Type *type) { } */ Ast *dummy_node = alloc_ast_node(nullptr, Ast_Invalid); - Scope *s = create_scope(builtin_scope, a); + Scope *s = create_scope(builtin_pkg->scope, a); auto fields = array_make(a, 0, 3); array_add(&fields, alloc_entity_field(s, make_token_ident(str_lit("key")), t_map_key, false, 0, EntityState_Resolved)); @@ -2131,7 +2131,7 @@ void init_map_internal_types(Type *type) { */ gbAllocator a = heap_allocator(); Ast *dummy_node = alloc_ast_node(nullptr, Ast_Invalid); - Scope *s = create_scope(builtin_scope, a); + Scope *s = create_scope(builtin_pkg->scope, a); Type *hashes_type = alloc_type_slice(t_int); Type *entries_type = alloc_type_dynamic_array(type->Map.entry_type); diff --git a/src/checker.cpp b/src/checker.cpp index 14daeb7ed..1f41a0d06 100644 --- a/src/checker.cpp +++ b/src/checker.cpp @@ -252,7 +252,7 @@ Scope *create_scope_from_package(CheckerContext *c, AstPackage *pkg) { decl_count += pkg->files[i]->decls.count; } isize init_elements_capacity = 2*decl_count; - Scope *s = create_scope(builtin_scope, c->allocator, init_elements_capacity); + Scope *s = create_scope(builtin_pkg->scope, c->allocator, init_elements_capacity); s->flags |= ScopeFlag_Pkg; s->pkg = pkg; @@ -492,14 +492,14 @@ void add_declaration_dependency(CheckerContext *c, Entity *e) { } -Entity *add_global_entity(Entity *entity) { +Entity *add_global_entity(Entity *entity, Scope *scope=builtin_pkg->scope) { String name = entity->token.string; defer (entity->state = EntityState_Resolved); if (gb_memchr(name.text, ' ', name.len)) { return entity; // NOTE(bill): Usually an 'untyped thing' } - if (scope_insert(builtin_scope, entity)) { + if (scope_insert(scope, entity)) { compiler_error("double declaration"); } return entity; @@ -532,12 +532,17 @@ void init_universal(void) { builtin_pkg->name = str_lit("builtin"); builtin_pkg->kind = Package_Normal; - builtin_scope = create_scope(nullptr, a); - builtin_scope->flags |= ScopeFlag_Pkg | ScopeFlag_Global; - builtin_scope->pkg = builtin_pkg; - builtin_pkg->scope = builtin_scope; + builtin_pkg->scope = create_scope(nullptr, a); + builtin_pkg->scope->flags |= ScopeFlag_Pkg | ScopeFlag_Global; + builtin_pkg->scope->pkg = builtin_pkg; + intrinsics_pkg = gb_alloc_item(a, AstPackage); + intrinsics_pkg->name = str_lit("intrinsics"); + intrinsics_pkg->kind = Package_Normal; + intrinsics_pkg->scope = create_scope(nullptr, a); + intrinsics_pkg->scope->flags |= ScopeFlag_Pkg | ScopeFlag_Global; + intrinsics_pkg->scope->pkg = intrinsics_pkg; // Types @@ -566,7 +571,15 @@ void init_universal(void) { if (name != "") { Entity *entity = alloc_entity(Entity_Builtin, nullptr, make_token_ident(name), t_invalid); entity->Builtin.id = id; - add_global_entity(entity); + switch (builtin_procs[i].pkg) { + case BuiltinProcPkg_builtin: + add_global_entity(entity, builtin_pkg->scope); + break; + case BuiltinProcPkg_intrinsics: + add_global_entity(entity, intrinsics_pkg->scope); + GB_ASSERT(scope_lookup_current(intrinsics_pkg->scope, name) != nullptr); + break; + } } } @@ -2006,8 +2019,8 @@ void check_builtin_attributes(CheckerContext *ctx, Entity *e, Array *attr } if (name == "builtin") { - add_entity(ctx->checker, builtin_scope, nullptr, e); - GB_ASSERT(scope_lookup(builtin_scope, e->token.string) != nullptr); + add_entity(ctx->checker, builtin_pkg->scope, nullptr, e); + GB_ASSERT(scope_lookup(builtin_pkg->scope, e->token.string) != nullptr); if (value != nullptr) { error(value, "'builtin' cannot have a field value"); } @@ -2448,7 +2461,7 @@ void add_import_dependency_node(Checker *c, Ast *decl, Map *M switch (decl->kind) { case_ast_node(id, ImportDecl, decl); String path = id->fullpath; - if (path == "builtin") { + if (is_package_name_reserved(path)) { return; } HashKey key = hash_string(path); @@ -2620,6 +2633,8 @@ void check_add_import_decl(CheckerContext *ctx, Ast *decl) { if (id->fullpath == "builtin") { scope = builtin_pkg->scope; + } else if (id->fullpath == "intrinsics") { + scope = intrinsics_pkg->scope; } else { HashKey key = hash_string(id->fullpath); AstPackage **found = map_get(pkgs, key); diff --git a/src/checker.hpp b/src/checker.hpp index 855a48da3..a5be1eac8 100644 --- a/src/checker.hpp +++ b/src/checker.hpp @@ -46,12 +46,19 @@ enum StmtFlag { Stmt_CheckScopeDecls = 1<<5, }; +enum BuiltinProcPkg { + BuiltinProcPkg_builtin, + BuiltinProcPkg_intrinsics, +}; + struct BuiltinProc { String name; isize arg_count; bool variadic; ExprKind kind; + BuiltinProcPkg pkg; }; + enum BuiltinProcId { BuiltinProc_Invalid, @@ -157,107 +164,107 @@ enum BuiltinProcId { BuiltinProc_COUNT, }; gb_global BuiltinProc builtin_procs[BuiltinProc_COUNT] = { - {STR_LIT(""), 0, false, Expr_Stmt}, + {STR_LIT(""), 0, false, Expr_Stmt, BuiltinProcPkg_builtin}, - {STR_LIT("len"), 1, false, Expr_Expr}, - {STR_LIT("cap"), 1, false, Expr_Expr}, + {STR_LIT("len"), 1, false, Expr_Expr, BuiltinProcPkg_builtin}, + {STR_LIT("cap"), 1, false, Expr_Expr, BuiltinProcPkg_builtin}, - {STR_LIT("size_of"), 1, false, Expr_Expr}, - {STR_LIT("align_of"), 1, false, Expr_Expr}, - {STR_LIT("offset_of"), 2, false, Expr_Expr}, - {STR_LIT("type_of"), 1, false, Expr_Expr}, - {STR_LIT("type_info_of"), 1, false, Expr_Expr}, - {STR_LIT("typeid_of"), 1, false, Expr_Expr}, + {STR_LIT("size_of"), 1, false, Expr_Expr, BuiltinProcPkg_builtin}, + {STR_LIT("align_of"), 1, false, Expr_Expr, BuiltinProcPkg_builtin}, + {STR_LIT("offset_of"), 2, false, Expr_Expr, BuiltinProcPkg_builtin}, + {STR_LIT("type_of"), 1, false, Expr_Expr, BuiltinProcPkg_builtin}, + {STR_LIT("type_info_of"), 1, false, Expr_Expr, BuiltinProcPkg_builtin}, + {STR_LIT("typeid_of"), 1, false, Expr_Expr, BuiltinProcPkg_builtin}, - {STR_LIT("swizzle"), 1, true, Expr_Expr}, + {STR_LIT("swizzle"), 1, true, Expr_Expr, BuiltinProcPkg_builtin}, - {STR_LIT("complex"), 2, false, Expr_Expr}, - {STR_LIT("real"), 1, false, Expr_Expr}, - {STR_LIT("imag"), 1, false, Expr_Expr}, - {STR_LIT("conj"), 1, false, Expr_Expr}, + {STR_LIT("complex"), 2, false, Expr_Expr, BuiltinProcPkg_builtin}, + {STR_LIT("real"), 1, false, Expr_Expr, BuiltinProcPkg_builtin}, + {STR_LIT("imag"), 1, false, Expr_Expr, BuiltinProcPkg_builtin}, + {STR_LIT("conj"), 1, false, Expr_Expr, BuiltinProcPkg_builtin}, - {STR_LIT("expand_to_tuple"), 1, false, Expr_Expr}, + {STR_LIT("expand_to_tuple"), 1, false, Expr_Expr, BuiltinProcPkg_builtin}, - {STR_LIT("min"), 2, true, Expr_Expr}, - {STR_LIT("max"), 2, true, Expr_Expr}, - {STR_LIT("abs"), 1, false, Expr_Expr}, - {STR_LIT("clamp"), 3, false, Expr_Expr}, + {STR_LIT("min"), 2, true, Expr_Expr, BuiltinProcPkg_builtin}, + {STR_LIT("max"), 2, true, Expr_Expr, BuiltinProcPkg_builtin}, + {STR_LIT("abs"), 1, false, Expr_Expr, BuiltinProcPkg_builtin}, + {STR_LIT("clamp"), 3, false, Expr_Expr, BuiltinProcPkg_builtin}, - {STR_LIT(""), 0, true, Expr_Expr}, // DIRECTIVE + {STR_LIT(""), 0, true, Expr_Expr, BuiltinProcPkg_builtin}, // DIRECTIVE // "Intrinsics" - {STR_LIT("__atomic_fence"), 0, false, Expr_Stmt}, - {STR_LIT("__atomic_fence_acq"), 0, false, Expr_Stmt}, - {STR_LIT("__atomic_fence_rel"), 0, false, Expr_Stmt}, - {STR_LIT("__atomic_fence_acqrel"), 0, false, Expr_Stmt}, + {STR_LIT("atomic_fence"), 0, false, Expr_Stmt, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_fence_acq"), 0, false, Expr_Stmt, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_fence_rel"), 0, false, Expr_Stmt, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_fence_acqrel"), 0, false, Expr_Stmt, BuiltinProcPkg_intrinsics}, - {STR_LIT("__atomic_store"), 2, false, Expr_Stmt}, - {STR_LIT("__atomic_store_rel"), 2, false, Expr_Stmt}, - {STR_LIT("__atomic_store_relaxed"), 2, false, Expr_Stmt}, - {STR_LIT("__atomic_store_unordered"), 2, false, Expr_Stmt}, + {STR_LIT("atomic_store"), 2, false, Expr_Stmt, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_store_rel"), 2, false, Expr_Stmt, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_store_relaxed"), 2, false, Expr_Stmt, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_store_unordered"), 2, false, Expr_Stmt, BuiltinProcPkg_intrinsics}, - {STR_LIT("__atomic_load"), 1, false, Expr_Expr}, - {STR_LIT("__atomic_load_acq"), 1, false, Expr_Expr}, - {STR_LIT("__atomic_load_relaxed"), 1, false, Expr_Expr}, - {STR_LIT("__atomic_load_unordered"), 1, false, Expr_Expr}, + {STR_LIT("atomic_load"), 1, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_load_acq"), 1, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_load_relaxed"), 1, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_load_unordered"), 1, false, Expr_Expr, BuiltinProcPkg_intrinsics}, - {STR_LIT("__atomic_add"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_add_acq"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_add_rel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_add_acqrel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_add_relaxed"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_sub"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_sub_acq"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_sub_rel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_sub_acqrel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_sub_relaxed"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_and"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_and_acq"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_and_rel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_and_acqrel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_and_relaxed"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_nand"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_nand_acq"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_nand_rel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_nand_acqrel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_nand_relaxed"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_or"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_or_acq"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_or_rel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_or_acqrel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_or_relaxed"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_xor"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_xor_acq"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_xor_rel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_xor_acqrel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_xor_relaxed"), 2, false, Expr_Expr}, + {STR_LIT("atomic_add"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_add_acq"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_add_rel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_add_acqrel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_add_relaxed"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_sub"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_sub_acq"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_sub_rel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_sub_acqrel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_sub_relaxed"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_and"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_and_acq"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_and_rel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_and_acqrel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_and_relaxed"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_nand"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_nand_acq"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_nand_rel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_nand_acqrel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_nand_relaxed"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_or"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_or_acq"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_or_rel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_or_acqrel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_or_relaxed"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_xor"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_xor_acq"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_xor_rel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_xor_acqrel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_xor_relaxed"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, - {STR_LIT("__atomic_xchg"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_xchg_acq"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_xchg_rel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_xchg_acqrel"), 2, false, Expr_Expr}, - {STR_LIT("__atomic_xchg_relaxed"), 2, false, Expr_Expr}, + {STR_LIT("atomic_xchg"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_xchg_acq"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_xchg_rel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_xchg_acqrel"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_xchg_relaxed"), 2, false, Expr_Expr, BuiltinProcPkg_intrinsics}, - {STR_LIT("__atomic_cxchg"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchg_acq"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchg_rel"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchg_acqrel"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchg_relaxed"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchg_failrelaxed"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchg_failacq"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchg_acq_failrelaxed"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchg_acqrel_failrelaxed"), 3, false, Expr_Expr}, + {STR_LIT("atomic_cxchg"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchg_acq"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchg_rel"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchg_acqrel"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchg_relaxed"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchg_failrelaxed"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchg_failacq"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchg_acq_failrelaxed"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchg_acqrel_failrelaxed"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, - {STR_LIT("__atomic_cxchgweak"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchgweak_acq"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchgweak_rel"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchgweak_acqrel"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchgweak_relaxed"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchgweak_failrelaxed"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchgweak_failacq"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchgweak_acq_failrelaxed"), 3, false, Expr_Expr}, - {STR_LIT("__atomic_cxchgweak_acqrel_failrelaxed"), 3, false, Expr_Expr}, + {STR_LIT("atomic_cxchgweak"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchgweak_acq"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchgweak_rel"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchgweak_acqrel"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchgweak_relaxed"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchgweak_failrelaxed"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchgweak_failacq"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchgweak_acq_failrelaxed"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, + {STR_LIT("atomic_cxchgweak_acqrel_failrelaxed"), 3, false, Expr_Expr, BuiltinProcPkg_intrinsics}, }; @@ -480,9 +487,8 @@ struct Checker { -gb_global AstPackage *builtin_pkg = nullptr; -gb_global Scope * builtin_scope = nullptr; - +gb_global AstPackage *builtin_pkg = nullptr; +gb_global AstPackage *intrinsics_pkg = nullptr; HashKey hash_node (Ast *node) { return hash_pointer(node); } diff --git a/src/entity.cpp b/src/entity.cpp index 15a70f0a5..22c7a24f4 100644 --- a/src/entity.cpp +++ b/src/entity.cpp @@ -153,9 +153,10 @@ struct Entity { }; }; -bool is_entity_kind_exported(EntityKind kind) { +bool is_entity_kind_exported(EntityKind kind, bool allow_builtin = false) { switch (kind) { case Entity_Builtin: + return allow_builtin; case Entity_ImportName: case Entity_LibraryName: case Entity_Nil: @@ -164,10 +165,10 @@ bool is_entity_kind_exported(EntityKind kind) { return true; } -bool is_entity_exported(Entity *e) { +bool is_entity_exported(Entity *e, bool allow_builtin = false) { // TODO(bill): Determine the actual exportation rules for imports of entities GB_ASSERT(e != nullptr); - if (!is_entity_kind_exported(e->kind)) { + if (!is_entity_kind_exported(e->kind, allow_builtin)) { return false; } diff --git a/src/parser.cpp b/src/parser.cpp index 4a563c086..7a8e6770d 100644 --- a/src/parser.cpp +++ b/src/parser.cpp @@ -4142,6 +4142,17 @@ bool is_import_path_valid(String path) { return false; } + +bool is_package_name_reserved(String const &name) { + if (name == "builtin") { + return true; + } else if (name == "intrinsics") { + return true; + } + return false; +} + + bool determine_path_from_string(Parser *p, Ast *node, String base_dir, String original_string, String *path) { GB_ASSERT(path != nullptr); @@ -4212,9 +4223,8 @@ bool determine_path_from_string(Parser *p, Ast *node, String base_dir, String or #endif } - - if (file_str == "builtin") { - *path = str_lit("builtin"); + if (is_package_name_reserved(file_str)) { + *path = file_str; } else { String fullpath = string_trim_whitespace(get_fullpath_relative(a, base_dir, file_str)); *path = fullpath; @@ -4278,7 +4288,7 @@ void parse_setup_file_decls(Parser *p, AstFile *f, String base_dir, Array import_path = string_trim_whitespace(import_path); id->fullpath = import_path; - if (import_path == "builtin") { + if (is_package_name_reserved(import_path)) { continue; } try_add_import_path(p, import_path, original_string, ast_token(node).pos); @@ -4425,7 +4435,7 @@ bool parse_file(Parser *p, AstFile *f) { error(package_name, "Invalid package name '_'"); } else if (f->pkg->kind != Package_Runtime && package_name.string == "runtime") { error(package_name, "Use of reserved package name '%.*s'", LIT(package_name.string)); - } else if (package_name.string == "builtin") { + } else if (is_package_name_reserved(package_name.string)) { error(package_name, "Use of reserved package name '%.*s'", LIT(package_name.string)); } }