forked from Lephenixnoir/fxos
52 lines
1.9 KiB
C++
52 lines
1.9 KiB
C++
//---
|
|
// fxos.disasm-passes.cfg: Control Flow Graph construction
|
|
//
|
|
// This pass explores functions and computes the [jmptarget] field of concrete
|
|
// instructions as it goes. This is required for other passes that work by
|
|
// traversing the CFG, such as the abstract interpretor.
|
|
//
|
|
// This is the main exploration pass. Other passes do not typically load new
|
|
// instructions from the underlying disassembly. Straightforward passes such as
|
|
// [print] iterate on instructions loaded by this pass.
|
|
//
|
|
// The main gimmick of this pass is to "resolve delay slots" by forcing down
|
|
// the properties of delayed instructions into their respective delay slots.
|
|
// For instance, in
|
|
// jmp @r0
|
|
// mov #1, r4
|
|
// the jump is delayed until after the move. To handle this, fxos makes the jmp
|
|
// a no-op and applies dual move-jump semantics to the mov below it.
|
|
//
|
|
// This could be tricky for the abstract interpreter because the jump target
|
|
// has to be computed with the environment before the jmp, which is not
|
|
// available when considering the mov. Luckily all delayed jumps are state
|
|
// no-ops so the state before the mov can be used instead.
|
|
//
|
|
// Note that jumping into a delay slot will activate the jump in fxos, which is
|
|
// not the actual behavior of the processor. fxos usually complains about the
|
|
// crazy compiler when this occurs. Note that if it happens but we don't know
|
|
// that it's a delay slot (ie. the instruction from above is never executed in
|
|
// the current function), then everything's fine.
|
|
//
|
|
// Take-home message: delay slots are a pain to analyze, so we get rid of them
|
|
// as soon as possible and proceed with normal semantics.
|
|
//---
|
|
|
|
#ifndef LIBFXOS_DISASM_PASSES_CFG_H
|
|
#define LIBFXOS_DISASM_PASSES_CFG_H
|
|
|
|
#include <fxos/disassembly.h>
|
|
|
|
namespace FxOS {
|
|
|
|
class CfgPass: public DisassemblyPass
|
|
{
|
|
public:
|
|
CfgPass(Disassembly &disasm);
|
|
bool analyze(uint32_t pc, ConcreteInstruction &inst) override;
|
|
};
|
|
|
|
} /* namespace FxOS */
|
|
|
|
#endif /* LIBFXOS_DISASM_PASSES_CFG_H */
|