aboutsummaryrefslogtreecommitdiff
path: root/src/check_expr.cpp
diff options
context:
space:
mode:
authorgingerBill <bill@gingerbill.org>2024-07-14 11:39:05 +0100
committergingerBill <bill@gingerbill.org>2024-07-14 11:39:05 +0100
commitedc793d7c123a38826860ef72684308902a7012c (patch)
tree0d6c6c97af7355313e76b3d433d555dfff43ab8d /src/check_expr.cpp
parentf98a7b84dfd03bffacc0951209e36e102a6448ca (diff)
Add `#no_capture args: ..T` to reuse the backing array stack memory
Diffstat (limited to 'src/check_expr.cpp')
-rw-r--r--src/check_expr.cpp17
1 files changed, 17 insertions, 0 deletions
diff --git a/src/check_expr.cpp b/src/check_expr.cpp
index 12acca0cb..645d8ac5a 100644
--- a/src/check_expr.cpp
+++ b/src/check_expr.cpp
@@ -6033,6 +6033,23 @@ gb_internal CallArgumentError check_call_arguments_internal(CheckerContext *c, A
Entity *vt = pt->params->Tuple.variables[pt->variadic_index];
o.type = vt->type;
+
+ // NOTE(bill, 2024-07-14): minimize the stack usage for variadic parameter that use `#no_capture`
+ // on the variadic parameter
+ if (c->decl && (vt->flags & EntityFlag_NoCapture)) {
+ bool found = false;
+ for (NoCaptureData &nc : c->decl->no_captures) {
+ if (are_types_identical(vt->type, nc.slice_type)) {
+ nc.max_count = gb_max(nc.max_count, variadic_operands.count);
+ found = true;
+ break;
+ }
+ }
+ if (!found) {
+ array_add(&c->decl->no_captures, NoCaptureData{vt->type, variadic_operands.count});
+ }
+ }
+
} else {
dummy_argument_count += 1;
o.type = t_untyped_nil;