Add #no_broadcast procedure parameter to disallow automatic array programming broadcasting on procedure arguments

This commit is contained in:
gingerBill
2024-03-21 11:52:48 +00:00
parent fc587c507a
commit 29e5f94c2a
11 changed files with 113 additions and 72 deletions
+6 -6
View File
@@ -447,12 +447,12 @@ _append_elem :: #force_inline proc(array: ^$T/[dynamic]$E, arg: E, should_zero:
} }
@builtin @builtin
append_elem :: proc(array: ^$T/[dynamic]$E, arg: E, loc := #caller_location) -> (n: int, err: Allocator_Error) #optional_allocator_error { append_elem :: proc(array: ^$T/[dynamic]$E, #no_broadcast arg: E, loc := #caller_location) -> (n: int, err: Allocator_Error) #optional_allocator_error {
return _append_elem(array, arg, true, loc=loc) return _append_elem(array, arg, true, loc=loc)
} }
@builtin @builtin
non_zero_append_elem :: proc(array: ^$T/[dynamic]$E, arg: E, loc := #caller_location) -> (n: int, err: Allocator_Error) #optional_allocator_error { non_zero_append_elem :: proc(array: ^$T/[dynamic]$E, #no_broadcast arg: E, loc := #caller_location) -> (n: int, err: Allocator_Error) #optional_allocator_error {
return _append_elem(array, arg, false, loc=loc) return _append_elem(array, arg, false, loc=loc)
} }
@@ -496,12 +496,12 @@ _append_elems :: #force_inline proc(array: ^$T/[dynamic]$E, should_zero: bool, l
} }
@builtin @builtin
append_elems :: proc(array: ^$T/[dynamic]$E, args: ..E, loc := #caller_location) -> (n: int, err: Allocator_Error) #optional_allocator_error { append_elems :: proc(array: ^$T/[dynamic]$E, #no_broadcast args: ..E, loc := #caller_location) -> (n: int, err: Allocator_Error) #optional_allocator_error {
return _append_elems(array, true, loc, ..args) return _append_elems(array, true, loc, ..args)
} }
@builtin @builtin
non_zero_append_elems :: proc(array: ^$T/[dynamic]$E, args: ..E, loc := #caller_location) -> (n: int, err: Allocator_Error) #optional_allocator_error { non_zero_append_elems :: proc(array: ^$T/[dynamic]$E, #no_broadcast args: ..E, loc := #caller_location) -> (n: int, err: Allocator_Error) #optional_allocator_error {
return _append_elems(array, false, loc, ..args) return _append_elems(array, false, loc, ..args)
} }
@@ -556,7 +556,7 @@ append_nothing :: proc(array: ^$T/[dynamic]$E, loc := #caller_location) -> (n: i
@builtin @builtin
inject_at_elem :: proc(array: ^$T/[dynamic]$E, index: int, arg: E, loc := #caller_location) -> (ok: bool, err: Allocator_Error) #no_bounds_check #optional_allocator_error { inject_at_elem :: proc(array: ^$T/[dynamic]$E, index: int, #no_broadcast arg: E, loc := #caller_location) -> (ok: bool, err: Allocator_Error) #no_bounds_check #optional_allocator_error {
if array == nil { if array == nil {
return return
} }
@@ -574,7 +574,7 @@ inject_at_elem :: proc(array: ^$T/[dynamic]$E, index: int, arg: E, loc := #calle
} }
@builtin @builtin
inject_at_elems :: proc(array: ^$T/[dynamic]$E, index: int, args: ..E, loc := #caller_location) -> (ok: bool, err: Allocator_Error) #no_bounds_check #optional_allocator_error { inject_at_elems :: proc(array: ^$T/[dynamic]$E, index: int, #no_broadcast args: ..E, loc := #caller_location) -> (ok: bool, err: Allocator_Error) #no_bounds_check #optional_allocator_error {
if array == nil { if array == nil {
return return
} }
+18 -18
View File
@@ -651,7 +651,7 @@ alpha_add_if_missing :: proc(img: ^Image, alpha_key := Alpha_Key{}, allocator :=
// We have keyed alpha. // We have keyed alpha.
o: GA_Pixel o: GA_Pixel
for p in inp { for p in inp {
if p == key.r { if p.r == key.r {
o = GA_Pixel{0, key.g} o = GA_Pixel{0, key.g}
} else { } else {
o = GA_Pixel{p.r, 255} o = GA_Pixel{p.r, 255}
@@ -710,7 +710,7 @@ alpha_add_if_missing :: proc(img: ^Image, alpha_key := Alpha_Key{}, allocator :=
// We have keyed alpha. // We have keyed alpha.
o: GA_Pixel_16 o: GA_Pixel_16
for p in inp { for p in inp {
if p == key.r { if p.r == key.r {
o = GA_Pixel_16{0, key.g} o = GA_Pixel_16{0, key.g}
} else { } else {
o = GA_Pixel_16{p.r, 65535} o = GA_Pixel_16{p.r, 65535}
@@ -842,11 +842,11 @@ alpha_drop_if_present :: proc(img: ^Image, options := Options{}, alpha_key := Al
bg := G_Pixel{} bg := G_Pixel{}
if temp_bg, temp_bg_ok := img.background.(RGB_Pixel_16); temp_bg_ok { if temp_bg, temp_bg_ok := img.background.(RGB_Pixel_16); temp_bg_ok {
// Background is RGB 16-bit, take just the red channel's topmost byte. // Background is RGB 16-bit, take just the red channel's topmost byte.
bg = u8(temp_bg.r >> 8) bg.r = u8(temp_bg.r >> 8)
} }
for p in inp { for p in inp {
out[0] = bg if p == key else p out[0] = bg if p.r == key else p
out = out[1:] out = out[1:]
} }
@@ -865,8 +865,8 @@ alpha_drop_if_present :: proc(img: ^Image, options := Options{}, alpha_key := Al
for p in inp { for p in inp {
a := f32(p.g) / 255.0 a := f32(p.g) / 255.0
c := ((1.0 - a) * bg + a * f32(p.r)) c := ((1.0 - a) * bg + a * f32(p.r))
out[0] = u8(c) out[0].r = u8(c)
out = out[1:] out = out[1:]
} }
} else if .alpha_premultiply in options { } else if .alpha_premultiply in options {
@@ -874,14 +874,14 @@ alpha_drop_if_present :: proc(img: ^Image, options := Options{}, alpha_key := Al
for p in inp { for p in inp {
a := f32(p.g) / 255.0 a := f32(p.g) / 255.0
c := f32(p.r) * a c := f32(p.r) * a
out[0] = u8(c) out[0].r = u8(c)
out = out[1:] out = out[1:]
} }
} else { } else {
// Just drop alpha on the floor. // Just drop alpha on the floor.
for p in inp { for p in inp {
out[0] = p.r out[0].r = p.r
out = out[1:] out = out[1:]
} }
} }
@@ -951,11 +951,11 @@ alpha_drop_if_present :: proc(img: ^Image, options := Options{}, alpha_key := Al
bg := G_Pixel_16{} bg := G_Pixel_16{}
if temp_bg, temp_bg_ok := img.background.(RGB_Pixel_16); temp_bg_ok { if temp_bg, temp_bg_ok := img.background.(RGB_Pixel_16); temp_bg_ok {
// Background is RGB 16-bit, take just the red channel. // Background is RGB 16-bit, take just the red channel.
bg = temp_bg.r bg.r = temp_bg.r
} }
for p in inp { for p in inp {
out[0] = bg if p == key else p out[0] = bg if p.r == key else p
out = out[1:] out = out[1:]
} }
@@ -974,8 +974,8 @@ alpha_drop_if_present :: proc(img: ^Image, options := Options{}, alpha_key := Al
for p in inp { for p in inp {
a := f32(p.g) / 65535.0 a := f32(p.g) / 65535.0
c := ((1.0 - a) * bg + a * f32(p.r)) c := ((1.0 - a) * bg + a * f32(p.r))
out[0] = u16(c) out[0].r = u16(c)
out = out[1:] out = out[1:]
} }
} else if .alpha_premultiply in options { } else if .alpha_premultiply in options {
@@ -983,14 +983,14 @@ alpha_drop_if_present :: proc(img: ^Image, options := Options{}, alpha_key := Al
for p in inp { for p in inp {
a := f32(p.g) / 65535.0 a := f32(p.g) / 65535.0
c := f32(p.r) * a c := f32(p.r) * a
out[0] = u16(c) out[0].r = u16(c)
out = out[1:] out = out[1:]
} }
} else { } else {
// Just drop alpha on the floor. // Just drop alpha on the floor.
for p in inp { for p in inp {
out[0] = p.r out[0].r = p.r
out = out[1:] out = out[1:]
} }
} }
+1 -1
View File
@@ -1112,7 +1112,7 @@ internal_int_prime_next_prime :: proc(a: ^Int, trials: int, bbs_style: bool, all
Generate the restable. Generate the restable.
*/ */
for x := 1; x < _PRIME_TAB_SIZE; x += 1 { for x := 1; x < _PRIME_TAB_SIZE; x += 1 {
res_tab = internal_mod(a, _private_prime_table[x]) or_return res_tab = cast(type_of(res_tab))(internal_mod(a, _private_prime_table[x]) or_return)
} }
for { for {
+10 -6
View File
@@ -597,6 +597,7 @@ Field_Flag :: enum {
Any_Int, Any_Int,
Subtype, Subtype,
By_Ptr, By_Ptr,
No_Broadcast,
Results, Results,
Tags, Tags,
@@ -616,6 +617,7 @@ field_flag_strings := [Field_Flag]string{
.Any_Int = "#any_int", .Any_Int = "#any_int",
.Subtype = "#subtype", .Subtype = "#subtype",
.By_Ptr = "#by_ptr", .By_Ptr = "#by_ptr",
.No_Broadcast ="#no_broadcast",
.Results = "results", .Results = "results",
.Tags = "field tag", .Tags = "field tag",
@@ -624,12 +626,13 @@ field_flag_strings := [Field_Flag]string{
} }
field_hash_flag_strings := []struct{key: string, flag: Field_Flag}{ field_hash_flag_strings := []struct{key: string, flag: Field_Flag}{
{"no_alias", .No_Alias}, {"no_alias", .No_Alias},
{"c_vararg", .C_Vararg}, {"c_vararg", .C_Vararg},
{"const", .Const}, {"const", .Const},
{"any_int", .Any_Int}, {"any_int", .Any_Int},
{"subtype", .Subtype}, {"subtype", .Subtype},
{"by_ptr", .By_Ptr}, {"by_ptr", .By_Ptr},
{"no_broadcast", .No_Broadcast},
} }
@@ -650,6 +653,7 @@ Field_Flags_Signature :: Field_Flags{
.Const, .Const,
.Any_Int, .Any_Int,
.By_Ptr, .By_Ptr,
.No_Broadcast,
.Default_Parameters, .Default_Parameters,
} }
+1 -1
View File
@@ -163,7 +163,7 @@ create_and_start_with_data :: proc(data: rawptr, fn: proc(data: rawptr), init_co
t := create(thread_proc, priority) t := create(thread_proc, priority)
t.data = rawptr(fn) t.data = rawptr(fn)
t.user_index = 1 t.user_index = 1
t.user_args = data t.user_args[0] = data
if self_cleanup { if self_cleanup {
t.flags += {.Self_Cleanup} t.flags += {.Self_Cleanup}
} }
+48 -28
View File
@@ -623,7 +623,7 @@ gb_internal bool check_cast_internal(CheckerContext *c, Operand *x, Type *type);
#define MAXIMUM_TYPE_DISTANCE 10 #define MAXIMUM_TYPE_DISTANCE 10
gb_internal i64 check_distance_between_types(CheckerContext *c, Operand *operand, Type *type) { gb_internal i64 check_distance_between_types(CheckerContext *c, Operand *operand, Type *type, bool allow_array_programming) {
if (c == nullptr) { if (c == nullptr) {
GB_ASSERT(operand->mode == Addressing_Value); GB_ASSERT(operand->mode == Addressing_Value);
GB_ASSERT(is_type_typed(operand->type)); GB_ASSERT(is_type_typed(operand->type));
@@ -832,7 +832,7 @@ gb_internal i64 check_distance_between_types(CheckerContext *c, Operand *operand
if (dst->Union.variants.count == 1) { if (dst->Union.variants.count == 1) {
Type *vt = dst->Union.variants[0]; Type *vt = dst->Union.variants[0];
i64 score = check_distance_between_types(c, operand, vt); i64 score = check_distance_between_types(c, operand, vt, allow_array_programming);
if (score >= 0) { if (score >= 0) {
return score+2; return score+2;
} }
@@ -840,7 +840,7 @@ gb_internal i64 check_distance_between_types(CheckerContext *c, Operand *operand
i64 prev_lowest_score = -1; i64 prev_lowest_score = -1;
i64 lowest_score = -1; i64 lowest_score = -1;
for (Type *vt : dst->Union.variants) { for (Type *vt : dst->Union.variants) {
i64 score = check_distance_between_types(c, operand, vt); i64 score = check_distance_between_types(c, operand, vt, allow_array_programming);
if (score >= 0) { if (score >= 0) {
if (lowest_score < 0) { if (lowest_score < 0) {
lowest_score = score; lowest_score = score;
@@ -863,14 +863,14 @@ gb_internal i64 check_distance_between_types(CheckerContext *c, Operand *operand
} }
if (is_type_relative_pointer(dst)) { if (is_type_relative_pointer(dst)) {
i64 score = check_distance_between_types(c, operand, dst->RelativePointer.pointer_type); i64 score = check_distance_between_types(c, operand, dst->RelativePointer.pointer_type, allow_array_programming);
if (score >= 0) { if (score >= 0) {
return score+2; return score+2;
} }
} }
if (is_type_relative_multi_pointer(dst)) { if (is_type_relative_multi_pointer(dst)) {
i64 score = check_distance_between_types(c, operand, dst->RelativeMultiPointer.pointer_type); i64 score = check_distance_between_types(c, operand, dst->RelativeMultiPointer.pointer_type, allow_array_programming);
if (score >= 0) { if (score >= 0) {
return score+2; return score+2;
} }
@@ -896,19 +896,21 @@ gb_internal i64 check_distance_between_types(CheckerContext *c, Operand *operand
} }
} }
if (is_type_array(dst)) { if (allow_array_programming) {
Type *elem = base_array_type(dst); if (is_type_array(dst)) {
i64 distance = check_distance_between_types(c, operand, elem); Type *elem = base_array_type(dst);
if (distance >= 0) { i64 distance = check_distance_between_types(c, operand, elem, allow_array_programming);
return distance + 6; if (distance >= 0) {
return distance + 6;
}
} }
}
if (is_type_simd_vector(dst)) { if (is_type_simd_vector(dst)) {
Type *dst_elem = base_array_type(dst); Type *dst_elem = base_array_type(dst);
i64 distance = check_distance_between_types(c, operand, dst_elem); i64 distance = check_distance_between_types(c, operand, dst_elem, allow_array_programming);
if (distance >= 0) { if (distance >= 0) {
return distance + 6; return distance + 6;
}
} }
} }
@@ -918,7 +920,7 @@ gb_internal i64 check_distance_between_types(CheckerContext *c, Operand *operand
} }
if (dst->Matrix.row_count == dst->Matrix.column_count) { if (dst->Matrix.row_count == dst->Matrix.column_count) {
Type *dst_elem = base_array_type(dst); Type *dst_elem = base_array_type(dst);
i64 distance = check_distance_between_types(c, operand, dst_elem); i64 distance = check_distance_between_types(c, operand, dst_elem, allow_array_programming);
if (distance >= 0) { if (distance >= 0) {
return distance + 7; return distance + 7;
} }
@@ -966,9 +968,9 @@ gb_internal i64 assign_score_function(i64 distance, bool is_variadic=false) {
} }
gb_internal bool check_is_assignable_to_with_score(CheckerContext *c, Operand *operand, Type *type, i64 *score_, bool is_variadic=false) { gb_internal bool check_is_assignable_to_with_score(CheckerContext *c, Operand *operand, Type *type, i64 *score_, bool is_variadic=false, bool allow_array_programming=true) {
i64 score = 0; i64 score = 0;
i64 distance = check_distance_between_types(c, operand, type); i64 distance = check_distance_between_types(c, operand, type, allow_array_programming);
bool ok = distance >= 0; bool ok = distance >= 0;
if (ok) { if (ok) {
score = assign_score_function(distance, is_variadic); score = assign_score_function(distance, is_variadic);
@@ -978,9 +980,9 @@ gb_internal bool check_is_assignable_to_with_score(CheckerContext *c, Operand *o
} }
gb_internal bool check_is_assignable_to(CheckerContext *c, Operand *operand, Type *type) { gb_internal bool check_is_assignable_to(CheckerContext *c, Operand *operand, Type *type, bool allow_array_programming=true) {
i64 score = 0; i64 score = 0;
return check_is_assignable_to_with_score(c, operand, type, &score); return check_is_assignable_to_with_score(c, operand, type, &score, /*is_variadic*/false, allow_array_programming);
} }
gb_internal bool internal_check_is_assignable_to(Type *src, Type *dst) { gb_internal bool internal_check_is_assignable_to(Type *src, Type *dst) {
@@ -3142,6 +3144,14 @@ gb_internal bool check_is_castable_to(CheckerContext *c, Operand *operand, Type
return true; return true;
} }
if (is_type_array(dst)) {
Type *elem = base_array_type(dst);
if (check_is_castable_to(c, operand, elem)) {
return true;
}
}
if (is_type_simd_vector(src) && is_type_simd_vector(dst)) { if (is_type_simd_vector(src) && is_type_simd_vector(dst)) {
if (src->SimdVector.count != dst->SimdVector.count) { if (src->SimdVector.count != dst->SimdVector.count) {
return false; return false;
@@ -5853,15 +5863,20 @@ gb_internal CallArgumentError check_call_arguments_internal(CheckerContext *c, A
} }
} }
auto eval_param_and_score = [](CheckerContext *c, Operand *o, Type *param_type, CallArgumentError &err, bool param_is_variadic, Entity *e, bool show_error) -> i64 { auto eval_param_and_score = [](CheckerContext *c, Operand *o, Type *param_type, CallArgumentError &err, bool param_is_variadic, Entity *e, bool show_error, bool allow_array_programming) -> i64 {
i64 s = 0; i64 s = 0;
if (!check_is_assignable_to_with_score(c, o, param_type, &s, param_is_variadic)) { if (!check_is_assignable_to_with_score(c, o, param_type, &s, param_is_variadic, allow_array_programming)) {
bool ok = false; bool ok = false;
if (e && e->flags & EntityFlag_AnyInt) { if (e && (e->flags & EntityFlag_AnyInt)) {
if (is_type_integer(param_type)) { if (is_type_integer(param_type)) {
ok = check_is_castable_to(c, o, param_type); ok = check_is_castable_to(c, o, param_type);
} }
} }
if (!allow_array_programming && check_is_assignable_to_with_score(c, o, param_type, nullptr, param_is_variadic, !allow_array_programming)) {
if (show_error) {
error(o->expr, "'#no_broadcast' disallows automatic broadcasting a value across all elements of an array-like type in a procedure argument");
}
}
if (ok) { if (ok) {
s = assign_score_function(MAXIMUM_TYPE_DISTANCE); s = assign_score_function(MAXIMUM_TYPE_DISTANCE);
} else { } else {
@@ -5878,7 +5893,6 @@ gb_internal CallArgumentError check_call_arguments_internal(CheckerContext *c, A
} }
err = CallArgumentError_WrongTypes; err = CallArgumentError_WrongTypes;
} }
} else if (show_error) { } else if (show_error) {
check_assignment(c, o, param_type, str_lit("procedure argument")); check_assignment(c, o, param_type, str_lit("procedure argument"));
} }
@@ -5963,12 +5977,14 @@ gb_internal CallArgumentError check_call_arguments_internal(CheckerContext *c, A
if (param_is_variadic) { if (param_is_variadic) {
continue; continue;
} }
score += eval_param_and_score(c, o, e->type, err, param_is_variadic, e, show_error); bool allow_array_programming = !(e && (e->flags & EntityFlag_NoBroadcast));
score += eval_param_and_score(c, o, e->type, err, param_is_variadic, e, show_error, allow_array_programming);
} }
} }
if (variadic) { if (variadic) {
Type *slice = pt->params->Tuple.variables[pt->variadic_index]->type; Entity *var_entity = pt->params->Tuple.variables[pt->variadic_index];
Type *slice = var_entity->type;
GB_ASSERT(is_type_slice(slice)); GB_ASSERT(is_type_slice(slice));
Type *elem = base_type(slice)->Slice.elem; Type *elem = base_type(slice)->Slice.elem;
Type *t = elem; Type *t = elem;
@@ -5994,7 +6010,8 @@ gb_internal CallArgumentError check_call_arguments_internal(CheckerContext *c, A
return CallArgumentError_MultipleVariadicExpand; return CallArgumentError_MultipleVariadicExpand;
} }
} }
score += eval_param_and_score(c, o, t, err, true, nullptr, show_error); bool allow_array_programming = !(var_entity && (var_entity->flags & EntityFlag_NoBroadcast));
score += eval_param_and_score(c, o, t, err, true, nullptr, show_error, allow_array_programming);
} }
} }
@@ -11148,6 +11165,9 @@ gb_internal gbString write_expr_to_string(gbString str, Ast *node, bool shorthan
if (f->flags&FieldFlag_any_int) { if (f->flags&FieldFlag_any_int) {
str = gb_string_appendc(str, "#any_int "); str = gb_string_appendc(str, "#any_int ");
} }
if (f->flags&FieldFlag_no_broadcast) {
str = gb_string_appendc(str, "#no_broadcast ");
}
if (f->flags&FieldFlag_const) { if (f->flags&FieldFlag_const) {
str = gb_string_appendc(str, "#const "); str = gb_string_appendc(str, "#const ");
} }
+15 -1
View File
@@ -1869,6 +1869,10 @@ gb_internal Type *check_get_params(CheckerContext *ctx, Scope *scope, Ast *_para
error(name, "'#any_int' can only be applied to variable fields"); error(name, "'#any_int' can only be applied to variable fields");
p->flags &= ~FieldFlag_any_int; p->flags &= ~FieldFlag_any_int;
} }
if (p->flags&FieldFlag_no_broadcast) {
error(name, "'#no_broadcast' can only be applied to variable fields");
p->flags &= ~FieldFlag_no_broadcast;
}
if (p->flags&FieldFlag_by_ptr) { if (p->flags&FieldFlag_by_ptr) {
error(name, "'#by_ptr' can only be applied to variable fields"); error(name, "'#by_ptr' can only be applied to variable fields");
p->flags &= ~FieldFlag_by_ptr; p->flags &= ~FieldFlag_by_ptr;
@@ -1926,7 +1930,13 @@ gb_internal Type *check_get_params(CheckerContext *ctx, Scope *scope, Ast *_para
} }
} }
} }
if (type != t_invalid && !check_is_assignable_to(ctx, &op, type)) {
bool allow_array_programming = true;
if (p->flags&FieldFlag_no_broadcast) {
allow_array_programming = false;
}
if (type != t_invalid && !check_is_assignable_to(ctx, &op, type, allow_array_programming)) {
bool ok = true; bool ok = true;
if (p->flags&FieldFlag_any_int) { if (p->flags&FieldFlag_any_int) {
if ((!is_type_integer(op.type) && !is_type_enum(op.type)) || (!is_type_integer(type) && !is_type_enum(type))) { if ((!is_type_integer(op.type) && !is_type_enum(op.type)) || (!is_type_integer(type) && !is_type_enum(type))) {
@@ -2002,6 +2012,10 @@ gb_internal Type *check_get_params(CheckerContext *ctx, Scope *scope, Ast *_para
if (p->flags&FieldFlag_no_alias) { if (p->flags&FieldFlag_no_alias) {
param->flags |= EntityFlag_NoAlias; param->flags |= EntityFlag_NoAlias;
} }
if (p->flags&FieldFlag_no_broadcast) {
param->flags |= EntityFlag_NoBroadcast;
}
if (p->flags&FieldFlag_any_int) { if (p->flags&FieldFlag_any_int) {
if (!is_type_integer(param->type) && !is_type_enum(param->type)) { if (!is_type_integer(param->type) && !is_type_enum(param->type)) {
gbString str = type_to_string(param->type); gbString str = type_to_string(param->type);
+1
View File
@@ -61,6 +61,7 @@ enum EntityFlag : u64 {
EntityFlag_CVarArg = 1ull<<22, EntityFlag_CVarArg = 1ull<<22,
EntityFlag_NoBroadcast = 1ull<<23,
EntityFlag_AnyInt = 1ull<<24, EntityFlag_AnyInt = 1ull<<24,
EntityFlag_Disabled = 1ull<<25, EntityFlag_Disabled = 1ull<<25,
+9 -8
View File
@@ -3898,14 +3898,15 @@ struct ParseFieldPrefixMapping {
FieldFlag flag; FieldFlag flag;
}; };
gb_global ParseFieldPrefixMapping parse_field_prefix_mappings[] = { gb_global ParseFieldPrefixMapping const parse_field_prefix_mappings[] = {
{str_lit("using"), Token_using, FieldFlag_using}, {str_lit("using"), Token_using, FieldFlag_using},
{str_lit("no_alias"), Token_Hash, FieldFlag_no_alias}, {str_lit("no_alias"), Token_Hash, FieldFlag_no_alias},
{str_lit("c_vararg"), Token_Hash, FieldFlag_c_vararg}, {str_lit("c_vararg"), Token_Hash, FieldFlag_c_vararg},
{str_lit("const"), Token_Hash, FieldFlag_const}, {str_lit("const"), Token_Hash, FieldFlag_const},
{str_lit("any_int"), Token_Hash, FieldFlag_any_int}, {str_lit("any_int"), Token_Hash, FieldFlag_any_int},
{str_lit("subtype"), Token_Hash, FieldFlag_subtype}, {str_lit("subtype"), Token_Hash, FieldFlag_subtype},
{str_lit("by_ptr"), Token_Hash, FieldFlag_by_ptr}, {str_lit("by_ptr"), Token_Hash, FieldFlag_by_ptr},
{str_lit("no_broadcast"), Token_Hash, FieldFlag_no_broadcast},
}; };
+2 -1
View File
@@ -326,6 +326,7 @@ enum FieldFlag : u32 {
FieldFlag_any_int = 1<<6, FieldFlag_any_int = 1<<6,
FieldFlag_subtype = 1<<7, FieldFlag_subtype = 1<<7,
FieldFlag_by_ptr = 1<<8, FieldFlag_by_ptr = 1<<8,
FieldFlag_no_broadcast = 1<<9, // disallow array programming
// Internal use by the parser only // Internal use by the parser only
FieldFlag_Tags = 1<<10, FieldFlag_Tags = 1<<10,
@@ -336,7 +337,7 @@ enum FieldFlag : u32 {
FieldFlag_Invalid = 1u<<31, FieldFlag_Invalid = 1u<<31,
// Parameter List Restrictions // Parameter List Restrictions
FieldFlag_Signature = FieldFlag_ellipsis|FieldFlag_using|FieldFlag_no_alias|FieldFlag_c_vararg|FieldFlag_const|FieldFlag_any_int|FieldFlag_by_ptr, FieldFlag_Signature = FieldFlag_ellipsis|FieldFlag_using|FieldFlag_no_alias|FieldFlag_c_vararg|FieldFlag_const|FieldFlag_any_int|FieldFlag_by_ptr|FieldFlag_no_broadcast,
FieldFlag_Struct = FieldFlag_using|FieldFlag_subtype|FieldFlag_Tags, FieldFlag_Struct = FieldFlag_using|FieldFlag_subtype|FieldFlag_Tags,
}; };
+2 -2
View File
@@ -159,7 +159,7 @@ Vector2Transform :: proc "c" (v: Vector2, m: Matrix) -> Vector2 {
// Calculate linear interpolation between two vectors // Calculate linear interpolation between two vectors
@(require_results, deprecated="Prefer = linalg.lerp(v1, v2, amount)") @(require_results, deprecated="Prefer = linalg.lerp(v1, v2, amount)")
Vector2Lerp :: proc "c" (v1, v2: Vector2, amount: f32) -> Vector2 { Vector2Lerp :: proc "c" (v1, v2: Vector2, amount: f32) -> Vector2 {
return linalg.lerp(v1, v2, amount) return linalg.lerp(v1, v2, Vector2(amount))
} }
// Calculate reflected vector to normal // Calculate reflected vector to normal
@(require_results, deprecated="Prefer = linalg.reflect(v, normal)") @(require_results, deprecated="Prefer = linalg.reflect(v, normal)")
@@ -405,7 +405,7 @@ Vector3Transform :: proc "c" (v: Vector3, m: Matrix) -> Vector3 {
// Calculate linear interpolation between two vectors // Calculate linear interpolation between two vectors
@(require_results, deprecated="Prefer = linalg.lerp(v1, v2, amount)") @(require_results, deprecated="Prefer = linalg.lerp(v1, v2, amount)")
Vector3Lerp :: proc "c" (v1, v2: Vector3, amount: f32) -> Vector3 { Vector3Lerp :: proc "c" (v1, v2: Vector3, amount: f32) -> Vector3 {
return linalg.lerp(v1, v2, amount) return linalg.lerp(v1, v2, Vector3(amount))
} }
// Calculate reflected vector to normal // Calculate reflected vector to normal
@(require_results, deprecated="Prefer = linalg.reflect(v, normal)") @(require_results, deprecated="Prefer = linalg.reflect(v, normal)")