Skip to content

Commit 52ebab8

Browse files
committed
[interp] Fix varargs passing
We must not push one vararg at a time since the alignment of the argument is not the same as the alignment of a value type in interp (which is always 8)
1 parent 3369b6e commit 52ebab8

1 file changed

Lines changed: 5 additions & 4 deletions

File tree

mono/mini/interp/transform.c

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1185,19 +1185,20 @@ interp_transform_call (TransformData *td, MonoMethod *method, MonoMethod *target
11851185

11861186
if (csignature->call_convention == MONO_CALL_VARARG) {
11871187
csignature = mono_method_get_signature_checked (target_method, image, token, generic_context, error);
1188+
int vararg_stack = 0;
11881189
/*
11891190
* For vararg calls, ArgIterator expects the signature and the varargs to be
11901191
* stored in a linear memory. We allocate the necessary vt_stack space for
11911192
* this. All varargs will be pushed to the vt_stack at call site.
11921193
*/
1193-
vt_stack_used += sizeof (gpointer);
1194-
PUSH_VT (td, sizeof (gpointer));
1194+
vararg_stack += sizeof (gpointer);
11951195
for (i = csignature->sentinelpos; i < csignature->param_count; ++i) {
11961196
int align, arg_size;
11971197
arg_size = mono_type_stack_size (csignature->params [i], &align);
1198-
vt_stack_used += arg_size;
1199-
PUSH_VT (td, arg_size);
1198+
vararg_stack += arg_size;
12001199
}
1200+
vt_stack_used += ALIGN_TO (vararg_stack, MINT_VT_ALIGNMENT);
1201+
PUSH_VT (td, vararg_stack);
12011202
}
12021203

12031204
g_assert (csignature->call_convention != MONO_CALL_THISCALL && csignature->call_convention != MONO_CALL_FASTCALL);

0 commit comments

Comments
 (0)