Ghidra Decompiler Analysis Engine
Classes | Public Types | Public Member Functions | List of all members
FlowInfo Class Reference

A class for generating the control-flow structure for a single function. More...

#include <flow.hh>

Public Types

enum  {
  ignore_outofbounds = 1, ignore_unimplemented = 2, error_outofbounds = 4, error_unimplemented = 8,
  error_reinterpreted = 0x10, error_toomanyinstructions = 0x20, unimplemented_present = 0x40, baddata_present = 0x80,
  outofbounds_present = 0x100, reinterpreted_present = 0x200, toomanyinstructions_present = 0x400, possible_unreachable = 0x1000,
  flow_forinline = 0x2000, record_jumploads = 0x4000
}
 

Public Member Functions

 FlowInfo (Funcdata &d, PcodeOpBank &o, BlockGraph &b, vector< FuncCallSpecs * > &q)
 Constructor. More...
 
 FlowInfo (Funcdata &d, PcodeOpBank &o, BlockGraph &b, vector< FuncCallSpecs * > &q, const FlowInfo *op2)
 Cloning constructor. More...
 
PcodeOptarget (const Address &addr) const
 Return first p-code op for instruction at given address. More...
 
PcodeOpbranchTarget (PcodeOp *op) const
 Find the target referred to by a given BRANCH or CBRANCH. More...
 
void generateOps (void)
 Generate raw control-flow from the function's base address.
 
void generateBlocks (void)
 Generate basic blocks from the raw control-flow.
 
bool testHardInlineRestrictions (Funcdata *inlinefd, PcodeOp *op, Address &retaddr)
 For in-lining using the hard model, make sure some restrictions are met. More...
 
bool checkEZModel (void) const
 Check if this flow matches the EX in-lining model. More...
 
void injectPcode (void)
 Perform substitution on any op that requires injection. More...
 
void forwardRecursion (const FlowInfo &op2)
 Pull in-lining recursion information from another flow. More...
 
void inlineClone (const FlowInfo &inlineflow, const Address &retaddr)
 Clone the given in-line flow into this flow using the hard model. More...
 
void inlineEZClone (const FlowInfo &inlineflow, const Address &calladdr)
 Clone the given in-line flow into this flow using the EZ model. More...
 

Detailed Description

A class for generating the control-flow structure for a single function.

Control-flow for the function is generated in two phases: the method generateOps() produces all the raw p-code ops for the function, and the method generateBlocks() organizes the p-code ops into basic blocks (PcodeBlockBasic). In generateOps(), p-code is generated for every machine instruction that is reachable starting with the entry point address of the function. All possible flow is followed, trimming flow at instructions that end with the formal RETURN p-code operation. CALL and CALLIND are treated as fall-through operations, and flow is not followed into the sub-function.

The class supports various options for handling corner cases during the flow following process, including how to handle:

In generateBlocks(), all previously generated PcodeOp instructions are assigned to a PcodeBlockBasic. These objects define the formal basic block structure of the function. Directed control-flow edges between the blocks are created at this time based on the flow of p-code.

A Funcdata object provided to the constructor holds:

The Translate object (provided by the Architecture owning the function) generates the raw p-code ops for a single instruction. This FlowInfo class also handles p-code injection triggers encountered during flow following, primarily using the architecture's PcodeInjectLibrary to resolve them.

Member Enumeration Documentation

◆ anonymous enum

anonymous enum
Enumerator
ignore_outofbounds 

Ignore/truncate flow into addresses out of the specified range.

ignore_unimplemented 

Treat unimplemented instructions as a NOP (no operation)

error_outofbounds 

Throw an exception for flow into addresses out of the specified range.

error_unimplemented 

Throw an exception for flow into unimplemented instructions.

error_reinterpreted 

Throw an exception for flow into previously encountered data at a difference cut.

error_toomanyinstructions 

Throw an exception if too many instructions are encountered.

unimplemented_present 

Indicate we have encountered unimplemented instructions.

baddata_present 

Indicate we have encountered flow into unaccessible data.

outofbounds_present 

Indicate we have encountered flow out of the specified range.

reinterpreted_present 

Indicate we have encountered reinterpreted data.

toomanyinstructions_present 

Indicate the maximum instruction threshold was reached.

possible_unreachable 

Indicate a CALL was converted to a BRANCH and some code may be unreachable.

flow_forinline 

Indicate flow is being generated to in-line (a function)

record_jumploads 

Indicate that any jump table recovery should record the table structure.

Constructor & Destructor Documentation

◆ FlowInfo() [1/2]

FlowInfo::FlowInfo ( Funcdata d,
PcodeOpBank o,
BlockGraph b,
vector< FuncCallSpecs * > &  q 
)

Constructor.

Prepare for tracing flow for a new function. The Funcdata object and references to its internal containers must be explicitly given.

Parameters
dis the new function to trace
ois the internal p-code container for the function
bis the internal basic block container
qis the internal container of call sites

◆ FlowInfo() [2/2]

FlowInfo::FlowInfo ( Funcdata d,
PcodeOpBank o,
BlockGraph b,
vector< FuncCallSpecs * > &  q,
const FlowInfo op2 
)

Cloning constructor.

Prepare a new flow cloned from an existing flow. Configuration from the existing flow is copied, but the actual PcodeOps must already be cloned within the new function.

Parameters
dis the new function that has been cloned
ois the internal p-code container for the function
bis the internal basic block container
qis the internal container of call sites
op2is the existing flow

Member Function Documentation

◆ branchTarget()

PcodeOp * FlowInfo::branchTarget ( PcodeOp op) const

Find the target referred to by a given BRANCH or CBRANCH.

The code reference passed as the first parameter to the branch is examined, and the p-code op it refers to is returned. The reference may be a normal direct address or a relative offset. If no target p-code can be found, an exception is thrown.

Parameters
opis the given branch op
Returns
the targetted p-code op

◆ checkEZModel()

bool FlowInfo::checkEZModel ( void  ) const

Check if this flow matches the EX in-lining model.

A function is in the EZ model if it is a straight-line leaf function.

Returns
true if this flow contains no CALL or BRANCH ops

◆ forwardRecursion()

void FlowInfo::forwardRecursion ( const FlowInfo op2)

Pull in-lining recursion information from another flow.

When preparing p-code for an in-lined function, the generation process needs to be informed of in-lining that has already been performed. This method copies the in-lining information from the parent flow, prior to p-code generation.

Parameters
op2is the parent flow

◆ injectPcode()

void FlowInfo::injectPcode ( void  )

Perform substitution on any op that requires injection.

Types of substitution include:

  • Sub-function in-lining
  • Sub-function injection
  • User defined op injection

Make sure to truncate recursion, and otherwise don't allow a sub-function to be in-lined more than once.

◆ inlineClone()

void FlowInfo::inlineClone ( const FlowInfo inlineflow,
const Address retaddr 
)

Clone the given in-line flow into this flow using the hard model.

Individual PcodeOps from the Funcdata being in-lined are cloned into the Funcdata for this flow, preserving their original address. Any RETURN op is replaced with jump to first address following the call site.

Parameters
inlineflowis the given in-line flow to clone
retaddris the first address after the call site in this flow

◆ inlineEZClone()

void FlowInfo::inlineEZClone ( const FlowInfo inlineflow,
const Address calladdr 
)

Clone the given in-line flow into this flow using the EZ model.

Individual PcodeOps from the Funcdata being in-lined are cloned into the Funcdata for this flow but are reassigned a new fixed address, and the RETURN op is eliminated.

Parameters
inlineflowis the given in-line flow to clone
calladdris the fixed address assigned to the cloned PcodeOps

◆ target()

PcodeOp * FlowInfo::target ( const Address addr) const

Return first p-code op for instruction at given address.

The first p-code op associated with the machine instruction at the given address is returned. If the instruction generated no p-code, an attempt is made to fall-thru to the next instruction. If no p-code op is ultimately found, an exception is thrown.

Parameters
addris the given address of the instruction
Returns
the targetted p-code op

◆ testHardInlineRestrictions()

bool FlowInfo::testHardInlineRestrictions ( Funcdata inlinefd,
PcodeOp op,
Address retaddr 
)

For in-lining using the hard model, make sure some restrictions are met.

  • Can only in-line the function once.
  • There must be a p-code op to return to.
  • There must be a distinct return address, so that the RETURN can be replaced with a BRANCH.

Pass back the distinct return address, unless the in-lined function doesn't return.

Parameters
inlinefdis the function being in-lined into this flow
opis CALL instruction at the site of the in-line
retaddrholds the passed back return address
Returns
true if all the hard model restrictions are met

The documentation for this class was generated from the following files: