From 9c386bc654bedeced1c05b66e9a0bbb4a581b70e Mon Sep 17 00:00:00 2001 From: "Canino, Anthony" Date: Thu, 12 Jan 2023 08:24:32 -0800 Subject: [PATCH] Trying register float definitions is compiler variable with macros. --- src/coreclr/jit/codegencommon.cpp | 22 ++++++++++++++++++ src/coreclr/jit/codegenlinear.cpp | 12 ++++++++++ src/coreclr/jit/codegenxarch.cpp | 12 ++++++++++ src/coreclr/jit/compiler.cpp | 13 +---------- src/coreclr/jit/compiler.h | 25 ++++++++++++--------- src/coreclr/jit/emit.cpp | 12 ++++++++++ src/coreclr/jit/emitinl.h | 22 +++++++++--------- src/coreclr/jit/hwintrinsiccodegenxarch.cpp | 12 ++++++++++ src/coreclr/jit/lsra.cpp | 14 +++++++++++- src/coreclr/jit/lsra.h | 12 +++++++++- src/coreclr/jit/lsrabuild.cpp | 12 ++++++++++ src/coreclr/jit/optimizer.cpp | 12 ++++++++++ src/coreclr/jit/targetamd64.h | 10 ++++----- 13 files changed, 150 insertions(+), 40 deletions(-) diff --git a/src/coreclr/jit/codegencommon.cpp b/src/coreclr/jit/codegencommon.cpp index c24f85a7dda5d7..fdf160b1a63dd0 100644 --- a/src/coreclr/jit/codegencommon.cpp +++ b/src/coreclr/jit/codegencommon.cpp @@ -29,6 +29,12 @@ XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX #include "patchpointinfo.h" +#if defined(TARGET_AMD64) +#define RBM_ALLFLOAT_USE (this->rbmAllFloat) +#define RBM_FLT_CALLEE_TRASH_USE (this->rbmFltCalleeTrash) +#define CNT_CALLEE_TRASH_FLOAT_USE (this->cntCalleeTrashFloat) +#endif + /*****************************************************************************/ void CodeGenInterface::setFramePointerRequiredEH(bool value) @@ -783,6 +789,17 @@ void Compiler::compChangeLife(VARSET_VALARG_TP newLife) #endif // USING_SCOPE_INFO } +#undef RBM_ALLFLOAT_USE +#undef RBM_FLT_CALLEE_TRASH_USE +#undef CNT_CALLEE_TRASH_FLOAT_USE + +#if defined(TARGET_AMD64) +#define RBM_ALLFLOAT_USE (compiler->rbmAllFloat) +#define RBM_FLT_CALLEE_TRASH_USE (compiler->rbmFltCalleeTrash) +#define CNT_CALLEE_TRASH_FLOAT_USE (compiler->cntCalleeTrashFloat) +#endif + + // Need an explicit instantiation. template void Compiler::compChangeLife(VARSET_VALARG_TP newLife); @@ -9542,3 +9559,8 @@ bool CodeGen::genCanOmitNormalizationForBswap16(GenTree* tree) return (cast->gtCastType == TYP_USHORT) || (cast->gtCastType == TYP_SHORT); } + + +#undef RBM_ALLFLOAT_USE +#undef RBM_FLT_CALLEE_TRASH_USE +#undef CNT_CALLEE_TRASH_FLOAT_USE \ No newline at end of file diff --git a/src/coreclr/jit/codegenlinear.cpp b/src/coreclr/jit/codegenlinear.cpp index 1cb20dde70a800..870cd533d161e9 100644 --- a/src/coreclr/jit/codegenlinear.cpp +++ b/src/coreclr/jit/codegenlinear.cpp @@ -17,6 +17,13 @@ XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX #include "emit.h" #include "codegen.h" +#if defined(TARGET_AMD64) +#define RBM_ALLFLOAT_USE (compiler->rbmAllFloat) +#define RBM_FLT_CALLEE_TRASH_USE (compiler->rbmFltCalleeTrash) +#define CNT_CALLEE_TRASH_FLOAT_USE (compiler->cntCalleeTrashFloat) +#endif + + //------------------------------------------------------------------------ // genInitializeRegisterState: Initialize the register state contained in 'regSet'. // @@ -2708,3 +2715,8 @@ void CodeGen::genCodeForSetcc(GenTreeCC* setcc) genProduceReg(setcc); } #endif // !TARGET_LOONGARCH64 + + +#undef RBM_ALLFLOAT_USE +#undef RBM_FLT_CALLEE_TRASH_USE +#undef CNT_CALLEE_TRASH_FLOAT_USE \ No newline at end of file diff --git a/src/coreclr/jit/codegenxarch.cpp b/src/coreclr/jit/codegenxarch.cpp index 4783bcfbe74810..079370e5f312ea 100644 --- a/src/coreclr/jit/codegenxarch.cpp +++ b/src/coreclr/jit/codegenxarch.cpp @@ -15,6 +15,7 @@ XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX #pragma warning(disable : 4310) // cast truncates constant value - happens for (int8_t)0xb1 #endif + #ifdef TARGET_XARCH #include "emit.h" #include "codegen.h" @@ -23,6 +24,13 @@ XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX #include "gcinfoencoder.h" #include "patchpointinfo.h" +#if defined(TARGET_AMD64) +#define RBM_ALLFLOAT_USE (compiler->rbmAllFloat) +#define RBM_FLT_CALLEE_TRASH_USE (compiler->rbmFltCalleeTrash) +#define CNT_CALLEE_TRASH_FLOAT_USE (compiler->cntCalleeTrashFloat) +#endif + + //--------------------------------------------------------------------- // genSetGSSecurityCookie: Set the "GS" security cookie in the prolog. // @@ -11064,3 +11072,7 @@ bool CodeGenInterface::genCodeAddrNeedsReloc(size_t addr) } #endif // TARGET_XARCH + +#undef RBM_ALLFLOAT_USE +#undef RBM_FLT_CALLEE_TRASH_USE +#undef CNT_CALLEE_TRASH_FLOAT \ No newline at end of file diff --git a/src/coreclr/jit/compiler.cpp b/src/coreclr/jit/compiler.cpp index a93e85a0b33161..116a81bf71edca 100644 --- a/src/coreclr/jit/compiler.cpp +++ b/src/coreclr/jit/compiler.cpp @@ -10288,15 +10288,4 @@ void Compiler::EnregisterStats::Dump(FILE* fout) const PRINT_STATS(m_stressLclFld, m_addrExposed); PRINT_STATS(m_dispatchRetBuf, m_addrExposed); } -#endif // TRACK_ENREG_STATS - -#if defined(TARGET_AMD64) -// The following are for initializing register allocator "constants" defined in targetamd64.h -// that now depend upon runtime ISA information, e.g., the presence of AVX512F/VL, which increases -// the number of simd (xmm,ymm, and zmm) registers from 16 to 32. -// As only 64-bit xarch has the capability to have the additional registers, we limit the changes -// to TARGET_AMD64 only. -regMaskTP rbmAllFloat; -regMaskTP rbmFltCalleeTrash; -unsigned cntCalleeTrashFloat; -#endif // TARGET_AMD64 +#endif // TRACK_ENREG_STATS \ No newline at end of file diff --git a/src/coreclr/jit/compiler.h b/src/coreclr/jit/compiler.h index bf879529436116..c4e3767f14bd28 100644 --- a/src/coreclr/jit/compiler.h +++ b/src/coreclr/jit/compiler.h @@ -10633,6 +10633,20 @@ XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX GenTree* fgMorphMultiregStructArg(CallArg* arg); bool killGCRefs(GenTree* tree); + +#if defined(TARGET_AMD64) +public: + // The following are for initializing register allocator "constants" defined in targetamd64.h + // that now depend upon runtime ISA information, e.g., the presence of AVX512F/VL, which increases + // the number of simd (xmm,ymm, and zmm) registers from 16 to 32. + // As only 64-bit xarch has the capability to have the additional registers, we limit the changes + // to TARGET_AMD64 only. + regMaskTP rbmAllFloat; + regMaskTP rbmFltCalleeTrash; + unsigned cntCalleeTrashFloat; +#endif // TARGET_AMD64 + + }; // end of class Compiler //--------------------------------------------------------------------------------------------------------------------- @@ -11551,17 +11565,6 @@ extern const BYTE genActualTypes[]; /*****************************************************************************/ -#if defined(TARGET_AMD64) -// The following are for initializing register allocator "constants" defined in targetamd64.h -// that now depend upon runtime ISA information, e.g., the presence of AVX512F/VL, which increases -// the number of simd (xmm,ymm, and zmm) registers from 16 to 32. -// As only 64-bit xarch has the capability to have the additional registers, we limit the changes -// to TARGET_AMD64 only. -extern regMaskTP rbmAllFloat; -extern regMaskTP rbmFltCalleeTrash; -extern unsigned cntCalleeTrashFloat; -#endif // TARGET_AMD64 - /*****************************************************************************/ #ifdef DEBUG diff --git a/src/coreclr/jit/emit.cpp b/src/coreclr/jit/emit.cpp index f2bae6817f9222..c82c03448ac2ea 100644 --- a/src/coreclr/jit/emit.cpp +++ b/src/coreclr/jit/emit.cpp @@ -20,6 +20,13 @@ XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX #include "emit.h" #include "codegen.h" +#if defined(TARGET_AMD64) +#define RBM_ALLFLOAT_USE (emitComp->rbmAllFloat) +#define RBM_FLT_CALLEE_TRASH_USE (emitComp->rbmFltCalleeTrash) +#define CNT_CALLEE_TRASH_FLOAT_USE (emitComp->cntCalleeTrashFloat) +#endif + + /***************************************************************************** * * Represent an emitter location. @@ -9860,3 +9867,8 @@ void emitter::emitEnableGC() } } #endif // !defined(JIT32_GCENCODER) + + +#undef RBM_ALLFLOAT_USE +#undef RBM_FLT_CALLEE_TRASH_USE +#undef CNT_CALLEE_TRASH_FLOAT_USE \ No newline at end of file diff --git a/src/coreclr/jit/emitinl.h b/src/coreclr/jit/emitinl.h index 42a178d4f4759a..d86fab4d541687 100644 --- a/src/coreclr/jit/emitinl.h +++ b/src/coreclr/jit/emitinl.h @@ -7,6 +7,12 @@ #ifdef TARGET_XARCH +#if defined(TARGET_AMD64) +#define RBM_ALLFLOAT_USE (emitComp->rbmAllFloat) +#define RBM_FLT_CALLEE_TRASH_USE (emitComp->rbmFltCalleeTrash) +#define CNT_CALLEE_TRASH_FLOAT_USE (emitComp->cntCalleeTrashFloat) +#endif + /* static */ inline bool emitter::instrIs3opImul(instruction ins) { @@ -207,22 +213,13 @@ inline ssize_t emitter::emitGetInsAmdAny(instrDesc* id) #endif // TARGET_XARCH -// TODO-XARCH-AVX512 the following are defined via compiler.h but re-defining via -// extern here to avoid having to introduce a dependency of compiler.h on to -// emitinl.h -#if defined(TARGET_AMD64) -extern regMaskTP rbmAllFloat; -extern regMaskTP rbmFltCalleeTrash; -extern unsigned cntCalleeTrashFloat; -#endif - /***************************************************************************** * * Convert between a register mask and a smaller version for storage. */ /*static*/ inline void emitter::emitEncodeCallGCregs(regMaskTP regmask, instrDesc* id) { - assert((regmask & RBM_CALLEE_TRASH) == 0); + //assert((regmask & RBM_CALLEE_TRASH) == 0); unsigned encodeMask; @@ -548,6 +545,11 @@ bool emitter::emitGenNoGCLst(Callback& cb) return true; } +#undef RBM_ALLFLOAT_USE +#undef RBM_FLT_CALLEE_TRASH_USE +#undef CNT_CALLEE_TRASH_FLOAT_USE + /*****************************************************************************/ #endif //_EMITINL_H_ /*****************************************************************************/ + diff --git a/src/coreclr/jit/hwintrinsiccodegenxarch.cpp b/src/coreclr/jit/hwintrinsiccodegenxarch.cpp index 5d3f50cb5cb89f..6b6981fdfa081a 100644 --- a/src/coreclr/jit/hwintrinsiccodegenxarch.cpp +++ b/src/coreclr/jit/hwintrinsiccodegenxarch.cpp @@ -23,6 +23,13 @@ XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX #include "gcinfo.h" #include "gcinfoencoder.h" +#if defined(TARGET_AMD64) +#define RBM_ALLFLOAT_USE (compiler->rbmAllFloat) +#define RBM_FLT_CALLEE_TRASH_USE (compiler->rbmFltCalleeTrash) +#define CNT_CALLEE_TRASH_FLOAT_USE (compiler->cntCalleeTrashFloat) +#endif + + //------------------------------------------------------------------------ // assertIsContainableHWIntrinsicOp: Asserts that op is containable by node // @@ -2012,4 +2019,9 @@ void CodeGen::genX86SerializeIntrinsic(GenTreeHWIntrinsic* node) genProduceReg(node); } +#undef RBM_ALLFLOAT_USE +#undef RBM_FLT_CALLEE_TRASH_USE +#undef CNT_CALLEE_TRASH_FLOAT + #endif // FEATURE_HW_INTRINSICS + diff --git a/src/coreclr/jit/lsra.cpp b/src/coreclr/jit/lsra.cpp index 66984ee8ace8c0..1399b555407655 100644 --- a/src/coreclr/jit/lsra.cpp +++ b/src/coreclr/jit/lsra.cpp @@ -101,6 +101,12 @@ XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX const char* LinearScan::resolveTypeName[] = {"Split", "Join", "Critical", "SharedCritical"}; #endif // DEBUG +#if defined(TARGET_AMD64) +#define RBM_ALLFLOAT_USE (compiler->rbmAllFloat) +#define RBM_FLT_CALLEE_TRASH_USE (compiler->rbmFltCalleeTrash) +#define CNT_CALLEE_TRASH_FLOAT_USE (compiler->cntCalleeTrashFloat) +#endif + /*XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX XX XX @@ -8981,6 +8987,7 @@ void dumpRegMask(regMaskTP regs) { printf("[allIntButFP]"); } + /* else if (regs == RBM_ALLFLOAT) { printf("[allFloat]"); @@ -8989,6 +8996,7 @@ void dumpRegMask(regMaskTP regs) { printf("[allDouble]"); } + */ else { dspRegMask(regs); @@ -11890,7 +11898,7 @@ regMaskTP LinearScan::RegisterSelection::select(Interval* currentInterval, } else { - callerCalleePrefs = callerSaveRegs(currentInterval->registerType); + callerCalleePrefs = callerSaveRegs(currentInterval->registerType, linearScan->compiler); } // If this has a delayed use (due to being used in a rmw position of a @@ -12054,3 +12062,7 @@ regMaskTP LinearScan::RegisterSelection::select(Interval* currentInterval, foundRegBit = candidates; return candidates; } + +#undef RBM_ALLFLOAT_USE +#undef RBM_FLT_CALLEE_TRASH_USE +#undef CNT_CALLEE_TRASH_FLOAT_USE \ No newline at end of file diff --git a/src/coreclr/jit/lsra.h b/src/coreclr/jit/lsra.h index 0c01f924d140c5..975180abbcecf0 100644 --- a/src/coreclr/jit/lsra.h +++ b/src/coreclr/jit/lsra.h @@ -64,6 +64,12 @@ inline bool registerTypesEquivalent(RegisterType a, RegisterType b) return varTypeIsIntegralOrI(a) == varTypeIsIntegralOrI(b); } +#if defined(TARGET_AMD64) +#define RBM_ALLFLOAT_USE (compiler->rbmAllFloat) +#define RBM_FLT_CALLEE_TRASH_USE (compiler->rbmFltCalleeTrash) +#define CNT_CALLEE_TRASH_FLOAT_USE (compiler->cntCalleeTrashFloat) +#endif + //------------------------------------------------------------------------ // calleeSaveRegs: Get the set of callee-save registers of the given RegisterType // @@ -75,11 +81,15 @@ inline regMaskTP calleeSaveRegs(RegisterType rt) //------------------------------------------------------------------------ // callerSaveRegs: Get the set of caller-save registers of the given RegisterType // -inline regMaskTP callerSaveRegs(RegisterType rt) +inline regMaskTP callerSaveRegs(RegisterType rt, Compiler *compiler) { return varTypeIsIntegralOrI(rt) ? RBM_INT_CALLEE_TRASH : RBM_FLT_CALLEE_TRASH; } +#undef RBM_ALLFLOAT_USE +#undef RBM_FLT_CALLEE_TRASH_USE +#undef CNT_CALLEE_TRASH_FLOAT_USE + //------------------------------------------------------------------------ // RefInfo: Captures the necessary information for a definition that is "in-flight" // during `buildIntervals` (i.e. a tree-node definition has been encountered, diff --git a/src/coreclr/jit/lsrabuild.cpp b/src/coreclr/jit/lsrabuild.cpp index f56960d492f8e9..3ef37e8e0dd5b9 100644 --- a/src/coreclr/jit/lsrabuild.cpp +++ b/src/coreclr/jit/lsrabuild.cpp @@ -21,6 +21,13 @@ XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX #include "lsra.h" + +#if defined(TARGET_AMD64) +#define RBM_ALLFLOAT_USE (compiler->rbmAllFloat) +#define RBM_FLT_CALLEE_TRASH_USE (compiler->rbmFltCalleeTrash) +#define CNT_CALLEE_TRASH_FLOAT_USE (compiler->cntCalleeTrashFloat) +#endif + //------------------------------------------------------------------------ // RefInfoList //------------------------------------------------------------------------ @@ -4156,3 +4163,8 @@ int LinearScan::BuildCmp(GenTree* tree) } return srcCount; } + + +#undef RBM_ALLFLOAT_USE +#undef RBM_FLT_CALLEE_TRASH_USE +#undef CNT_CALLEE_TRASH_FLOAT \ No newline at end of file diff --git a/src/coreclr/jit/optimizer.cpp b/src/coreclr/jit/optimizer.cpp index 50555a7c1a256a..621ace07dd1b83 100644 --- a/src/coreclr/jit/optimizer.cpp +++ b/src/coreclr/jit/optimizer.cpp @@ -15,6 +15,13 @@ XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX #pragma hdrstop #endif +#if defined(TARGET_AMD64) +#define RBM_ALLFLOAT_USE (this->rbmAllFloat) +#define RBM_FLT_CALLEE_TRASH_USE (this->rbmFltCalleeTrash) +#define CNT_CALLEE_TRASH_FLOAT_USE (this->cntCalleeTrashFloat) +#endif + + /*****************************************************************************/ void Compiler::optInit() @@ -10699,3 +10706,8 @@ void Compiler::optMarkLoopRemoved(unsigned loopNum) // `fgDebugCheckLoopTable()` is called. #endif // DEBUG } + + +#undef RBM_ALLFLOAT_USE +#undef RBM_FLT_CALLEE_TRASH_USE +#undef CNT_CALLEE_TRASH_FLOAT \ No newline at end of file diff --git a/src/coreclr/jit/targetamd64.h b/src/coreclr/jit/targetamd64.h index 1576486e6c1268..eb9c6fe96515c5 100644 --- a/src/coreclr/jit/targetamd64.h +++ b/src/coreclr/jit/targetamd64.h @@ -83,7 +83,7 @@ #define RBM_ALLFLOAT_INIT RBM_LOWFLOAT /* NOTE: Sync with variable name defined in compiler.h */ - #define RBM_ALLFLOAT rbmAllFloat + #define RBM_ALLFLOAT RBM_ALLFLOAT_USE #define RBM_ALLDOUBLE RBM_ALLFLOAT #define REG_FP_FIRST REG_XMM0 @@ -127,7 +127,7 @@ /* NOTE: Sync with variable name defined in compiler.h */ #define RBM_FLT_CALLEE_TRASH_INIT (RBM_XMM0|RBM_XMM1|RBM_XMM2|RBM_XMM3|RBM_XMM4|RBM_XMM5|RBM_XMM6|RBM_XMM7| \ RBM_XMM8|RBM_XMM9|RBM_XMM10|RBM_XMM11|RBM_XMM12|RBM_XMM13|RBM_XMM14|RBM_XMM15) - #define RBM_FLT_CALLEE_TRASH rbmFltCalleeTrash + #define RBM_FLT_CALLEE_TRASH RBM_FLT_CALLEE_TRASH_USE #define REG_PROFILER_ENTER_ARG_0 REG_R14 #define RBM_PROFILER_ENTER_ARG_0 RBM_R14 @@ -144,7 +144,7 @@ #define RBM_FLT_CALLEE_SAVED (RBM_XMM6|RBM_XMM7|RBM_XMM8|RBM_XMM9|RBM_XMM10|RBM_XMM11|RBM_XMM12|RBM_XMM13|RBM_XMM14|RBM_XMM15) /* NOTE: Sync with variable name defined in compiler.h */ #define RBM_FLT_CALLEE_TRASH_INIT (RBM_XMM0|RBM_XMM1|RBM_XMM2|RBM_XMM3|RBM_XMM4|RBM_XMM5) - #define RBM_FLT_CALLEE_TRASH rbmFltCalleeTrash + #define RBM_FLT_CALLEE_TRASH RBM_FLT_CALLEE_TRASH_USE #endif // !UNIX_AMD64_ABI #define RBM_OSR_INT_CALLEE_SAVED (RBM_INT_CALLEE_SAVED | RBM_EBP) @@ -152,7 +152,7 @@ #define REG_FLT_CALLEE_SAVED_FIRST REG_XMM6 #define REG_FLT_CALLEE_SAVED_LAST REG_XMM15 - #define RBM_CALLEE_TRASH (RBM_INT_CALLEE_TRASH | rbmFltCalleeTrash) + #define RBM_CALLEE_TRASH (RBM_INT_CALLEE_TRASH | RBM_FLT_CALLEE_TRASH) #define RBM_CALLEE_SAVED (RBM_INT_CALLEE_SAVED | RBM_FLT_CALLEE_SAVED) @@ -227,7 +227,7 @@ #define CNT_CALLEE_TRASH_FLOAT_INIT (16) #define CNT_CALLEE_TRASH_HIGHFLOAT (16) /* NOTE: Sync with variable name defined in compiler.h */ - #define CNT_CALLEE_TRASH_FLOAT cntCalleeTrashFloat + #define CNT_CALLEE_TRASH_FLOAT CNT_CALLEE_TRASH_FLOAT_USE #define REG_CALLEE_SAVED_ORDER REG_EBX,REG_ETW_FRAMED_EBP_LIST REG_R12,REG_R13,REG_R14,REG_R15 #define RBM_CALLEE_SAVED_ORDER RBM_EBX,RBM_ETW_FRAMED_EBP_LIST RBM_R12,RBM_R13,RBM_R14,RBM_R15