@@ -27081,9 +27081,6 @@ static const char *getRetpolineSymbol(const X86Subtarget &Subtarget,
27081
27081
// attempt to help out kernels and other systems where duplicating the
27082
27082
// thunks is costly.
27083
27083
switch (Reg) {
27084
- case 0:
27085
- assert(!Subtarget.is64Bit() && "R11 should always be available on x64");
27086
- return "__x86_indirect_thunk";
27087
27084
case X86::EAX:
27088
27085
assert(!Subtarget.is64Bit() && "Should not be using a 32-bit thunk!");
27089
27086
return "__x86_indirect_thunk_eax";
@@ -27093,6 +27090,9 @@ static const char *getRetpolineSymbol(const X86Subtarget &Subtarget,
27093
27090
case X86::EDX:
27094
27091
assert(!Subtarget.is64Bit() && "Should not be using a 32-bit thunk!");
27095
27092
return "__x86_indirect_thunk_edx";
27093
+ case X86::EDI:
27094
+ assert(!Subtarget.is64Bit() && "Should not be using a 32-bit thunk!");
27095
+ return "__x86_indirect_thunk_edi";
27096
27096
case X86::R11:
27097
27097
assert(Subtarget.is64Bit() && "Should not be using a 64-bit thunk!");
27098
27098
return "__x86_indirect_thunk_r11";
@@ -27102,9 +27102,6 @@ static const char *getRetpolineSymbol(const X86Subtarget &Subtarget,
27102
27102
27103
27103
// When targeting an internal COMDAT thunk use an LLVM-specific name.
27104
27104
switch (Reg) {
27105
- case 0:
27106
- assert(!Subtarget.is64Bit() && "R11 should always be available on x64");
27107
- return "__llvm_retpoline_push";
27108
27105
case X86::EAX:
27109
27106
assert(!Subtarget.is64Bit() && "Should not be using a 32-bit thunk!");
27110
27107
return "__llvm_retpoline_eax";
@@ -27114,6 +27111,9 @@ static const char *getRetpolineSymbol(const X86Subtarget &Subtarget,
27114
27111
case X86::EDX:
27115
27112
assert(!Subtarget.is64Bit() && "Should not be using a 32-bit thunk!");
27116
27113
return "__llvm_retpoline_edx";
27114
+ case X86::EDI:
27115
+ assert(!Subtarget.is64Bit() && "Should not be using a 32-bit thunk!");
27116
+ return "__llvm_retpoline_edi";
27117
27117
case X86::R11:
27118
27118
assert(Subtarget.is64Bit() && "Should not be using a 64-bit thunk!");
27119
27119
return "__llvm_retpoline_r11";
@@ -27135,15 +27135,13 @@ X86TargetLowering::EmitLoweredRetpoline(MachineInstr &MI,
27135
27135
// just use R11, but we scan for uses anyway to ensure we don't generate
27136
27136
// incorrect code. On 32-bit, we use one of EAX, ECX, or EDX that isn't
27137
27137
// already a register use operand to the call to hold the callee. If none
27138
- // are available, push the callee instead. This is less efficient, but is
27139
- // necessary for functions using 3 regparms. Such function calls are
27140
- // (currently) not eligible for tail call optimization, because there is no
27141
- // scratch register available to hold the address of the callee.
27138
+ // are available, use EDI instead. EDI is chosen because EBX is the PIC base
27139
+ // register and ESI is the base pointer to realigned stack frames with VLAs.
27142
27140
SmallVector<unsigned, 3> AvailableRegs;
27143
27141
if (Subtarget.is64Bit())
27144
27142
AvailableRegs.push_back(X86::R11);
27145
27143
else
27146
- AvailableRegs.append({X86::EAX, X86::ECX, X86::EDX});
27144
+ AvailableRegs.append({X86::EAX, X86::ECX, X86::EDX, X86::EDI });
27147
27145
27148
27146
// Zero out any registers that are already used.
27149
27147
for (const auto &MO : MI.operands()) {
@@ -27161,30 +27159,18 @@ X86TargetLowering::EmitLoweredRetpoline(MachineInstr &MI,
27161
27159
break;
27162
27160
}
27163
27161
}
27162
+ if (!AvailableReg)
27163
+ report_fatal_error("calling convention incompatible with retpoline, no "
27164
+ "available registers");
27164
27165
27165
27166
const char *Symbol = getRetpolineSymbol(Subtarget, AvailableReg);
27166
27167
27167
- if (AvailableReg == 0) {
27168
- // No register available. Use PUSH. This must not be a tailcall, and this
27169
- // must not be x64.
27170
- if (Subtarget.is64Bit())
27171
- report_fatal_error(
27172
- "Cannot make an indirect call on x86-64 using both retpoline and a "
27173
- "calling convention that preservers r11");
27174
- if (Opc != X86::CALLpcrel32)
27175
- report_fatal_error("Cannot make an indirect tail call on x86 using "
27176
- "retpoline without a preserved register");
27177
- BuildMI(*BB, MI, DL, TII->get(X86::PUSH32r)).addReg(CalleeVReg);
27178
- MI.getOperand(0).ChangeToES(Symbol);
27179
- MI.setDesc(TII->get(Opc));
27180
- } else {
27181
- BuildMI(*BB, MI, DL, TII->get(TargetOpcode::COPY), AvailableReg)
27182
- .addReg(CalleeVReg);
27183
- MI.getOperand(0).ChangeToES(Symbol);
27184
- MI.setDesc(TII->get(Opc));
27185
- MachineInstrBuilder(*BB->getParent(), &MI)
27186
- .addReg(AvailableReg, RegState::Implicit | RegState::Kill);
27187
- }
27168
+ BuildMI(*BB, MI, DL, TII->get(TargetOpcode::COPY), AvailableReg)
27169
+ .addReg(CalleeVReg);
27170
+ MI.getOperand(0).ChangeToES(Symbol);
27171
+ MI.setDesc(TII->get(Opc));
27172
+ MachineInstrBuilder(*BB->getParent(), &MI)
27173
+ .addReg(AvailableReg, RegState::Implicit | RegState::Kill);
27188
27174
return BB;
27189
27175
}
27190
27176
0 commit comments