mirror of
https://github.com/odin-lang/Odin.git
synced 2026-02-23 03:16:40 +00:00
Implement Explicit context creation #639
This commit is contained in:
@@ -125,7 +125,7 @@ bprintf :: proc(buf: []byte, fmt: string, args: ..any) -> string {
|
||||
}
|
||||
|
||||
|
||||
assertf :: proc "contextless" (condition: bool, fmt: string, args: ..any, loc := #caller_location) -> bool {
|
||||
assertf :: proc(condition: bool, fmt: string, args: ..any, loc := #caller_location) -> bool {
|
||||
if !condition {
|
||||
p := context.assertion_failure_proc;
|
||||
if p == nil {
|
||||
@@ -137,7 +137,7 @@ assertf :: proc "contextless" (condition: bool, fmt: string, args: ..any, loc :=
|
||||
return condition;
|
||||
}
|
||||
|
||||
panicf :: proc "contextless" (fmt: string, args: ..any, loc := #caller_location) {
|
||||
panicf :: proc(fmt: string, args: ..any, loc := #caller_location) {
|
||||
p := context.assertion_failure_proc;
|
||||
if p == nil {
|
||||
p = runtime.default_assertion_failure_proc;
|
||||
|
||||
@@ -440,6 +440,12 @@ default_logger :: proc() -> Logger {
|
||||
}
|
||||
|
||||
|
||||
default_context :: proc "contextless" () -> Context {
|
||||
c: Context;
|
||||
__init_context(&c);
|
||||
return c;
|
||||
}
|
||||
|
||||
@private
|
||||
__init_context_from_ptr :: proc "contextless" (c: ^Context, other: ^Context) {
|
||||
if c == nil do return;
|
||||
|
||||
@@ -7724,6 +7724,15 @@ ExprKind check_expr_base_internal(CheckerContext *c, Operand *o, Ast *node, Type
|
||||
return kind;
|
||||
}
|
||||
|
||||
if (unparen_expr(c->assignment_lhs_hint) == node) {
|
||||
c->scope->flags |= ScopeFlag_ContextDefined;
|
||||
}
|
||||
|
||||
if ((c->scope->flags & ScopeFlag_ContextDefined) == 0) {
|
||||
error(node, "'context' has not been defined within this scope");
|
||||
// Continue with value
|
||||
}
|
||||
|
||||
init_core_context(c->checker);
|
||||
o->mode = Addressing_Context;
|
||||
o->type = t_context;
|
||||
|
||||
@@ -2501,6 +2501,19 @@ bool check_procedure_type(CheckerContext *ctx, Type *type, Ast *proc_type_node,
|
||||
c->curr_proc_sig = type;
|
||||
c->in_proc_sig = true;
|
||||
|
||||
|
||||
ProcCallingConvention cc = pt->calling_convention;
|
||||
if (cc == ProcCC_ForeignBlockDefault) {
|
||||
cc = ProcCC_CDecl;
|
||||
if (c->foreign_context.default_cc > 0) {
|
||||
cc = c->foreign_context.default_cc;
|
||||
}
|
||||
}
|
||||
GB_ASSERT(cc > 0);
|
||||
if (cc == ProcCC_Odin) {
|
||||
c->scope->flags |= ScopeFlag_ContextDefined;
|
||||
}
|
||||
|
||||
bool variadic = false;
|
||||
isize variadic_index = -1;
|
||||
bool success = true;
|
||||
@@ -2534,14 +2547,7 @@ bool check_procedure_type(CheckerContext *ctx, Type *type, Ast *proc_type_node,
|
||||
}
|
||||
|
||||
|
||||
ProcCallingConvention cc = pt->calling_convention;
|
||||
if (cc == ProcCC_ForeignBlockDefault) {
|
||||
cc = ProcCC_CDecl;
|
||||
if (c->foreign_context.default_cc > 0) {
|
||||
cc = c->foreign_context.default_cc;
|
||||
}
|
||||
}
|
||||
GB_ASSERT(cc > 0);
|
||||
|
||||
|
||||
bool optional_ok = (pt->tags & ProcTag_optional_ok) != 0;
|
||||
if (optional_ok) {
|
||||
|
||||
@@ -231,6 +231,11 @@ Scope *create_scope(Scope *parent, gbAllocator allocator, isize init_elements_ca
|
||||
if (parent != nullptr && parent != builtin_pkg->scope) {
|
||||
DLIST_APPEND(parent->first_child, parent->last_child, s);
|
||||
}
|
||||
|
||||
if (parent != nullptr && parent->flags & ScopeFlag_ContextDefined) {
|
||||
s->flags |= ScopeFlag_ContextDefined;
|
||||
}
|
||||
|
||||
return s;
|
||||
}
|
||||
|
||||
|
||||
@@ -158,7 +158,7 @@ struct ProcInfo {
|
||||
|
||||
|
||||
|
||||
enum ScopeFlag {
|
||||
enum ScopeFlag : i32 {
|
||||
ScopeFlag_Pkg = 1<<1,
|
||||
ScopeFlag_Global = 1<<2,
|
||||
ScopeFlag_File = 1<<3,
|
||||
@@ -167,6 +167,8 @@ enum ScopeFlag {
|
||||
ScopeFlag_Type = 1<<6,
|
||||
|
||||
ScopeFlag_HasBeenImported = 1<<10, // This is only applicable to file scopes
|
||||
|
||||
ScopeFlag_ContextDefined = 1<<16,
|
||||
};
|
||||
|
||||
struct Scope {
|
||||
|
||||
Reference in New Issue
Block a user