aboutsummaryrefslogtreecommitdiff
path: root/src/checker.cpp
diff options
context:
space:
mode:
authorgingerBill <bill@gingerbill.org>2021-11-04 12:40:50 +0000
committergingerBill <bill@gingerbill.org>2021-11-04 12:40:50 +0000
commit6ded538546cca4f1e50a011a64932f7f3c784cc2 (patch)
tree03ac73c9042cc45ab20da51a93de3f9bf6f8de0f /src/checker.cpp
parent3fa7dabaa87e99386e469bd5e4badab23f89aaef (diff)
`@(linkage=<string>)` for procedures and variables; `@(require)` for procedures; `package runtime` linkage improvements; Subsequence improvements to `lb_run_remove_unused_function_pass`
Diffstat (limited to 'src/checker.cpp')
-rw-r--r--src/checker.cpp55
1 files changed, 53 insertions, 2 deletions
diff --git a/src/checker.cpp b/src/checker.cpp
index 92e38a643..591377726 100644
--- a/src/checker.cpp
+++ b/src/checker.cpp
@@ -783,6 +783,7 @@ void init_universal(void) {
add_global_bool_constant("ODIN_DEFAULT_TO_NIL_ALLOCATOR", bc->ODIN_DEFAULT_TO_NIL_ALLOCATOR);
add_global_bool_constant("ODIN_NO_DYNAMIC_LITERALS", bc->no_dynamic_literals);
add_global_bool_constant("ODIN_NO_CRT", bc->no_crt);
+ add_global_bool_constant("ODIN_USE_SEPARATE_MODULES", bc->use_separate_modules);
add_global_bool_constant("ODIN_TEST", bc->command_kind == Command_test);
@@ -1388,7 +1389,9 @@ bool could_entity_be_lazy(Entity *e, DeclInfo *d) {
return false;
} else if (name == "init") {
return false;
- }
+ } else if (name == "linkage") {
+ return false;
+ }
}
}
}
@@ -2658,6 +2661,32 @@ DECL_ATTRIBUTE_PROC(proc_decl_attribute) {
return false;
}
return true;
+ } else if (name == "linkage") {
+ ExactValue ev = check_decl_attribute_value(c, value);
+ if (ev.kind != ExactValue_String) {
+ error(value, "Expected either a string 'linkage'");
+ return false;
+ }
+ String linkage = ev.value_string;
+ if (linkage == "internal" ||
+ linkage == "strong" ||
+ linkage == "weak" ||
+ linkage == "link_once") {
+ ac->linkage = linkage;
+ } else {
+ error(elem, "Invalid linkage '%.*s'. Valid kinds:", LIT(linkage));
+ error_line("\tinternal\n");
+ error_line("\tstrong\n");
+ error_line("\tweak\n");
+ error_line("\tlink_once\n");
+ }
+ return true;
+ } else if (name == "require") {
+ if (value != nullptr) {
+ error(elem, "'require' does not have any parameters");
+ }
+ ac->require_declaration = true;
+ return true;
} else if (name == "init") {
if (value != nullptr) {
error(value, "'%.*s' expects no parameter, or a string literal containing \"file\" or \"package\"", LIT(name));
@@ -2894,7 +2923,7 @@ DECL_ATTRIBUTE_PROC(var_decl_attribute) {
if (name == "require") {
if (value != nullptr) {
- error(elem, "'static' does not have any parameters");
+ error(elem, "'require' does not have any parameters");
}
ac->require_declaration = true;
return true;
@@ -2912,6 +2941,26 @@ DECL_ATTRIBUTE_PROC(var_decl_attribute) {
error(elem, "An exported variable cannot be thread local");
}
return true;
+ } else if (name == "linkage") {
+ ExactValue ev = check_decl_attribute_value(c, value);
+ if (ev.kind != ExactValue_String) {
+ error(value, "Expected either a string 'linkage'");
+ return false;
+ }
+ String linkage = ev.value_string;
+ if (linkage == "internal" ||
+ linkage == "strong" ||
+ linkage == "weak" ||
+ linkage == "link_once") {
+ ac->linkage = linkage;
+ } else {
+ error(elem, "Invalid linkage '%.*s'. Valid kinds:", LIT(linkage));
+ error_line("\tinternal\n");
+ error_line("\tstrong\n");
+ error_line("\tweak\n");
+ error_line("\tlink_once\n");
+ }
+ return true;
} else if (name == "link_name") {
if (ev.kind == ExactValue_String) {
ac->link_name = ev.value_string;
@@ -3959,6 +4008,8 @@ DECL_ATTRIBUTE_PROC(foreign_import_decl_attribute) {
if (name == "force" || name == "require") {
if (value != nullptr) {
error(elem, "Expected no parameter for '%.*s'", LIT(name));
+ } else if (name == "force") {
+ warning(elem, "'force' is deprecated and is identical to 'require'");
}
ac->require_declaration = true;
return true;