mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2025-10-06 12:00:04 +02:00
Merge remote-tracking branch 'origin/GT-3145_OverrideExternalRef' into Ghidra_9.1
This commit is contained in:
commit
cd4d26d226
4 changed files with 25 additions and 3 deletions
|
@ -4470,6 +4470,8 @@ void FuncCallSpecs::deindirect(Funcdata &data,Funcdata *newfd)
|
||||||
Varnode *vn = data.newVarnodeCallSpecs(this);
|
Varnode *vn = data.newVarnodeCallSpecs(this);
|
||||||
data.opSetInput(op,vn,0);
|
data.opSetInput(op,vn,0);
|
||||||
data.opSetOpcode(op,CPUI_CALL);
|
data.opSetOpcode(op,CPUI_CALL);
|
||||||
|
if (isOverride()) // If we are overridden at the call-site
|
||||||
|
return; // Don't use the discovered function prototype
|
||||||
|
|
||||||
// Try our best to merge existing prototype
|
// Try our best to merge existing prototype
|
||||||
// with the one we have just been handed
|
// with the one we have just been handed
|
||||||
|
|
|
@ -1158,7 +1158,8 @@ class FuncProto {
|
||||||
unknown_model = 512, ///< Set if the PrototypeModel isn't known
|
unknown_model = 512, ///< Set if the PrototypeModel isn't known
|
||||||
is_constructor = 0x400, ///< Function is an (object-oriented) constructor
|
is_constructor = 0x400, ///< Function is an (object-oriented) constructor
|
||||||
is_destructor = 0x800, ///< Function is an (object-oriented) destructor
|
is_destructor = 0x800, ///< Function is an (object-oriented) destructor
|
||||||
has_thisptr= 0x1000 ///< Function is a method with a 'this' pointer as an argument
|
has_thisptr= 0x1000, ///< Function is a method with a 'this' pointer as an argument
|
||||||
|
is_override = 0x2000 ///< Set if \b this prototype is created to override a single call site
|
||||||
};
|
};
|
||||||
ProtoModel *model; ///< Model of for \b this prototype
|
ProtoModel *model; ///< Model of for \b this prototype
|
||||||
ProtoStore *store; ///< Storage interface for parameters
|
ProtoStore *store; ///< Storage interface for parameters
|
||||||
|
@ -1332,6 +1333,8 @@ public:
|
||||||
bool isStackGrowsNegative(void) const { return model->isStackGrowsNegative(); } ///< Return \b true if the stack grows toward smaller addresses
|
bool isStackGrowsNegative(void) const { return model->isStackGrowsNegative(); } ///< Return \b true if the stack grows toward smaller addresses
|
||||||
bool isDotdotdot(void) const { return ((flags&dotdotdot)!=0); } ///< Return \b true if \b this takes a variable number of arguments
|
bool isDotdotdot(void) const { return ((flags&dotdotdot)!=0); } ///< Return \b true if \b this takes a variable number of arguments
|
||||||
void setDotdotdot(bool val) { flags = val ? (flags|dotdotdot) : (flags & ~((uint4)dotdotdot)); } ///< Toggle whether \b this takes variable arguments
|
void setDotdotdot(bool val) { flags = val ? (flags|dotdotdot) : (flags & ~((uint4)dotdotdot)); } ///< Toggle whether \b this takes variable arguments
|
||||||
|
bool isOverride(void) const { return ((flags&is_override)!=0); } ///< Return \b true if \b this is a call site override
|
||||||
|
void setOverride(bool val) { flags = val ? (flags|is_override) : (flags & ~((uint4)is_override)); } ///< Toggle whether \b this is a call site override
|
||||||
uint4 hasEffect(const Address &addr,int4 size) const;
|
uint4 hasEffect(const Address &addr,int4 size) const;
|
||||||
vector<EffectRecord>::const_iterator effectBegin(void) const; ///< Get iterator to front of EffectRecord list
|
vector<EffectRecord>::const_iterator effectBegin(void) const; ///< Get iterator to front of EffectRecord list
|
||||||
vector<EffectRecord>::const_iterator effectEnd(void) const; ///< Get iterator to end of EffectRecord list
|
vector<EffectRecord>::const_iterator effectEnd(void) const; ///< Get iterator to end of EffectRecord list
|
||||||
|
|
|
@ -117,7 +117,8 @@ void Override::insertProtoOverride(const Address &callpoint,FuncProto *p)
|
||||||
if (iter != protoover.end()) // Check for pre-existing override
|
if (iter != protoover.end()) // Check for pre-existing override
|
||||||
delete (*iter).second; // and delete it
|
delete (*iter).second; // and delete it
|
||||||
|
|
||||||
protoover[callpoint] = p;
|
p->setOverride(true); // Mark this as an override
|
||||||
|
protoover[callpoint] = p; // Take ownership of the object
|
||||||
}
|
}
|
||||||
|
|
||||||
/// \brief Flag an indirect jump for multistage analysis
|
/// \brief Flag an indirect jump for multistage analysis
|
||||||
|
|
|
@ -29,6 +29,7 @@ import ghidra.program.model.address.Address;
|
||||||
import ghidra.program.model.data.*;
|
import ghidra.program.model.data.*;
|
||||||
import ghidra.program.model.listing.*;
|
import ghidra.program.model.listing.*;
|
||||||
import ghidra.program.model.pcode.*;
|
import ghidra.program.model.pcode.*;
|
||||||
|
import ghidra.program.model.symbol.Reference;
|
||||||
import ghidra.util.Msg;
|
import ghidra.util.Msg;
|
||||||
import ghidra.util.UndefinedFunction;
|
import ghidra.util.UndefinedFunction;
|
||||||
import ghidra.util.exception.CancelledException;
|
import ghidra.util.exception.CancelledException;
|
||||||
|
@ -140,7 +141,22 @@ public class OverridePrototypeAction extends AbstractDecompilerAction {
|
||||||
}
|
}
|
||||||
Address addr = op.getInput(0).getAddress();
|
Address addr = op.getInput(0).getAddress();
|
||||||
Program program = controller.getProgram();
|
Program program = controller.getProgram();
|
||||||
return program.getFunctionManager().getFunctionAt(addr);
|
FunctionManager functionManager = program.getFunctionManager();
|
||||||
|
Function function = functionManager.getFunctionAt(addr);
|
||||||
|
if (function != null) {
|
||||||
|
return function;
|
||||||
|
}
|
||||||
|
Address opAddr = op.getSeqnum().getTarget();
|
||||||
|
Reference[] references = program.getReferenceManager().getFlowReferencesFrom(opAddr);
|
||||||
|
for (Reference ref : references) {
|
||||||
|
if (ref.getReferenceType().isCall()) {
|
||||||
|
function = functionManager.getFunctionAt(ref.getToAddress());
|
||||||
|
if (function != null) {
|
||||||
|
return function;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
private String generateSignature(PcodeOp op, String name) {
|
private String generateSignature(PcodeOp op, String name) {
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue