mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2025-10-05 10:49:34 +02:00
CircleRange contain and widen adjustments
This commit is contained in:
parent
ab9b8dd602
commit
49f72d2de7
1 changed files with 64 additions and 34 deletions
|
@ -295,7 +295,7 @@ int4 CircleRange::getMaxInfo(void) const
|
||||||
}
|
}
|
||||||
|
|
||||||
/// \param op2 is the specific range to test for containment.
|
/// \param op2 is the specific range to test for containment.
|
||||||
/// \return \b true if \b true contains the interval \b op2
|
/// \return \b true if \b this contains the interval \b op2
|
||||||
bool CircleRange::contains(const CircleRange &op2) const
|
bool CircleRange::contains(const CircleRange &op2) const
|
||||||
|
|
||||||
{
|
{
|
||||||
|
@ -303,13 +303,24 @@ bool CircleRange::contains(const CircleRange &op2) const
|
||||||
return op2.isempty;
|
return op2.isempty;
|
||||||
if (op2.isempty)
|
if (op2.isempty)
|
||||||
return true;
|
return true;
|
||||||
if (step > op2.step) return false; // Cannot be containment because step is wrong
|
if (step > op2.step) {
|
||||||
|
// This must have a smaller or equal step to op2 or containment is impossible
|
||||||
|
// except in the corner case where op2 consists of a single element (its step is meaningless)
|
||||||
|
if (!op2.isSingle())
|
||||||
|
return false;
|
||||||
|
}
|
||||||
if (left == right) return true;
|
if (left == right) return true;
|
||||||
if (op2.left == op2.right) return false;
|
if (op2.left == op2.right) return false;
|
||||||
|
if (left % step != op2.left % step) return false; // Wrong phase
|
||||||
|
if (left == op2.left && right == op2.right) return true;
|
||||||
|
|
||||||
char overlapCode = encodeRangeOverlaps(left, right, op2.left, op2.right);
|
char overlapCode = encodeRangeOverlaps(left, right, op2.left, op2.right);
|
||||||
|
|
||||||
return (overlapCode == 'c');
|
if (overlapCode == 'c')
|
||||||
|
return true;
|
||||||
|
if (overlapCode == 'b' && (right == op2.right))
|
||||||
|
return true;
|
||||||
|
return false;
|
||||||
|
|
||||||
// Missing one case where op2.step > this->step, and the boundaries don't show containment,
|
// Missing one case where op2.step > this->step, and the boundaries don't show containment,
|
||||||
// but there is containment because the lower step size UP TO right still contains the edge points
|
// but there is containment because the lower step size UP TO right still contains the edge points
|
||||||
|
@ -1368,7 +1379,13 @@ void CircleRange::widen(const CircleRange &op2,bool leftIsStable)
|
||||||
|
|
||||||
{
|
{
|
||||||
if (leftIsStable) {
|
if (leftIsStable) {
|
||||||
right = (op2.right + step-1) & mask;
|
uintb lmod = left % step;
|
||||||
|
uintb mod = op2.right % step;
|
||||||
|
if (mod <= lmod)
|
||||||
|
right = op2.right + (lmod - mod);
|
||||||
|
else
|
||||||
|
right = op2.right - (mod - lmod);
|
||||||
|
right &= mask;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
left = op2.left & mask;
|
left = op2.left & mask;
|
||||||
|
@ -1534,7 +1551,7 @@ bool ValueSet::computeTypeCode(void)
|
||||||
|
|
||||||
{
|
{
|
||||||
int4 relCount = 0;
|
int4 relCount = 0;
|
||||||
int4 lastTypeCode;
|
int4 lastTypeCode = 0;
|
||||||
PcodeOp *op = vn->getDef();
|
PcodeOp *op = vn->getDef();
|
||||||
for(int4 i=0;i<numParams;++i) {
|
for(int4 i=0;i<numParams;++i) {
|
||||||
ValueSet *valueSet = op->getIn(i)->getValueSet();
|
ValueSet *valueSet = op->getIn(i)->getValueSet();
|
||||||
|
@ -2176,42 +2193,48 @@ void ValueSetSolver::generateConstraints(const vector<Varnode *> &worklist,const
|
||||||
|
|
||||||
{
|
{
|
||||||
vector<FlowBlock *> blockList;
|
vector<FlowBlock *> blockList;
|
||||||
|
// Collect all blocks that contain a system op or dominate a container
|
||||||
for(int4 i=0;i<worklist.size();++i) {
|
for(int4 i=0;i<worklist.size();++i) {
|
||||||
PcodeOp *op = worklist[i]->getDef();
|
PcodeOp *op = worklist[i]->getDef();
|
||||||
if (op == (PcodeOp *)0) continue;
|
if (op == (PcodeOp *)0) continue;
|
||||||
BlockBasic *bl = (BlockBasic *)op->getParent()->getImmedDom();
|
FlowBlock *bl = op->getParent();
|
||||||
while(bl != (FlowBlock *)0) {
|
while(bl != (FlowBlock *)0) {
|
||||||
if (!bl->isMark()) {
|
if (bl->isMark()) break;
|
||||||
bl->setMark();
|
bl->setMark();
|
||||||
blockList.push_back(bl);
|
blockList.push_back(bl);
|
||||||
PcodeOp *lastOp = bl->lastOp();
|
bl = bl->getImmedDom();
|
||||||
if (lastOp != (PcodeOp *)0 && lastOp->code() == CPUI_CBRANCH) {
|
|
||||||
constraintsFromCBranch(lastOp);
|
|
||||||
}
|
|
||||||
bl = (BlockBasic *)bl->getImmedDom();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for(int4 i=0;i<reads.size();++i) {
|
for(int4 i=0;i<reads.size();++i) {
|
||||||
BlockBasic *bl = (BlockBasic *)reads[i]->getParent()->getImmedDom();
|
FlowBlock *bl = reads[i]->getParent();
|
||||||
while(bl != (FlowBlock *)0) {
|
while(bl != (FlowBlock *)0) {
|
||||||
if (!bl->isMark()) {
|
if (bl->isMark()) break;
|
||||||
bl->setMark();
|
bl->setMark();
|
||||||
blockList.push_back(bl);
|
blockList.push_back(bl);
|
||||||
PcodeOp *lastOp = bl->lastOp();
|
bl = bl->getImmedDom();
|
||||||
if (lastOp != (PcodeOp *)0 && lastOp->code() == CPUI_CBRANCH) {
|
|
||||||
constraintsFromCBranch(lastOp);
|
|
||||||
}
|
|
||||||
bl = (BlockBasic *)bl->getImmedDom();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for(int4 i=0;i<blockList.size();++i)
|
for(int4 i=0;i<blockList.size();++i)
|
||||||
blockList[i]->clearMark();
|
blockList[i]->clearMark();
|
||||||
|
|
||||||
|
vector<FlowBlock *> finalList;
|
||||||
|
// Now go through input blocks to the previously calculated blocks
|
||||||
|
for(int4 i=0;i<blockList.size();++i) {
|
||||||
|
FlowBlock *bl = blockList[i];
|
||||||
|
for(int4 j=0;j<bl->sizeIn();++j) {
|
||||||
|
BlockBasic *splitPoint = (BlockBasic *)bl->getIn(j);
|
||||||
|
if (splitPoint->isMark()) continue;
|
||||||
|
if (splitPoint->sizeOut() != 2) continue;
|
||||||
|
PcodeOp *lastOp = splitPoint->lastOp();
|
||||||
|
if (lastOp != (PcodeOp *)0 && lastOp->code() == CPUI_CBRANCH) {
|
||||||
|
splitPoint->setMark();
|
||||||
|
finalList.push_back(splitPoint);
|
||||||
|
constraintsFromCBranch(lastOp); // Try to generate constraints from this splitPoint
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for(int4 i=0;i<finalList.size();++i)
|
||||||
|
finalList[i]->clearMark();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Verify that the given Varnode is produced by a straight line sequence of
|
/// Verify that the given Varnode is produced by a straight line sequence of
|
||||||
|
@ -2248,7 +2271,7 @@ bool ValueSetSolver::checkRelativeConstant(Varnode *vn,int4 &typeCode,uintb &val
|
||||||
else
|
else
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
return true; // Never reach here
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Given a binary PcodeOp producing a conditional branch, check if it can be interpreted
|
/// Given a binary PcodeOp producing a conditional branch, check if it can be interpreted
|
||||||
|
@ -2298,12 +2321,19 @@ void ValueSetSolver::generateRelativeConstraint(PcodeOp *compOp,PcodeOp *cbranch
|
||||||
while(!endVn->isMark()) {
|
while(!endVn->isMark()) {
|
||||||
if (!endVn->isWritten()) return;
|
if (!endVn->isWritten()) return;
|
||||||
PcodeOp *op = endVn->getDef();
|
PcodeOp *op = endVn->getDef();
|
||||||
if (op->code() != CPUI_COPY && op->code() != CPUI_INDIRECT)
|
opc = op->code();
|
||||||
|
if (opc == CPUI_COPY || opc == CPUI_PTRSUB) {
|
||||||
|
endVn = op->getIn(0);
|
||||||
|
}
|
||||||
|
else if (opc == CPUI_INT_ADD) { // Can pull-back through INT_ADD
|
||||||
|
if (!op->getIn(1)->isConstant()) // if second param is constant
|
||||||
return;
|
return;
|
||||||
endVn = op->getIn(0);
|
endVn = op->getIn(0);
|
||||||
}
|
}
|
||||||
if (endVn != (Varnode *)0)
|
else
|
||||||
constraintsFromPath(typeCode,lift,endVn,endVn,cbranch);
|
return;
|
||||||
|
}
|
||||||
|
constraintsFromPath(typeCode,lift,vn,endVn,cbranch);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// \brief Build value sets for a data-flow system
|
/// \brief Build value sets for a data-flow system
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue