SkillAgentSearch skills...

GhidraSnippets

Python snippets for Ghidra's Program and Decompiler APIs

Install / Use

/learn @HackOvert/GhidraSnippets
About this skill

Quality Score

0/100

Supported Platforms

Universal

README

Ghidra Snippets

Ghidra Snippets is a collection of Python examples showing how to work with Ghidra APIs. There are three primary APIs covered here, the [Flat Program API][1], the [Flat Decompiler API][2], and everything else ("Complex API"). The Flat APIs are 'simple' versions of the full fledged Complex Ghidra API. They are a great starting point for anyone looking to develop Ghidra modules and/or scripts.

At some point however, you need to reach outside of the Flat APIs to do really interesting things. Everything here is just a mashup to get the job done. There's more than one way to accomplish each task so make sure you ask yourself if these snippets are really what you need before copy/pasta.

Latest Release & API Docs

  • Loooking for the latest release of Ghidra? [Download it here][0].
  • Loooking for the latest API Docs? In Ghidra's UI, select Help -> Ghidra API Help to unpack the docs and view them.
  • Just want a quick online API reference? Ghidra.re hosts an online version of the API docs (may not be up to date).

Contributing

Feel free to submit pull requests to master on this repo with any modifications you see fit. Most of these snippets are meant to be verbose, but if you know of a better way to do something, please share it via pull request or submitting an issue. Thanks!

Table of Contents

<details> <summary>Working with the Flat APIs</summary> </details> <details> <summary>Working with Projects</summary> </details> <details> <summary>Working with Programs</summary> </details> <details> <summary>Working with Functions</summary> </details> <details> <summary>Working with Basic Blocks</summary> </details> <details> <summary>Working with Instructions</summary> </details> <details> <summary>Working with Variables</summary> </details> <details> <summary>Working with the Decompiler</summary> </details> <details> <summary>Working with Comments</summary> </details> <details> <summary>Working with PCode</summary> </details> <details> <summary>Working with Graphs</summary> </details> <details> <summary>Miscellaneous</summary> </details>

Working with the Flat APIs

As stated in the introduction, the simplest method of using Ghidra's API is via the Flat APIs. As of Ghidra 10.2 this includes FlatProgramAPI, FlatDecompilerAPI, and the most recent FlatDebuggerAPI. The Flat APIs are designed to offer a stable API interface to some of Ghidra's high level functionality. The simplicity and convenience offered by the Flat APIs can be quickly eclipsed by their limited functionality. However, if what you need to do is offered via the Flat APIs, it's highly recommended you use them.

Using the FlatProgramAPI

The FlatProgramAPI is a simple interface to Ghidra's program related functionality. This includes functions, data, instructions, etc.

from ghidra.program.flatapi import FlatProgramAPI

state = getState()
program = state.getCurrentProgram()
fpapi = FlatProgramAPI(program)

for x in dir(fpapi): print(x)
print(fpapi.currentProgram)
print(fpapi.firstFunction)
<details> <summary>Output example</summary>
MAX_REFERENCES_TO
__class__
<...snip...>
addressFactory
analyze
analyzeAll
<...snip...>
currentProgram
disassemble
<...snip...>
findStrings
firstData
firstFunction
firstInstruction
getAddressFactory
getBookmarks
<...snip...>
bug - .ProgramDB
_init
</details>

<br>⬆ Back to top

Using the FlatDecompilerAPI

The FlatDecompilerAPI is a simple interface to Ghidra's decompiler and requires an instance of the FlatProgramAPI for initialization in order to do anything useful. In other words, we need a target program to use the decompiler.

from ghidra.app.decompiler.flatapi import FlatDecompilerAPI
from ghidra.program.flatapi import FlatProgramAPI

fpapi = FlatProgramAPI(getState().getCurrentProgram())
fdapi = FlatDecompilerAPI(fpapi)

for x in dir(fdapi): print(x)

main_decomp = fdapi.decompile(fpapi.getFunction('main'))
print(main_decomp)

<details> <summary>Output example</summary>
<...snip...>
decompile
decompiler
dispose
equals
getClass
getDecompiler
hashCode
initialize
notify
notifyAll
toString
wait

int main(void)

{
  int retVal;
  long in_FS_OFFSET;
  int choice;
  char *local_38 [5];
  long stackCookie;
  
  stackCookie = *(long *)(in_FS_OFFSET + 0x28);
  choice = 0;
  local_38[0] = "My secret";
  local_38[1] = "Red";
  local_38[2] = "Green";
  local_38[3] = "Blue";
  printf("Choice: ");
  __isoc99_fscanf(stdin,"%d",&choice);
  if ((choice == 0) || (3 < choice)) {
    printf("Invalid choice: %d!\n",(ulong)(uint)choice);
    retVal = -1;
  }
  else {
    printf("data[%d]: %s\n",(ulong)(uint)choice,local_38[(int)(char)choice]);
    retVal = 0;
  }
  if (stackCookie != *(long *)(in_FS_OFFSET + 0x28)) {
                    /* WARNING: Subroutine does not return */
    __stack_chk_fail();
  }
  return retVal;
}
</details>

<br>⬆ Back to top

Using the FlatDebuggerAPI

The FlatDebuggerAPI is a simple interface to Ghidra's debugger and trace functionality. This is a new feature as of Ghidra 10.2 and yet to be documented in the Ghidra 10.2 API docs. For some extra context about this API, see DemoDebuggerScript.java. As I learn more about this API I'll update this section.

from ghidra.debug.flatapi import FlatDebuggerAPI

fdapi = FlatDebuggerAPI

for x in dir(fdapi): print(x)
<details> <summary>Output example</summary>
<...snip...>
kill
launch
launchOffers
<...snip...>
writeMemory
writeRegister
</details>

<br>⬆ Back to top

Working with Projects

A Ghidra Project (class [GhidraProject][4]) contains a logical set of program binaries related to a reverse engineering effort. Projects can be shared (collaborative) or non-shared (private). The snippets in this section deal with bulk import and analysis, locating project files on disk, and more.

Get the name and location on disk of the current project

If you're looking to automate analysis using headless scripts you'll likley have to deal with project management. This includes adding binaries to existing projects, cleaning up old projects, or perhaps syncing analysis to shared projects.

state = getState()
project = state.getProject()
program = state.getCurrentProgram()
locator = project.getProjectData().getProjectLocator()
print("type(state):           {}".format(type(state)))
print("type(project):         {}".format(type(project)))
print("type(program):         {}".format(type(program)))
print("type(locator):         {}".format(type(locator)))
print("Project Name:          {}".format(locator.getName()))
print("Files in this project: {}".format(project.getProjectData().getFileCount()))
print("Is a remote project:   {}".format(locator.isTransient()))
print("Project location:      {}".format(locator.getLocation()))
print("Project directory:     {}".format(locator.getProjectDir()))
print("Lock file:             {}".format(locator.getProjectLockFile()))
print("Marker file:           {}".format(locator.getMarkerFile()))
print("Project URL:           {}".format(locator.getURL()))
<details> <summary>Output example</summary>
type(state):           <type 'ghidra.app.script.GhidraState'>
type(project):         <t

Related Skills

View on GitHub
GitHub Stars871
CategoryDevelopment
Updated19d ago
Forks72

Security Score

100/100

Audited on Mar 20, 2026

No findings