Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Remove the varargs-based mdarray helper. #62855

Merged
merged 8 commits into from
Dec 16, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 0 additions & 1 deletion docs/design/coreclr/botr/readytorun-format.md
Original file line number Diff line number Diff line change
Expand Up @@ -719,7 +719,6 @@ enum ReadyToRunHelper
READYTORUN_HELPER_Unbox = 0x5A,
READYTORUN_HELPER_Unbox_Nullable = 0x5B,
READYTORUN_HELPER_NewMultiDimArr = 0x5C,
READYTORUN_HELPER_NewMultiDimArr_NonVarArg = 0x5D,

// Helpers used with generic handle lookup cases
READYTORUN_HELPER_NewObject = 0x60,
Expand Down
4 changes: 1 addition & 3 deletions src/coreclr/inc/corinfo.h
Original file line number Diff line number Diff line change
Expand Up @@ -362,8 +362,7 @@ enum CorInfoHelpFunc
CORINFO_HELP_NEWSFAST_ALIGN8, // allocator for small, non-finalizer, non-array object, 8 byte aligned
CORINFO_HELP_NEWSFAST_ALIGN8_VC,// allocator for small, value class, 8 byte aligned
CORINFO_HELP_NEWSFAST_ALIGN8_FINALIZE, // allocator for small, finalizable, non-array object, 8 byte aligned
CORINFO_HELP_NEW_MDARR, // multi-dim array helper (with or without lower bounds - dimensions passed in as vararg)
CORINFO_HELP_NEW_MDARR_NONVARARG,// multi-dim array helper (with or without lower bounds - dimensions passed in as unmanaged array)
CORINFO_HELP_NEW_MDARR,// multi-dim array helper (with or without lower bounds - dimensions passed in as unmanaged array)
CORINFO_HELP_NEWARR_1_DIRECT, // helper for any one dimensional array creation
CORINFO_HELP_NEWARR_1_OBJ, // optimized 1-D object arrays
CORINFO_HELP_NEWARR_1_VC, // optimized 1-D value class arrays
Expand Down Expand Up @@ -622,7 +621,6 @@ enum CorInfoHelpSig
CORINFO_HELP_SIG_8_STACK,
CORINFO_HELP_SIG_12_STACK,
CORINFO_HELP_SIG_16_STACK,
CORINFO_HELP_SIG_8_VA, //2 arguments plus varargs

CORINFO_HELP_SIG_EBPCALL, //special calling convention that uses EDX and
//EBP as arguments
Expand Down
10 changes: 5 additions & 5 deletions src/coreclr/inc/jiteeversionguid.h
Original file line number Diff line number Diff line change
Expand Up @@ -43,11 +43,11 @@ typedef const GUID *LPCGUID;
#define GUID_DEFINED
#endif // !GUID_DEFINED

constexpr GUID JITEEVersionIdentifier = { /* 29ff53ef-3c61-4fc4-bdab-82e39a3d7970 */
0x29ff53ef,
0x3c61,
0x4fc4,
{0xbd, 0xab, 0x82, 0xe3, 0x9a, 0x3d, 0x79, 0x70}
constexpr GUID JITEEVersionIdentifier = { /* 1d61ee87-b3be-48ae-a12e-2fb9b5b1cee7 */
0x1d61ee87,
0xb3be,
0x48ae,
{0xa1, 0x2e, 0x2f, 0xb9, 0xb5, 0xb1, 0xce, 0xe7}
};

//////////////////////////////////////////////////////////////////////////////////////////////////////////
Expand Down
3 changes: 1 addition & 2 deletions src/coreclr/inc/jithelpers.h
Original file line number Diff line number Diff line change
Expand Up @@ -75,8 +75,7 @@
DYNAMICJITHELPER(CORINFO_HELP_NEWSFAST_ALIGN8, JIT_New, CORINFO_HELP_SIG_REG_ONLY)
JITHELPER(CORINFO_HELP_NEWSFAST_ALIGN8_VC, NULL, CORINFO_HELP_SIG_REG_ONLY)
JITHELPER(CORINFO_HELP_NEWSFAST_ALIGN8_FINALIZE, NULL, CORINFO_HELP_SIG_REG_ONLY)
JITHELPER(CORINFO_HELP_NEW_MDARR, JIT_NewMDArr,CORINFO_HELP_SIG_8_VA)
JITHELPER(CORINFO_HELP_NEW_MDARR_NONVARARG, JIT_NewMDArrNonVarArg,CORINFO_HELP_SIG_4_STACK)
JITHELPER(CORINFO_HELP_NEW_MDARR, JIT_NewMDArr,CORINFO_HELP_SIG_4_STACK)
JITHELPER(CORINFO_HELP_NEWARR_1_DIRECT, JIT_NewArr1,CORINFO_HELP_SIG_REG_ONLY)
DYNAMICJITHELPER(CORINFO_HELP_NEWARR_1_OBJ, JIT_NewArr1,CORINFO_HELP_SIG_REG_ONLY)
DYNAMICJITHELPER(CORINFO_HELP_NEWARR_1_VC, JIT_NewArr1,CORINFO_HELP_SIG_REG_ONLY)
Expand Down
1 change: 0 additions & 1 deletion src/coreclr/inc/readytorun.h
Original file line number Diff line number Diff line change
Expand Up @@ -297,7 +297,6 @@ enum ReadyToRunHelper
READYTORUN_HELPER_Unbox = 0x5A,
READYTORUN_HELPER_Unbox_Nullable = 0x5B,
READYTORUN_HELPER_NewMultiDimArr = 0x5C,
READYTORUN_HELPER_NewMultiDimArr_NonVarArg = 0x5D,

// Helpers used with generic handle lookup cases
READYTORUN_HELPER_NewObject = 0x60,
Expand Down
1 change: 0 additions & 1 deletion src/coreclr/inc/readytorunhelpers.h
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,6 @@ HELPER(READYTORUN_HELPER_Box_Nullable, CORINFO_HELP_BOX_NULLABLE,
HELPER(READYTORUN_HELPER_Unbox, CORINFO_HELP_UNBOX, )
HELPER(READYTORUN_HELPER_Unbox_Nullable, CORINFO_HELP_UNBOX_NULLABLE, )
HELPER(READYTORUN_HELPER_NewMultiDimArr, CORINFO_HELP_NEW_MDARR, )
HELPER(READYTORUN_HELPER_NewMultiDimArr_NonVarArg, CORINFO_HELP_NEW_MDARR_NONVARARG, )

HELPER(READYTORUN_HELPER_NewObject, CORINFO_HELP_NEWFAST, )
HELPER(READYTORUN_HELPER_NewArray, CORINFO_HELP_NEWARR_1_DIRECT, )
Expand Down
130 changes: 41 additions & 89 deletions src/coreclr/jit/importer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3364,7 +3364,7 @@ GenTree* Compiler::impInitializeArrayIntrinsic(CORINFO_SIG_INFO* sig)
#endif
)
{
if (newArrayCall->AsCall()->gtCallMethHnd != eeFindHelper(CORINFO_HELP_NEW_MDARR_NONVARARG))
if (newArrayCall->AsCall()->gtCallMethHnd != eeFindHelper(CORINFO_HELP_NEW_MDARR))
{
return nullptr;
}
Expand Down Expand Up @@ -7428,107 +7428,59 @@ void Compiler::impImportNewObjArray(CORINFO_RESOLVED_TOKEN* pResolvedToken, CORI

GenTree* node;

//
// There are two different JIT helpers that can be used to allocate
// multi-dimensional arrays:
//
// - CORINFO_HELP_NEW_MDARR - takes the array dimensions as varargs.
// This variant is deprecated. It should be eventually removed.
//
// - CORINFO_HELP_NEW_MDARR_NONVARARG - takes the array dimensions as
// pointer to block of int32s. This variant is more portable.
//
// The non-varargs helper is enabled for CoreRT only for now. Enabling this
// unconditionally would require ReadyToRun version bump.
//
CLANG_FORMAT_COMMENT_ANCHOR;

if (!opts.IsReadyToRun() || IsTargetAbi(CORINFO_CORERT_ABI))
// Reuse the temp used to pass the array dimensions to avoid bloating
// the stack frame in case there are multiple calls to multi-dim array
// constructors within a single method.
if (lvaNewObjArrayArgs == BAD_VAR_NUM)
{
lvaNewObjArrayArgs = lvaGrabTemp(false DEBUGARG("NewObjArrayArgs"));
lvaTable[lvaNewObjArrayArgs].lvType = TYP_BLK;
lvaTable[lvaNewObjArrayArgs].lvExactSize = 0;
}

// Reuse the temp used to pass the array dimensions to avoid bloating
// the stack frame in case there are multiple calls to multi-dim array
// constructors within a single method.
if (lvaNewObjArrayArgs == BAD_VAR_NUM)
{
lvaNewObjArrayArgs = lvaGrabTemp(false DEBUGARG("NewObjArrayArgs"));
lvaTable[lvaNewObjArrayArgs].lvType = TYP_BLK;
lvaTable[lvaNewObjArrayArgs].lvExactSize = 0;
}

// Increase size of lvaNewObjArrayArgs to be the largest size needed to hold 'numArgs' integers
// for our call to CORINFO_HELP_NEW_MDARR_NONVARARG.
lvaTable[lvaNewObjArrayArgs].lvExactSize =
max(lvaTable[lvaNewObjArrayArgs].lvExactSize, pCallInfo->sig.numArgs * sizeof(INT32));

// The side-effects may include allocation of more multi-dimensional arrays. Spill all side-effects
// to ensure that the shared lvaNewObjArrayArgs local variable is only ever used to pass arguments
// to one allocation at a time.
impSpillSideEffects(true, (unsigned)CHECK_SPILL_ALL DEBUGARG("impImportNewObjArray"));

//
// The arguments of the CORINFO_HELP_NEW_MDARR_NONVARARG helper are:
// - Array class handle
// - Number of dimension arguments
// - Pointer to block of int32 dimensions - address of lvaNewObjArrayArgs temp.
//

node = gtNewLclvNode(lvaNewObjArrayArgs, TYP_BLK);
node = gtNewOperNode(GT_ADDR, TYP_I_IMPL, node);

// Pop dimension arguments from the stack one at a time and store it
// into lvaNewObjArrayArgs temp.
for (int i = pCallInfo->sig.numArgs - 1; i >= 0; i--)
{
GenTree* arg = impImplicitIorI4Cast(impPopStack().val, TYP_INT);

GenTree* dest = gtNewLclvNode(lvaNewObjArrayArgs, TYP_BLK);
dest = gtNewOperNode(GT_ADDR, TYP_I_IMPL, dest);
dest = gtNewOperNode(GT_ADD, TYP_I_IMPL, dest,
new (this, GT_CNS_INT) GenTreeIntCon(TYP_I_IMPL, sizeof(INT32) * i));
dest = gtNewOperNode(GT_IND, TYP_INT, dest);

node = gtNewOperNode(GT_COMMA, node->TypeGet(), gtNewAssignNode(dest, arg), node);
}
// Increase size of lvaNewObjArrayArgs to be the largest size needed to hold 'numArgs' integers
// for our call to CORINFO_HELP_NEW_MDARR.
lvaTable[lvaNewObjArrayArgs].lvExactSize =
max(lvaTable[lvaNewObjArrayArgs].lvExactSize, pCallInfo->sig.numArgs * sizeof(INT32));

GenTreeCall::Use* args = gtNewCallArgs(node);
// The side-effects may include allocation of more multi-dimensional arrays. Spill all side-effects
// to ensure that the shared lvaNewObjArrayArgs local variable is only ever used to pass arguments
// to one allocation at a time.
impSpillSideEffects(true, (unsigned)CHECK_SPILL_ALL DEBUGARG("impImportNewObjArray"));

// pass number of arguments to the helper
args = gtPrependNewCallArg(gtNewIconNode(pCallInfo->sig.numArgs), args);
//
// The arguments of the CORINFO_HELP_NEW_MDARR helper are:
// - Array class handle
// - Number of dimension arguments
// - Pointer to block of int32 dimensions - address of lvaNewObjArrayArgs temp.
//

args = gtPrependNewCallArg(classHandle, args);
node = gtNewLclvNode(lvaNewObjArrayArgs, TYP_BLK);
node = gtNewOperNode(GT_ADDR, TYP_I_IMPL, node);

node = gtNewHelperCallNode(CORINFO_HELP_NEW_MDARR_NONVARARG, TYP_REF, args);
}
else
// Pop dimension arguments from the stack one at a time and store it
// into lvaNewObjArrayArgs temp.
for (int i = pCallInfo->sig.numArgs - 1; i >= 0; i--)
{
//
// The varargs helper needs the type and method handles as last
// and last-1 param (this is a cdecl call, so args will be
// pushed in reverse order on the CPU stack)
//
GenTree* arg = impImplicitIorI4Cast(impPopStack().val, TYP_INT);

GenTreeCall::Use* args = gtNewCallArgs(classHandle);
GenTree* dest = gtNewLclvNode(lvaNewObjArrayArgs, TYP_BLK);
dest = gtNewOperNode(GT_ADDR, TYP_I_IMPL, dest);
dest = gtNewOperNode(GT_ADD, TYP_I_IMPL, dest,
new (this, GT_CNS_INT) GenTreeIntCon(TYP_I_IMPL, sizeof(INT32) * i));
dest = gtNewOperNode(GT_IND, TYP_INT, dest);

// pass number of arguments to the helper
args = gtPrependNewCallArg(gtNewIconNode(pCallInfo->sig.numArgs), args);
node = gtNewOperNode(GT_COMMA, node->TypeGet(), gtNewAssignNode(dest, arg), node);
}

args = impPopCallArgs(pCallInfo->sig.numArgs, &pCallInfo->sig, args);
GenTreeCall::Use* args = gtNewCallArgs(node);

node = gtNewHelperCallNode(CORINFO_HELP_NEW_MDARR, TYP_REF, args);
// pass number of arguments to the helper
args = gtPrependNewCallArg(gtNewIconNode(pCallInfo->sig.numArgs), args);

// varargs, so we pop the arguments
node->gtFlags |= GTF_CALL_POP_ARGS;
args = gtPrependNewCallArg(classHandle, args);

#ifdef DEBUG
// At the present time we don't track Caller pop arguments
// that have GC references in them
for (GenTreeCall::Use& use : GenTreeCall::UseList(args))
{
assert(use.GetNode()->TypeGet() != TYP_REF);
}
#endif
}
node = gtNewHelperCallNode(CORINFO_HELP_NEW_MDARR, TYP_REF, args);

for (GenTreeCall::Use& use : node->AsCall()->Args())
{
Expand Down
25 changes: 11 additions & 14 deletions src/coreclr/jit/valuenum.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -9816,6 +9816,12 @@ void Compiler::fgValueNumberHelperCallFunc(GenTreeCall* call, VNFunc vnf, ValueN
}
break;

case VNF_JitNewMdArr:
{
generateUniqueVN = true;
}
break;

case VNF_Box:
case VNF_BoxNullable:
{
Expand Down Expand Up @@ -10221,6 +10227,10 @@ VNFunc Compiler::fgValueNumberJitHelperMethodVNFunc(CorInfoHelpFunc helpFunc)
vnf = VNF_JitNewArr;
break;

case CORINFO_HELP_NEW_MDARR:
vnf = VNF_JitNewMdArr;
break;

case CORINFO_HELP_READYTORUN_NEWARR_1:
vnf = VNF_JitReadyToRunNewArr;
break;
Expand Down Expand Up @@ -10447,20 +10457,7 @@ bool Compiler::fgValueNumberHelperCall(GenTreeCall* call)
}
else
{
// TODO-CQ: this is a list of helpers we're going to treat as non-pure,
// because they raise complications. Eventually, we need to handle those complications...
bool needsFurtherWork = false;
switch (helpFunc)
{
case CORINFO_HELP_NEW_MDARR:
// This is a varargs helper. We need to represent the array shape in the VN world somehow.
needsFurtherWork = true;
break;
default:
break;
}

if (!needsFurtherWork && (pure || isAlloc))
if (pure || isAlloc)
{
VNFunc vnf = fgValueNumberJitHelperMethodVNFunc(helpFunc);

Expand Down
1 change: 1 addition & 0 deletions src/coreclr/jit/valuenumfuncs.h
Original file line number Diff line number Diff line change
Expand Up @@ -132,6 +132,7 @@ ValueNumFuncDef(GetStaticAddrTLS, 1, false, true, false)

ValueNumFuncDef(JitNew, 2, false, true, false)
ValueNumFuncDef(JitNewArr, 3, false, true, false)
ValueNumFuncDef(JitNewMdArr, 4, false, true, false)
ValueNumFuncDef(JitReadyToRunNew, 2, false, true, false)
ValueNumFuncDef(JitReadyToRunNewArr, 3, false, true, false)
ValueNumFuncDef(Box, 3, false, false, false)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -214,7 +214,6 @@ public enum ReadyToRunHelper
Unbox = 0x5A,
Unbox_Nullable = 0x5B,
NewMultiDimArr = 0x5C,
NewMultiDimArr_NonVarArg = 0x5D,

// Helpers used with generic handle lookup cases
NewObject = 0x60,
Expand Down
3 changes: 1 addition & 2 deletions src/coreclr/tools/Common/JitInterface/CorInfoHelpFunc.cs
Original file line number Diff line number Diff line change
Expand Up @@ -56,8 +56,7 @@ which is the right helper to use to allocate an object of a given type. */
CORINFO_HELP_NEWSFAST_ALIGN8, // allocator for small, non-finalizer, non-array object, 8 byte aligned
CORINFO_HELP_NEWSFAST_ALIGN8_VC,// allocator for small, value class, 8 byte aligned
CORINFO_HELP_NEWSFAST_ALIGN8_FINALIZE, // allocator for small, finalizable, non-array object, 8 byte aligned
CORINFO_HELP_NEW_MDARR, // multi-dim array helper (with or without lower bounds - dimensions passed in as vararg)
CORINFO_HELP_NEW_MDARR_NONVARARG,// multi-dim array helper (with or without lower bounds - dimensions passed in as unmanaged array)
CORINFO_HELP_NEW_MDARR,// multi-dim array helper (with or without lower bounds - dimensions passed in as unmanaged array)
CORINFO_HELP_NEWARR_1_DIRECT, // helper for any one dimensional array creation
CORINFO_HELP_NEWARR_1_OBJ, // optimized 1-D object arrays
CORINFO_HELP_NEWARR_1_VC, // optimized 1-D value class arrays
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,7 @@ public static void GetEntryPoint(TypeSystemContext context, ReadyToRunHelper id,
mangledName = "RhUnboxNullable";
break;

case ReadyToRunHelper.NewMultiDimArr_NonVarArg:
case ReadyToRunHelper.NewMultiDimArr:
methodDesc = context.GetHelperEntryPoint("ArrayHelpers", "NewObjArray");
break;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -310,7 +310,7 @@ private void ImportCall(ILOpcode opcode, int token)
{
// RyuJIT is going to call the "MdArray" creation helper even if this is an SzArray,
// hence the IsArray check above. Note that the MdArray helper can handle SzArrays.
_dependencies.Add(GetHelperEntrypoint(ReadyToRunHelper.NewMultiDimArr_NonVarArg), reason);
_dependencies.Add(GetHelperEntrypoint(ReadyToRunHelper.NewMultiDimArr), reason);
return;
}
else
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -704,9 +704,6 @@ private ISymbolNode GetHelperFtnUncached(CorInfoHelpFunc ftnNum)
case CorInfoHelpFunc.CORINFO_HELP_NEW_MDARR:
id = ReadyToRunHelper.NewMultiDimArr;
break;
case CorInfoHelpFunc.CORINFO_HELP_NEW_MDARR_NONVARARG:
id = ReadyToRunHelper.NewMultiDimArr_NonVarArg;
break;
case CorInfoHelpFunc.CORINFO_HELP_NEWFAST:
id = ReadyToRunHelper.NewObject;
break;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1726,10 +1726,6 @@ private void ParseHelper(StringBuilder builder)
builder.Append("NEW_MULTI_DIM_ARR");
break;

case ReadyToRunHelper.NewMultiDimArr_NonVarArg:
builder.Append("NEW_MULTI_DIM_ARR__NON_VAR_ARG");
break;

case ReadyToRunHelper.MonitorEnter:
builder.Append("MONITOR_ENTER");
break;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -501,8 +501,8 @@ private ISymbolNode GetHelperFtnUncached(CorInfoHelpFunc ftnNum)
case CorInfoHelpFunc.CORINFO_HELP_UNBOX_NULLABLE:
id = ReadyToRunHelper.Unbox_Nullable;
break;
case CorInfoHelpFunc.CORINFO_HELP_NEW_MDARR_NONVARARG:
id = ReadyToRunHelper.NewMultiDimArr_NonVarArg;
case CorInfoHelpFunc.CORINFO_HELP_NEW_MDARR:
id = ReadyToRunHelper.NewMultiDimArr;
break;
case CorInfoHelpFunc.CORINFO_HELP_NEWFAST:
id = ReadyToRunHelper.NewObject;
Expand Down
3 changes: 0 additions & 3 deletions src/coreclr/vm/fcall.h
Original file line number Diff line number Diff line change
Expand Up @@ -1143,7 +1143,6 @@ struct FCSigCheck {
#define HCIMPL2_RAW(rettype, funcname, a1, a2) rettype F_CALL_CONV funcname(int /* EAX */, a2, a1) {
#define HCIMPL2_VV(rettype, funcname, a1, a2) rettype F_CALL_CONV funcname(int /* EAX */, int /* EDX */, int /* ECX */, a2, a1) { HCIMPL_PROLOG(funcname)
#define HCIMPL2_IV(rettype, funcname, a1, a2) rettype F_CALL_CONV funcname(int /* EAX */, int /* EDX */, a1, a2) { HCIMPL_PROLOG(funcname)
#define HCIMPL2VA(rettype, funcname, a1, a2) rettype F_CALL_VA_CONV funcname(a1, a2, ...) { HCIMPL_PROLOG(funcname)
#define HCIMPL3(rettype, funcname, a1, a2, a3) rettype F_CALL_CONV funcname(int /* EAX */, a2, a1, a3) { HCIMPL_PROLOG(funcname)
#define HCIMPL3_RAW(rettype, funcname, a1, a2, a3) rettype F_CALL_CONV funcname(int /* EAX */, a2, a1, a3) {
#define HCIMPL4(rettype, funcname, a1, a2, a3, a4) rettype F_CALL_CONV funcname(int /* EAX */, a2, a1, a4, a3) { HCIMPL_PROLOG(funcname)
Expand All @@ -1168,7 +1167,6 @@ struct FCSigCheck {
#define HCIMPL2_RAW(rettype, funcname, a1, a2) rettype F_CALL_CONV funcname(a1, a2) {
#define HCIMPL2_VV(rettype, funcname, a1, a2) rettype F_CALL_CONV funcname(a2, a1) { HCIMPL_PROLOG(funcname)
#define HCIMPL2_IV(rettype, funcname, a1, a2) rettype F_CALL_CONV funcname(a1, a2) { HCIMPL_PROLOG(funcname)
#define HCIMPL2VA(rettype, funcname, a1, a2) rettype F_CALL_VA_CONV funcname(a1, a2, ...) { HCIMPL_PROLOG(funcname)
#define HCIMPL3(rettype, funcname, a1, a2, a3) rettype F_CALL_CONV funcname(a1, a2, a3) { HCIMPL_PROLOG(funcname)
#define HCIMPL3_RAW(rettype, funcname, a1, a2, a3) rettype F_CALL_CONV funcname(a1, a2, a3) {
#define HCIMPL4(rettype, funcname, a1, a2, a3, a4) rettype F_CALL_CONV funcname(a1, a2, a4, a3) { HCIMPL_PROLOG(funcname)
Expand All @@ -1194,7 +1192,6 @@ struct FCSigCheck {
#define HCIMPL2_RAW(rettype, funcname, a1, a2) rettype F_CALL_CONV funcname(a1, a2) {
#define HCIMPL2_VV(rettype, funcname, a1, a2) rettype F_CALL_CONV funcname(a1, a2) { HCIMPL_PROLOG(funcname)
#define HCIMPL2_IV(rettype, funcname, a1, a2) rettype F_CALL_CONV funcname(a1, a2) { HCIMPL_PROLOG(funcname)
#define HCIMPL2VA(rettype, funcname, a1, a2) rettype F_CALL_VA_CONV funcname(a1, a2, ...) { HCIMPL_PROLOG(funcname)
#define HCIMPL3(rettype, funcname, a1, a2, a3) rettype F_CALL_CONV funcname(a1, a2, a3) { HCIMPL_PROLOG(funcname)
#define HCIMPL3_RAW(rettype, funcname, a1, a2, a3) rettype F_CALL_CONV funcname(a1, a2, a3) {
#define HCIMPL4(rettype, funcname, a1, a2, a3, a4) rettype F_CALL_CONV funcname(a1, a2, a3, a4) { HCIMPL_PROLOG(funcname)
Expand Down
Loading