Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(758)

Unified Diff: lib/Target/Mips/MipsLongBranch.cpp

Issue 27690005: [MIPS] Modify LongBranch expansion to work with sandboxing (Closed) Base URL: http://git.chromium.org/native_client/pnacl-llvm.git@master
Patch Set: Changes per code review. Created 7 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: lib/Target/Mips/MipsLongBranch.cpp
diff --git a/lib/Target/Mips/MipsLongBranch.cpp b/lib/Target/Mips/MipsLongBranch.cpp
index 24b42b9150447a9da5925368352fe8c3e9e0dbdb..e8fe1214bb0273a9272aa5a9eeeff39b141e24d0 100644
--- a/lib/Target/Mips/MipsLongBranch.cpp
+++ b/lib/Target/Mips/MipsLongBranch.cpp
@@ -68,7 +68,8 @@ namespace {
TII(static_cast<const MipsInstrInfo*>(tm.getInstrInfo())),
IsPIC(TM.getRelocationModel() == Reloc::PIC_),
ABI(TM.getSubtarget<MipsSubtarget>().getTargetABI()),
- LongBranchSeqSize(!IsPIC ? 2 : (ABI == MipsSubtarget::N64 ? 13 : 9)) {}
+ LongBranchSeqSize(!IsPIC ? 2 : (ABI == MipsSubtarget::N64 ? 13 :
+ (/*@LOCALMOD*/Triple(TM.getTargetTriple()).isOSNaCl() ? 10 : 9))) {}
virtual const char *getPassName() const {
return "Mips Long Branch";
@@ -263,7 +264,9 @@ void MipsLongBranch::expandToLongBranch(MBBInfo &I) {
BalTgtMBB->addSuccessor(TgtMBB);
int64_t TgtAddress = MBBInfos[TgtMBB->getNumber()].Address;
- unsigned BalTgtMBBSize = 5;
+ // @LOCALMOD-START
+ unsigned BalTgtMBBSize = Triple(TM.getTargetTriple()).isOSNaCl() ? 6 : 5;
+ // @LOCALMOD-END
int64_t Offset = TgtAddress - (I.Address + I.Size - BalTgtMBBSize * 4);
int64_t Lo = SignExtend64<16>(Offset & 0xffff);
int64_t Hi = SignExtend64<16>(((Offset + 0x8000) >> 16) & 0xffff);
@@ -290,23 +293,69 @@ void MipsLongBranch::expandToLongBranch(MBBInfo &I) {
BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::SW)).addReg(Mips::RA)
.addReg(Mips::SP).addImm(0);
- MIBundleBuilder(*LongBrMBB, Pos)
- .append(BuildMI(*MF, DL, TII->get(Mips::BAL_BR)).addMBB(BalTgtMBB))
- .append(BuildMI(*MF, DL, TII->get(Mips::LUi), Mips::AT).addImm(Hi));
-
- Pos = BalTgtMBB->begin();
-
- BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::ADDiu), Mips::AT)
- .addReg(Mips::AT).addImm(Lo);
- BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::ADDu), Mips::AT)
- .addReg(Mips::RA).addReg(Mips::AT);
- BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::LW), Mips::RA)
- .addReg(Mips::SP).addImm(0);
-
- MIBundleBuilder(*BalTgtMBB, Pos)
- .append(BuildMI(*MF, DL, TII->get(Mips::JR)).addReg(Mips::AT))
- .append(BuildMI(*MF, DL, TII->get(Mips::ADDiu), Mips::SP)
- .addReg(Mips::SP).addImm(8));
+ if (Triple(TM.getTargetTriple()).isOSNaCl()) {
+ // @LOCALMOD-START
+ // LUi and ADDiu instructions create 32-bit offset of the target basic
+ // block from the BAL target. We cannot use immediate value as the
+ // offset (as non-NaCl version does) because it does not take
+ // sandboxed instructions into account ("sanboxing" is run after this
+ // pass). We therefore replace it with relocation expressions
+ // %hi($tgt-$baltgt) and %lo($tgt-$baltgt). This expressions are
+ // resolved during the fixup after all sandboxing code is added, so the
+ // values will always be correct.
+ //
+ // Since we cannot create %hi($tgt-$baltgt) and %lo($tgt-$baltgt)
+ // expressions at this point (it is possible only at the MC layer),
+ // we replace LUi and ADDiu with pseudo instructions
+ // NACL_LONG_BRANCH_LUi and NACL_LONG_BRANCH_ADDiu, and add both basic
+ // block as operands to these instructions. When lowering these pseudo
+ // instructions to LUi and ADDiu in the MC layer, we will create
+ // %hi($tgt-$baltgt) and %lo($tgt-$baltgt) expressions add add them as
+ // operands to lowered instructions.
+ MIBundleBuilder(*LongBrMBB, Pos)
+ .append(BuildMI(*MF, DL, TII->get(Mips::BAL_BR)).addMBB(BalTgtMBB))
+ .append(BuildMI(*MF, DL, TII->get(Mips::NACL_LONG_BRANCH_LUi),
+ Mips::AT).addMBB(TgtMBB).addMBB(BalTgtMBB));
+
+ Pos = BalTgtMBB->begin();
+
+ BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::NACL_LONG_BRANCH_ADDiu),
+ Mips::AT).addReg(Mips::AT).addMBB(TgtMBB).addMBB(BalTgtMBB);
+ BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::ADDu), Mips::AT)
+ .addReg(Mips::RA).addReg(Mips::AT);
+ BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::LW), Mips::RA)
+ .addReg(Mips::SP).addImm(0);
+
+ // In NaCl, modifying sp is not allowed in branch delay slot.
+ BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::ADDiu), Mips::SP)
+ .addReg(Mips::SP).addImm(8);
+
+ MIBundleBuilder(*BalTgtMBB, Pos)
+ .append(BuildMI(*MF, DL, TII->get(Mips::JR)).addReg(Mips::AT))
+ .append(BuildMI(*MF, DL, TII->get(Mips::NOP)));
+
+ // Align target of JR instruction.
+ TgtMBB->setAlignment(4);
+ // @LOCALMOD-END
+ } else {
+ MIBundleBuilder(*LongBrMBB, Pos)
+ .append(BuildMI(*MF, DL, TII->get(Mips::BAL_BR)).addMBB(BalTgtMBB))
+ .append(BuildMI(*MF, DL, TII->get(Mips::LUi), Mips::AT).addImm(Hi));
+
+ Pos = BalTgtMBB->begin();
+
+ BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::ADDiu), Mips::AT)
+ .addReg(Mips::AT).addImm(Lo);
+ BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::ADDu), Mips::AT)
+ .addReg(Mips::RA).addReg(Mips::AT);
+ BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::LW), Mips::RA)
+ .addReg(Mips::SP).addImm(0);
+
+ MIBundleBuilder(*BalTgtMBB, Pos)
+ .append(BuildMI(*MF, DL, TII->get(Mips::JR)).addReg(Mips::AT))
+ .append(BuildMI(*MF, DL, TII->get(Mips::ADDiu), Mips::SP)
+ .addReg(Mips::SP).addImm(8));
+ }
} else {
// $longbr:
// daddiu $sp, $sp, -16
@@ -430,8 +479,23 @@ bool MipsLongBranch::runOnMachineFunction(MachineFunction &F) {
continue;
// Check if offset fits into 16-bit immediate field of branches.
- if (!ForceLongBranch && isInt<16>(computeOffset(I->Br) / 4))
- continue;
+ if (Triple(TM.getTargetTriple()).isOSNaCl()) {
+ // @LOCALMOD-START
+ int64_t Offset = computeOffset(I->Br) / 4;
+
+ // This offset calculation does not include sandboxing instructions
+ // that will be added later in the MC layer. Since at this point we
+ // don't know the exact amount of code that "sanboxing" will add, we
+ // conservatively estimate that code will not grow more than 100%.
+ Offset *= 2;
+
+ if (!ForceLongBranch && isInt<16>(Offset))
+ continue;
+ // @LOCALMOD-END
+ } else {
+ if (!ForceLongBranch && isInt<16>(computeOffset(I->Br) / 4))
+ continue;
+ }
I->HasLongBranch = true;
I->Size += LongBranchSeqSize * 4;

Powered by Google App Engine
This is Rietveld 408576698