summaryrefslogtreecommitdiff
path: root/lib/CodeGen
diff options
context:
space:
mode:
authorDimitry Andric <dim@FreeBSD.org>2016-02-13 14:57:10 +0000
committerDimitry Andric <dim@FreeBSD.org>2016-02-13 14:57:10 +0000
commita322a4af1fe8b989fe5d1bbc15de8736a26c03ca (patch)
tree0daaa3c98a8029d259c5918dfa1c13c9d4fe7971 /lib/CodeGen
parentaff3ef6f6ccad9bd4e082546f8161727c2019117 (diff)
Notes
Diffstat (limited to 'lib/CodeGen')
-rw-r--r--lib/CodeGen/AsmPrinter/AsmPrinterInlineAsm.cpp5
-rw-r--r--lib/CodeGen/AsmPrinter/DwarfDebug.cpp55
2 files changed, 47 insertions, 13 deletions
diff --git a/lib/CodeGen/AsmPrinter/AsmPrinterInlineAsm.cpp b/lib/CodeGen/AsmPrinter/AsmPrinterInlineAsm.cpp
index 4171657b5285..5633aa4a5655 100644
--- a/lib/CodeGen/AsmPrinter/AsmPrinterInlineAsm.cpp
+++ b/lib/CodeGen/AsmPrinter/AsmPrinterInlineAsm.cpp
@@ -555,6 +555,11 @@ bool AsmPrinter::PrintAsmOperand(const MachineInstr *MI, unsigned OpNo,
return true;
O << -MO.getImm();
return false;
+ case 's': // The GCC deprecated s modifier
+ if (MO.getType() != MachineOperand::MO_Immediate)
+ return true;
+ O << ((32 - MO.getImm()) & 31);
+ return false;
}
}
return true;
diff --git a/lib/CodeGen/AsmPrinter/DwarfDebug.cpp b/lib/CodeGen/AsmPrinter/DwarfDebug.cpp
index ae62b6b19a42..f56c8e492e52 100644
--- a/lib/CodeGen/AsmPrinter/DwarfDebug.cpp
+++ b/lib/CodeGen/AsmPrinter/DwarfDebug.cpp
@@ -793,16 +793,27 @@ static DebugLocEntry::Value getDebugLocValue(const MachineInstr *MI) {
llvm_unreachable("Unexpected 4-operand DBG_VALUE instruction!");
}
-/// Determine whether two variable pieces overlap.
-static bool piecesOverlap(const DIExpression *P1, const DIExpression *P2) {
- if (!P1->isBitPiece() || !P2->isBitPiece())
- return true;
+// Determine the relative position of the pieces described by P1 and P2.
+// Returns -1 if P1 is entirely before P2, 0 if P1 and P2 overlap,
+// 1 if P1 is entirely after P2.
+static int pieceCmp(const DIExpression *P1, const DIExpression *P2) {
unsigned l1 = P1->getBitPieceOffset();
unsigned l2 = P2->getBitPieceOffset();
unsigned r1 = l1 + P1->getBitPieceSize();
unsigned r2 = l2 + P2->getBitPieceSize();
- // True where [l1,r1[ and [r1,r2[ overlap.
- return (l1 < r2) && (l2 < r1);
+ if (r1 <= l2)
+ return -1;
+ else if (r2 <= l1)
+ return 1;
+ else
+ return 0;
+}
+
+/// Determine whether two variable pieces overlap.
+static bool piecesOverlap(const DIExpression *P1, const DIExpression *P2) {
+ if (!P1->isBitPiece() || !P2->isBitPiece())
+ return true;
+ return pieceCmp(P1, P2) == 0;
}
/// \brief If this and Next are describing different pieces of the same
@@ -811,14 +822,32 @@ static bool piecesOverlap(const DIExpression *P1, const DIExpression *P2) {
/// Return true if the merge was successful.
bool DebugLocEntry::MergeValues(const DebugLocEntry &Next) {
if (Begin == Next.Begin) {
- auto *Expr = cast_or_null<DIExpression>(Values[0].Expression);
- auto *NextExpr = cast_or_null<DIExpression>(Next.Values[0].Expression);
- if (Expr->isBitPiece() && NextExpr->isBitPiece() &&
- !piecesOverlap(Expr, NextExpr)) {
- addValues(Next.Values);
- End = Next.End;
- return true;
+ auto *FirstExpr = cast<DIExpression>(Values[0].Expression);
+ auto *FirstNextExpr = cast<DIExpression>(Next.Values[0].Expression);
+ if (!FirstExpr->isBitPiece() || !FirstNextExpr->isBitPiece())
+ return false;
+
+ // We can only merge entries if none of the pieces overlap any others.
+ // In doing so, we can take advantage of the fact that both lists are
+ // sorted.
+ for (unsigned i = 0, j = 0; i < Values.size(); ++i) {
+ for (; j < Next.Values.size(); ++j) {
+ int res = pieceCmp(cast<DIExpression>(Values[i].Expression),
+ cast<DIExpression>(Next.Values[j].Expression));
+ if (res == 0) // The two expressions overlap, we can't merge.
+ return false;
+ // Values[i] is entirely before Next.Values[j],
+ // so go back to the next entry of Values.
+ else if (res == -1)
+ break;
+ // Next.Values[j] is entirely before Values[i], so go on to the
+ // next entry of Next.Values.
+ }
}
+
+ addValues(Next.Values);
+ End = Next.End;
+ return true;
}
return false;
}