# Lib.CFG module

Classes for a RiscV CFG: `CFG` for the CFG itself, and `Block` for its basic blocks.

class Lib.CFG.Block(label: Label, insts: List[ Lib.Statement.Instru3A | Lib.Statement.Comment ], terminator: Lib.Terminator.Return | Lib.Statement.AbsoluteJump | Lib.Terminator.BranchingTerminator )

  Bases: `object`

  A basic block of a `CFG` is made of three main parts:

  - a start `label` that uniquely identifies the block in the CFG

  - the main body of the block, a list of instructions (excluding labels, jumps and branching instructions)

  - a `terminator` that represents the final jump or branching instruction of the block, and points to the successors of the block. See the documentation for `Lib.Terminator.Terminator` for further explanations.

  to_dot() → str

    Outputs all statements of the block as a string.

  get_body() → List[ Lib.Statement.Instru3A | Lib.Statement.Comment ]

    Return the statements in the body of the block (no phi-node nor the terminator).

  get_all_statements() → List[ Statement ]

    Return all statements of the block (including phi-nodes and the terminator, but not the label of the block).

  get_body_and_terminator() → List[ Statement ]

    Return all statements of the block, except phi-nodes (and the label of the block).

  get_label() → Label

    Return the label of the block.

  get_in() → List[ Block ]

    Return the list of blocks with an edge to the considered block.

  get_terminator() → Lib.Terminator.Return | Lib.Statement.AbsoluteJump | Lib.Terminator.BranchingTerminator

    Return the terminator of the block.

  set_terminator(term: Lib.Terminator.Return | Lib.Statement.AbsoluteJump | Lib.Terminator.BranchingTerminator ) → None

    Set the terminator of the block.

  iter_statements(f) → None

    Iterate over instructions. For each real instruction i (not label or comment), replace it with the list of instructions given by f(i).

    Assume there is no phi-node.

  add_instruction(instr: Lib.Statement.Instru3A | Lib.Statement.Comment ) → None

    Add an instruction to the body of the block.

class Lib.CFG.CFG(fdata: FunctionData )

  Bases: `object`

  A complete control-flow graph representing a function. This class is mainly made of a list of basic `Block`, a label indicating the `entry point of the function`, and an `exit label`.

  As with linear code, metadata about the function can be found in the `fdata` member variable.

  fdata: FunctionData

    Metadata about the function represented by this CFG

  get_start() → Label

    Return the entry label of the CFG.

  set_start(start: Label ) → None

    Set the entry label of the CFG.

  get_end() → Label

    Return the exit label of the CFG.

  add_block(blk: Block ) → None

    Add a new block to the CFG.

  get_block(name: Label ) → Block

    Return the block with label name.

  get_blocks() → List[ Block ]

    Return all the blocks.

  get_entries() → List[ Block ]

    Return all the blocks with no predecessors.

  add_edge(src: Block, dest: Block ) → None

    Add the edge src -> dest in the control flow graph.

  remove_edge(src: Block, dest: Block ) → None

    Remove the edge src -> dest in the control flow graph.

  out_blocks(block: Block ) → List[ Block ]

    Return the list of blocks in the CFG targeted by the Terminator of Block block.

  gather_defs() → Dict[Any, Set[ Block ]]

    Return a dictionary associating variables to all the blocks containing one of their definitions.

  iter_statements(f) → None

    Apply f to all instructions in all the blocks.

  linearize_naive() → Iterator[ Statement ]

    Linearize the given control flow graph as a list of instructions. Naive procedure that adds jumps everywhere.

  print_code(output, linearize=<function CFG.<lambda>>, comment=None) → None

    Print the linearization of the CFG.

  print_dot(filename, DF=None, view=False) → None

    Print the CFG as a graph.