From ef30f22e96f6bfb6cd956e2ec355ef1116650a3c Mon Sep 17 00:00:00 2001 From: Brendan Hansen Date: Tue, 15 Nov 2022 17:20:06 -0600 Subject: [PATCH] added optional operator overloading via methods --- compiler/include/astnodes.h | 2 ++ compiler/src/types.c | 5 ++++ core/misc/method_ops.onyx | 47 +++++++++++++++++++++++++++++++++++++ 3 files changed, 54 insertions(+) create mode 100644 core/misc/method_ops.onyx diff --git a/compiler/include/astnodes.h b/compiler/include/astnodes.h index 05349313..ae5b9d29 100644 --- a/compiler/include/astnodes.h +++ b/compiler/include/astnodes.h @@ -689,6 +689,8 @@ struct AstStructLiteral { AstTyped *stnode; Arguments args; + + Type *generated_inferred_type; }; struct AstArrayLiteral { AstTyped_base; diff --git a/compiler/src/types.c b/compiler/src/types.c index e74f0c78..ec3b3334 100644 --- a/compiler/src/types.c +++ b/compiler/src/types.c @@ -709,6 +709,10 @@ Type* type_build_compound_type(bh_allocator alloc, AstCompound* compound) { } Type* type_build_implicit_type_of_struct_literal(bh_allocator alloc, AstStructLiteral* lit) { + if (lit->generated_inferred_type) { + return lit->generated_inferred_type; + } + Type* type = type_create(Type_Kind_Struct, alloc, 0); type->ast_type = NULL; type->Struct.name = NULL; @@ -779,6 +783,7 @@ Type* type_build_implicit_type_of_struct_literal(bh_allocator alloc, AstStructLi build_linear_types_with_offset(type, &type->Struct.linear_members, 0); type->Struct.status = SPS_Uses_Done; + lit->generated_inferred_type = type; return type; } diff --git a/core/misc/method_ops.onyx b/core/misc/method_ops.onyx new file mode 100644 index 00000000..f9d975d1 --- /dev/null +++ b/core/misc/method_ops.onyx @@ -0,0 +1,47 @@ +package core + +#local { + __HasEqMethod :: interface (t: $T, r: $R) { T.__eq(t, r); } + __HasNeMethod :: interface (t: $T, r: $R) { T.__ne(t, r); } + __HasLtMethod :: interface (t: $T, r: $R) { T.__lt(t, r); } + __HasLeMethod :: interface (t: $T, r: $R) { T.__le(t, r); } + __HasGtMethod :: interface (t: $T, r: $R) { T.__gt(t, r); } + __HasGeMethod :: interface (t: $T, r: $R) { T.__ge(t, r); } + __HasAddMethod :: interface (t: $T, r: $R) { T.__add(t, r); } + __HasMinusMethod :: interface (t: $T, r: $R) { T.__minus(t, r); } + __HasMulMethod :: interface (t: $T, r: $R) { T.__mul(t, r); } + __HasDivMethod :: interface (t: $T, r: $R) { T.__div(t, r); } + __HasModMethod :: interface (t: $T, r: $R) { T.__mod(t, r); } + __HasAndMethod :: interface (t: $T, r: $R) { T.__and(t, r); } + __HasOrMethod :: interface (t: $T, r: $R) { T.__or(t, r); } + __HasShlMethod :: interface (t: $T, r: $R) { T.__shl(t, r); } + __HasShrMethod :: interface (t: $T, r: $R) { T.__shr(t, r); } + __HasSarMethod :: interface (t: $T, r: $R) { T.__sar(t, r); } + __HasXorMethod :: interface (t: $T, r: $R) { T.__xor(t, r); } + __HasBandMethod :: interface (t: $T, r: $R) { T.__band(t, r); } + __HasBorMethod :: interface (t: $T, r: $R) { T.__bor(t, r); } + __HasSubMethod :: interface (t: $T, r: $R) { T.__sub(t, r); } +} + +#if #defined(runtime.vars.Onyx_Enable_Operator_Methods) { + #operator == #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasEqMethod(T, R) do return T.__eq(t, r); + #operator != #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasNeMethod(T, R) do return T.__ne(t, r); + #operator < #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasLtMethod(T, R) do return T.__lt(t, r); + #operator <= #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasLeMethod(T, R) do return T.__le(t, r); + #operator > #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasGtMethod(T, R) do return T.__gt(t, r); + #operator >= #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasGeMethod(T, R) do return T.__ge(t, r); + #operator + #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasAddMethod(T, R) do return T.__add(t, r); + #operator - #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasMinusMethod(T, R) do return T.__minus(t, r); + #operator * #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasMulMethod(T, R) do return T.__mul(t, r); + #operator / #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasDivMethod(T, R) do return T.__div(t, r); + #operator % #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasModMethod(T, R) do return T.__mod(t, r); + #operator & #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasAndMethod(T, R) do return T.__and(t, r); + #operator | #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasOrMethod(T, R) do return T.__or(t, r); + #operator << #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasShlMethod(T, R) do return T.__shl(t, r); + #operator >> #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasShrMethod(T, R) do return T.__shr(t, r); + #operator >>> #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasSarMethod(T, R) do return T.__sar(t, r); + #operator ^ #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasXorMethod(T, R) do return T.__xor(t, r); + #operator && #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasBandMethod(T, R) do return T.__band(t, r); + #operator || #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasBorMethod(T, R) do return T.__bor(t, r); + #operator [] #precedence 10000 macro (t: $T, r: $R) -> #auto where __HasSubMethod(T, R) do return T.__sub(t, r); +} -- 2.25.1