[RFC PATCH 9/8] [x86] Attempt to fix retw for 16-bit mode
David Woodhouse
dwmw2 at infradead.org
Mon Dec 16 14:14:56 PST 2013
This one is fun. Apparently if I want to make 'ret' alias to 'retw'
in .code16 and to 'retl' in .code32, I have to separate the two
definitions for 32-bit and 64-bit mode, and then I end up hacking up a
whole *bunch* of code I have no understanding of, as well as all the
tests.
It's mostly cosmetic though. I could actually live with having to
explicitly say 'retw' in .code16 instead of expecting 'ret' to alias to
it.
Any time someone with an actual clue wants to take a look and put me out
of my misery, that would be fine... :)
---
Although this is patch 9/8 there are still only 8 really, since I've
dropped the second one from my series. I came to the conclusion that the
signed 16-bit relocation was entirely pointless, and just used FK_Data_2
instead. Rather than spamming the list with the whole set again, I've
pushed them to http://git.infradead.org/users/dwmw2/llvm.git
lib/Target/X86/X86FastISel.cpp | 2 +-
lib/Target/X86/X86FloatingPoint.cpp | 3 ++-
lib/Target/X86/X86FrameLowering.cpp | 10 ++++++----
lib/Target/X86/X86InstrControl.td | 11 +++++++----
lib/Target/X86/X86InstrInfo.td | 5 +++--
lib/Target/X86/X86MCInstLower.cpp | 13 +++++++++----
test/CodeGen/X86/2008-08-31-EH_RETURN64.ll | 2 +-
test/CodeGen/X86/fast-isel-x86.ll | 6 +++---
test/CodeGen/X86/sibcall.ll | 4 ++--
test/CodeGen/X86/stdcall-notailcall.ll | 4 ++--
test/CodeGen/X86/stdcall.ll | 4 ++--
test/CodeGen/X86/win32_sret.ll | 28 ++++++++++++++--------------
12 files changed, 52 insertions(+), 40 deletions(-)
diff --git a/lib/Target/X86/X86FastISel.cpp b/lib/Target/X86/X86FastISel.cpp
index 28a6ac0..115c9ca 100644
--- a/lib/Target/X86/X86FastISel.cpp
+++ b/lib/Target/X86/X86FastISel.cpp
@@ -888,7 +888,7 @@ bool X86FastISel::X86SelectRet(const Instruction *I) {
// Now emit the RET.
MachineInstrBuilder MIB =
- BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DL, TII.get(X86::RET));
+ BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DL, TII.get(Subtarget->is64Bit() ? X86::RETQ : X86::RETL));
for (unsigned i = 0, e = RetRegs.size(); i != e; ++i)
MIB.addReg(RetRegs[i], RegState::Implicit);
return true;
diff --git a/lib/Target/X86/X86FloatingPoint.cpp b/lib/Target/X86/X86FloatingPoint.cpp
index 48470da..d6d0bbc 100644
--- a/lib/Target/X86/X86FloatingPoint.cpp
+++ b/lib/Target/X86/X86FloatingPoint.cpp
@@ -1671,7 +1671,8 @@ void FPS::handleSpecialFP(MachineBasicBlock::iterator &I) {
break;
}
- case X86::RET:
+ case X86::RETQ:
+ case X86::RETL:
case X86::RETI:
// If RET has an FP register use operand, pass the first one in ST(0) and
// the second one in ST(1).
diff --git a/lib/Target/X86/X86FrameLowering.cpp b/lib/Target/X86/X86FrameLowering.cpp
index 0c5209c..5a92e7e 100644
--- a/lib/Target/X86/X86FrameLowering.cpp
+++ b/lib/Target/X86/X86FrameLowering.cpp
@@ -107,7 +107,8 @@ static unsigned findDeadCallerSavedReg(MachineBasicBlock &MBB,
unsigned Opc = MBBI->getOpcode();
switch (Opc) {
default: return 0;
- case X86::RET:
+ case X86::RETL:
+ case X86::RETQ:
case X86::RETI:
case X86::TCRETURNdi:
case X86::TCRETURNri:
@@ -728,7 +729,8 @@ void X86FrameLowering::emitEpilogue(MachineFunction &MF,
switch (RetOpcode) {
default:
llvm_unreachable("Can only insert epilog into returning blocks");
- case X86::RET:
+ case X86::RETQ:
+ case X86::RETL:
case X86::RETI:
case X86::TCRETURNdi:
case X86::TCRETURNri:
@@ -886,8 +888,8 @@ void X86FrameLowering::emitEpilogue(MachineFunction &MF,
// Delete the pseudo instruction TCRETURN.
MBB.erase(MBBI);
- } else if ((RetOpcode == X86::RET || RetOpcode == X86::RETI) &&
- (X86FI->getTCReturnAddrDelta() < 0)) {
+ } else if ((RetOpcode == X86::RETQ || RetOpcode == X86::RETI ||
+ RetOpcode == X86::RETL) && (X86FI->getTCReturnAddrDelta() < 0)) {
// Add the return addr area delta back since we are not tail calling.
int delta = -1*X86FI->getTCReturnAddrDelta();
MBBI = MBB.getLastNonDebugInstr();
diff --git a/lib/Target/X86/X86InstrControl.td b/lib/Target/X86/X86InstrControl.td
index fd82c55..6ece45e 100644
--- a/lib/Target/X86/X86InstrControl.td
+++ b/lib/Target/X86/X86InstrControl.td
@@ -21,14 +21,17 @@
// ST1 arguments when returning values on the x87 stack.
let isTerminator = 1, isReturn = 1, isBarrier = 1,
hasCtrlDep = 1, FPForm = SpecialFP, SchedRW = [WriteJumpLd] in {
- def RET : I <0xC3, RawFrm, (outs), (ins variable_ops),
- "ret",
- [(X86retflag 0)], IIC_RET>, OpSize16;
+ def RETL : I <0xC3, RawFrm, (outs), (ins variable_ops),
+ "ret{l}",
+ [(X86retflag 0)], IIC_RET>, OpSize16, Requires<[Not64BitMode]>;
+ def RETQ : I <0xC3, RawFrm, (outs), (ins variable_ops),
+ "ret{q}",
+ [(X86retflag 0)], IIC_RET>, Requires<[In64BitMode]>;
def RETW : I <0xC3, RawFrm, (outs), (ins),
"ret{w}",
[], IIC_RET>, OpSize;
def RETI : Ii16<0xC2, RawFrm, (outs), (ins i16imm:$amt, variable_ops),
- "ret\t$amt",
+ "ret{l}\t$amt",
[(X86retflag timm:$amt)], IIC_RET_IMM>, OpSize16;
def RETIW : Ii16<0xC2, RawFrm, (outs), (ins i16imm:$amt),
"ret{w}\t$amt",
diff --git a/lib/Target/X86/X86InstrInfo.td b/lib/Target/X86/X86InstrInfo.td
index b8576be..f8d67bf 100644
--- a/lib/Target/X86/X86InstrInfo.td
+++ b/lib/Target/X86/X86InstrInfo.td
@@ -2170,8 +2170,9 @@ def : MnemonicAlias<"repe", "rep", "att">;
def : MnemonicAlias<"repz", "rep", "att">;
def : MnemonicAlias<"repnz", "repne", "att">;
-def : MnemonicAlias<"retl", "ret", "att">, Requires<[Not64BitMode]>;
-def : MnemonicAlias<"retq", "ret", "att">, Requires<[In64BitMode]>;
+def : MnemonicAlias<"ret", "retw", "att">, Requires<[In16BitMode]>;
+def : MnemonicAlias<"ret", "retl", "att">, Requires<[In32BitMode]>;
+def : MnemonicAlias<"ret", "retq", "att">, Requires<[In64BitMode]>;
def : MnemonicAlias<"salb", "shlb", "att">;
def : MnemonicAlias<"salw", "shlw", "att">;
diff --git a/lib/Target/X86/X86MCInstLower.cpp b/lib/Target/X86/X86MCInstLower.cpp
index 78d45e8..545ed4a 100644
--- a/lib/Target/X86/X86MCInstLower.cpp
+++ b/lib/Target/X86/X86MCInstLower.cpp
@@ -466,10 +466,15 @@ ReSimplify:
break;
}
- case X86::EH_RETURN:
+ case X86::EH_RETURN: {
+ OutMI = MCInst();
+ OutMI.setOpcode(X86::RETL);
+ break;
+ }
+
case X86::EH_RETURN64: {
OutMI = MCInst();
- OutMI.setOpcode(X86::RET);
+ OutMI.setOpcode(X86::RETQ);
break;
}
@@ -873,12 +878,12 @@ void X86AsmPrinter::EmitInstruction(const MachineInstr *MI) {
return LowerPATCHPOINT(OutStreamer, SM, *MI, Subtarget->is64Bit());
case X86::MORESTACK_RET:
- OutStreamer.EmitInstruction(MCInstBuilder(X86::RET));
+ OutStreamer.EmitInstruction(MCInstBuilder(Subtarget->is64Bit() ? X86::RETQ : X86::RETL));
return;
case X86::MORESTACK_RET_RESTORE_R10:
// Return, then restore R10.
- OutStreamer.EmitInstruction(MCInstBuilder(X86::RET));
+ OutStreamer.EmitInstruction(MCInstBuilder(Subtarget->is64Bit() ? X86::RETQ : X86::RETL));
OutStreamer.EmitInstruction(MCInstBuilder(X86::MOV64rr)
.addReg(X86::R10)
.addReg(X86::RAX));
diff --git a/test/CodeGen/X86/2008-08-31-EH_RETURN64.ll b/test/CodeGen/X86/2008-08-31-EH_RETURN64.ll
index 496779c..51064f1 100644
--- a/test/CodeGen/X86/2008-08-31-EH_RETURN64.ll
+++ b/test/CodeGen/X86/2008-08-31-EH_RETURN64.ll
@@ -9,7 +9,7 @@ target triple = "x86_64-unknown-linux-gnu"
; CHECK: movq %rsp, %rbp
; CHECK: popq %rbp
; CHECK: movq %rcx, %rsp
-; CHECK: ret # eh_return, addr: %rcx
+; CHECK: retq # eh_return, addr: %rcx
define i8* @test(i64 %a, i8* %b) {
entry:
call void @llvm.eh.unwind.init()
diff --git a/test/CodeGen/X86/fast-isel-x86.ll b/test/CodeGen/X86/fast-isel-x86.ll
index ba86e88..a212a7c 100644
--- a/test/CodeGen/X86/fast-isel-x86.ll
+++ b/test/CodeGen/X86/fast-isel-x86.ll
@@ -3,7 +3,7 @@
; This should use flds to set the return value.
; CHECK-LABEL: test0:
; CHECK: flds
-; CHECK: ret
+; CHECK: retl
@G = external global float
define float @test0() nounwind {
%t = load float* @G
@@ -12,7 +12,7 @@ define float @test0() nounwind {
; This should pop 4 bytes on return.
; CHECK-LABEL: test1:
-; CHECK: ret $4
+; CHECK: retl $4
define void @test1({i32, i32, i32, i32}* sret %p) nounwind {
store {i32, i32, i32, i32} zeroinitializer, {i32, i32, i32, i32}* %p
ret void
@@ -25,7 +25,7 @@ define void @test1({i32, i32, i32, i32}* sret %p) nounwind {
; CHECK-NEXT: L2$pb:
; CHECK-NEXT: pop
; CHECK: HHH
-; CHECK: ret
+; CHECK: retl
@HHH = external global i32
define i32 @test2() nounwind {
%t = load i32* @HHH
diff --git a/test/CodeGen/X86/sibcall.ll b/test/CodeGen/X86/sibcall.ll
index 589e9ec..28fc626 100644
--- a/test/CodeGen/X86/sibcall.ll
+++ b/test/CodeGen/X86/sibcall.ll
@@ -247,11 +247,11 @@ entry:
define void @t15(%struct.foo* noalias sret %agg.result) nounwind {
; 32-LABEL: t15:
; 32: calll {{_?}}f
-; 32: ret $4
+; 32: retl $4
; 64-LABEL: t15:
; 64: callq {{_?}}f
-; 64: ret
+; 64: retq
tail call fastcc void @f(%struct.foo* noalias sret %agg.result) nounwind
ret void
}
diff --git a/test/CodeGen/X86/stdcall-notailcall.ll b/test/CodeGen/X86/stdcall-notailcall.ll
index c847ec7..448db4c 100644
--- a/test/CodeGen/X86/stdcall-notailcall.ll
+++ b/test/CodeGen/X86/stdcall-notailcall.ll
@@ -4,7 +4,7 @@
define x86_stdcallcc void @bar(%struct.I* nocapture %this) ssp align 2 {
; CHECK-LABEL: bar:
; CHECK-NOT: jmp
-; CHECK: ret $4
+; CHECK: retl $4
entry:
tail call void @foo()
ret void
@@ -13,7 +13,7 @@ entry:
define x86_thiscallcc void @test2(%struct.I* %this, i32 %a) {
; CHECK-LABEL: test2:
; CHECK: calll _foo
-; CHECK: ret $4
+; CHECK: retl $4
tail call void @foo()
ret void
}
diff --git a/test/CodeGen/X86/stdcall.ll b/test/CodeGen/X86/stdcall.ll
index 73826ed..3cefe14 100644
--- a/test/CodeGen/X86/stdcall.ll
+++ b/test/CodeGen/X86/stdcall.ll
@@ -6,14 +6,14 @@
define internal x86_stdcallcc void @MyFunc() nounwind {
entry:
; CHECK: MyFunc at 0:
-; CHECK: ret
+; CHECK: retl
ret void
}
; PR14410
define x86_stdcallcc i32 @"\01DoNotMangle"(i32 %a) {
; CHECK: DoNotMangle:
-; CHECK: ret $4
+; CHECK: retl $4
entry:
ret i32 %a
}
diff --git a/test/CodeGen/X86/win32_sret.ll b/test/CodeGen/X86/win32_sret.ll
index 78f1821..d8ecd44 100644
--- a/test/CodeGen/X86/win32_sret.ll
+++ b/test/CodeGen/X86/win32_sret.ll
@@ -16,13 +16,13 @@ entry:
; WIN32-LABEL: _sret1:
; WIN32: movb $42, (%eax)
; WIN32-NOT: popl %eax
-; WIN32: {{ret$}}
+; WIN32: {{retl$}}
; MINGW_X86-LABEL: _sret1:
-; MINGW_X86: {{ret$}}
+; MINGW_X86: {{retl$}}
; LINUX-LABEL: sret1:
-; LINUX: ret $4
+; LINUX: retl $4
store i8 42, i8* %x, align 4
ret void
@@ -33,13 +33,13 @@ entry:
; WIN32-LABEL: _sret2:
; WIN32: movb {{.*}}, (%eax)
; WIN32-NOT: popl %eax
-; WIN32: {{ret$}}
+; WIN32: {{retl$}}
; MINGW_X86-LABEL: _sret2:
-; MINGW_X86: {{ret$}}
+; MINGW_X86: {{retl$}}
; LINUX-LABEL: sret2:
-; LINUX: ret $4
+; LINUX: retl $4
store i8 %y, i8* %x
ret void
@@ -51,13 +51,13 @@ entry:
; WIN32: movb $42, (%eax)
; WIN32-NOT: movb $13, (%eax)
; WIN32-NOT: popl %eax
-; WIN32: {{ret$}}
+; WIN32: {{retl$}}
; MINGW_X86-LABEL: _sret3:
-; MINGW_X86: {{ret$}}
+; MINGW_X86: {{retl$}}
; LINUX-LABEL: sret3:
-; LINUX: ret $4
+; LINUX: retl $4
store i8 42, i8* %x
store i8 13, i8* %y
@@ -72,13 +72,13 @@ entry:
; WIN32-LABEL: _sret4:
; WIN32: movl $42, (%eax)
; WIN32-NOT: popl %eax
-; WIN32: {{ret$}}
+; WIN32: {{retl$}}
; MINGW_X86-LABEL: _sret4:
-; MINGW_X86: {{ret$}}
+; MINGW_X86: {{retl$}}
; LINUX-LABEL: sret4:
-; LINUX: ret $4
+; LINUX: retl $4
%x = getelementptr inbounds %struct.S4* %agg.result, i32 0, i32 0
store i32 42, i32* %x, align 4
@@ -105,7 +105,7 @@ entry:
; should match both 4(%esp) and 8(%esp).
; WIN32: {{[48]}}(%esp), %eax
; WIN32: movl $42, (%eax)
-; WIN32: ret $4
+; WIN32: retl $4
}
define void @call_foo5() {
@@ -126,7 +126,7 @@ entry:
; The this pointer goes to ECX.
; WIN32-NEXT: leal {{[0-9]+}}(%esp), %ecx
; WIN32-NEXT: calll "?foo at C5@@QAE?AUS5@@XZ"
-; WIN32: ret
+; WIN32: retl
ret void
}
--
1.8.3.1
--
David Woodhouse Open Source Technology Centre
David.Woodhouse at intel.com Intel Corporation
-------------- next part --------------
A non-text attachment was scrubbed...
Name: smime.p7s
Type: application/x-pkcs7-signature
Size: 5745 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20131216/6d922b69/attachment.bin>
More information about the llvm-commits
mailing list