<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
  <channel>
    <title>Spinsel</title>
    <description>Blog about computers, science and math</description>
    <link>https://spinsel.dev/</link>
    <atom:link href="https://spinsel.dev/feed.xml" rel="self" type="application/rss+xml"/>
    <pubDate>Sat, 03 Apr 2021 13:04:06 +0000</pubDate>
    <lastBuildDate>Sat, 03 Apr 2021 13:04:06 +0000</lastBuildDate>
    <generator>Jekyll v3.9.0</generator>
    
      <item>
        <title>Debugging Ghidra and its decompiler</title>
        <description>&lt;p&gt;Recently, I came across an oddity in the Ghidra decompiler that I wanted to debug.
The decompiler is a native C++ application that runs separate from Ghidra itself (the Java application).
Whenever Ghidra needs to decompile a function, display a function graph, etc., Ghidra launches the decompiler and delegates that task to it.&lt;/p&gt;

&lt;p&gt;Debugging the decompiler when it’s running standalone is as simple as running &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;gdb path_to_repo/Ghidra/Features/Decompiler/build/os/linux64/decompile&lt;/code&gt;.
In my case, however, I wanted to debug the decompiler when it’s instantiated by Ghidra.
It’s not so straightforward to just attach a debugger to a running decompiler process, since it would require you to launch the debugger at the same time as the decompiler is launched.
If you write a script that waits until a decompiler process is created and then attaches to it, you’ll likely run into timing issues.&lt;/p&gt;

&lt;p&gt;In this post, I’ll explain how to properly debug Ghidra’s decompiler.
Since it’s easy to debug Ghidra itself using the development environment we’ll have to set up for the decompiler, I’ll cover that too.
The commands and code in this post should work for a Debian-based distro, but the same can be achieved on any (not-too-exotic) operating system.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;NB: there’s already &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/issues/720&quot;&gt;some basic functionality built into Ghidra&lt;/a&gt; that allows for inspecting the global state of the decompiler, but it’s not (intended to be) a full-fledged debugger.&lt;/em&gt;&lt;/p&gt;

&lt;h1 id=&quot;setting-things-up&quot;&gt;Setting things up&lt;/h1&gt;
&lt;p&gt;The &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/master/DevGuide.md&quot;&gt;&lt;em&gt;Developer’s Guide&lt;/em&gt;&lt;/a&gt; that comes with Ghidra explains how to set up a Ghidra development environment.
A short summary is given here, but be sure to read the official guide if you want to customize the installation.&lt;/p&gt;

&lt;p&gt;First, install some basic prerequisites:&lt;/p&gt;
&lt;div class=&quot;language-bash highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nb&quot;&gt;sudo &lt;/span&gt;apt update &lt;span class=&quot;o&quot;&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;sudo &lt;/span&gt;apt upgrade &lt;span class=&quot;nt&quot;&gt;-y&lt;/span&gt;
&lt;span class=&quot;nb&quot;&gt;sudo &lt;/span&gt;apt &lt;span class=&quot;nb&quot;&gt;install&lt;/span&gt; &lt;span class=&quot;nt&quot;&gt;-y&lt;/span&gt; build-essential git wget unzip
&lt;span class=&quot;nb&quot;&gt;sudo &lt;/span&gt;apt &lt;span class=&quot;nb&quot;&gt;install&lt;/span&gt; &lt;span class=&quot;nt&quot;&gt;-y&lt;/span&gt; default-jre default-jdk
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Install &lt;a href=&quot;https://gradle.org/install/&quot;&gt;Gradle&lt;/a&gt;, if it’s not already on your system:&lt;/p&gt;
&lt;div class=&quot;language-bash highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;wget &lt;span class=&quot;nt&quot;&gt;-P&lt;/span&gt; /tmp/ https://services.gradle.org/distributions/gradle-6.8.3-bin.zip
unzip &lt;span class=&quot;nt&quot;&gt;-d&lt;/span&gt; /opt/gradle /tmp/gradle-6.8.3-bin.zip
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Add Gradle to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;PATH&lt;/code&gt; by appending the following code to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;~/.bashrc&lt;/code&gt;:&lt;/p&gt;
&lt;div class=&quot;language-bash highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nb&quot;&gt;export &lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;GRADLE_HOME&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;=&lt;/span&gt;/opt/gradle/gradle-6.8.3
&lt;span class=&quot;nb&quot;&gt;export &lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;PATH&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;=&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;$GRADLE_HOME&lt;/span&gt;/bin:&lt;span class=&quot;nv&quot;&gt;$PATH&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;
&lt;p&gt;Run &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;source ~/.bashrc&lt;/code&gt; to apply these changes.&lt;/p&gt;

&lt;p&gt;Build Ghidra and set up the development environment (this may take some time, so relax and grab a cup of coffee in the meantime):&lt;/p&gt;
&lt;div class=&quot;language-bash highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;git clone https://github.com/NationalSecurityAgency/ghidra.git
gradle &lt;span class=&quot;nt&quot;&gt;--init-script&lt;/span&gt; gradle/support/fetchDependencies.gradle init
gradle buildGhidra
gradle prepDev
gradle eclipse
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;You’ll also probably want to install Eclipse to run and debug Ghidra.
Eclipse can be downloaded &lt;a href=&quot;https://www.eclipse.org/downloads/&quot;&gt;here&lt;/a&gt;.&lt;/p&gt;

&lt;h1 id=&quot;debugging-ghidra&quot;&gt;Debugging Ghidra&lt;/h1&gt;
&lt;p&gt;If you’ve followed the steps above or the &lt;em&gt;Developer’s Guide&lt;/em&gt;, debugging Ghidra will be a breeze.
First, we’ll open the Ghidra project in Eclipse:&lt;/p&gt;
&lt;ol&gt;
  &lt;li&gt;In Eclipse, click &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;File → Import...&lt;/code&gt;.&lt;/li&gt;
  &lt;li&gt;Select &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;General → Existing Projects into Workspace&lt;/code&gt;.&lt;/li&gt;
  &lt;li&gt;Choose the Ghidra repository as root directory.&lt;/li&gt;
  &lt;li&gt;Mark &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Search for nested projects&lt;/code&gt; and click &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Select all&lt;/code&gt;.&lt;/li&gt;
  &lt;li&gt;Click &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Finish&lt;/code&gt;.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;To debug Ghidra for the first time, go to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Debug → Debug configurations...&lt;/code&gt; in the menu bar, select &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Java Application → Ghidra&lt;/code&gt; and hit &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Debug&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2021-04-02-ghidra-decompiler-debugging/images/debug_config.png&quot; alt=&quot;Debug configuration menu&quot; /&gt;&lt;/p&gt;

&lt;p&gt;The next time you want to debug Ghidra, you can just press the debug button in the toolbar.&lt;/p&gt;

&lt;p&gt;Eclipse now allows you to set breakpoints, step through code, inspect and modify variables etc. for the Ghidra application.&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2021-04-02-ghidra-decompiler-debugging/images/eclipse.png&quot; alt=&quot;Eclipse debug perspective&quot; /&gt;&lt;/p&gt;

&lt;h1 id=&quot;debugging-the-decompiler&quot;&gt;Debugging the decompiler&lt;/h1&gt;
&lt;p&gt;The approach to debug the decompiler is as follows:&lt;/p&gt;
&lt;ul&gt;
  &lt;li&gt;We’ll add a boolean &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;debugger_present&lt;/code&gt; to the decompiler, which is initially &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;false&lt;/code&gt;.&lt;/li&gt;
  &lt;li&gt;Before executing the rest of the program, the decompiler will loop until &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;debugger_present&lt;/code&gt; is &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;true&lt;/code&gt;.&lt;/li&gt;
  &lt;li&gt;The debugger attaches to the running decompiler process, sets &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;debugger_present&lt;/code&gt; to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;true&lt;/code&gt; and optionally configures some breakpoints.
After that, the normal execution flow continues.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;We add the following code to &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/472ad40077e598dfe01f65afcd0e8c3fd81c060b/Ghidra/Features/Decompiler/src/decompile/cpp/ghidra_process.cc&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Ghidra/Features/Decompiler/src/decompile/cpp/ghidra_process.cc&lt;/code&gt;&lt;/a&gt;&lt;sup id=&quot;fnref:volatile&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:volatile&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;1&lt;/a&gt;&lt;/sup&gt;:&lt;/p&gt;
&lt;div class=&quot;language-cpp highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;cp&quot;&gt;#include &amp;lt;thread&amp;gt;
#include &amp;lt;chrono&amp;gt;
&lt;/span&gt;
&lt;span class=&quot;k&quot;&gt;volatile&lt;/span&gt; &lt;span class=&quot;kt&quot;&gt;bool&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;debugger_present&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;false&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;
&lt;span class=&quot;kt&quot;&gt;void&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;wait_for_debugger&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;()&lt;/span&gt; &lt;span class=&quot;p&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;while&lt;/span&gt; &lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;!&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;debugger_present&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt;
        &lt;span class=&quot;n&quot;&gt;std&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;::&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;this_thread&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;::&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;sleep_for&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;std&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;::&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;chrono&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;::&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;milliseconds&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;mi&quot;&gt;500&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;));&lt;/span&gt;
&lt;span class=&quot;p&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;In this same file, insert a call to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;wait_for_debugger&lt;/code&gt; in the &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/472ad40077e598dfe01f65afcd0e8c3fd81c060b/Ghidra/Features/Decompiler/src/decompile/cpp/ghidra_process.cc#L509&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;main&lt;/code&gt;&lt;/a&gt; function, which is the entry point of the decompiler:&lt;/p&gt;
&lt;div class=&quot;language-cpp highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kt&quot;&gt;int&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;main&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;int&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;argc&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;,&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;char&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;**&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;argv&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt;

&lt;span class=&quot;p&quot;&gt;{&lt;/span&gt;
  &lt;span class=&quot;n&quot;&gt;wait_for_debugger&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;();&lt;/span&gt;
  &lt;span class=&quot;p&quot;&gt;...&lt;/span&gt;
&lt;span class=&quot;p&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;We also need to build the decompiler with debug flags and no optimization flags.
This can be done by commenting/uncommenting the appropriate lines for your compiler in &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/472ad40077e598dfe01f65afcd0e8c3fd81c060b/Ghidra/Features/Decompiler/build.gradle#L537-L568&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Ghidra/Features/Decompiler/build.gradle#L537-L568&lt;/code&gt;&lt;/a&gt;.
In my case (gcc) I had to change lines 537-538 from&lt;/p&gt;
&lt;div class=&quot;language-groovy highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;n&quot;&gt;b&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;cppCompiler&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;args&lt;/span&gt; &lt;span class=&quot;s2&quot;&gt;&quot;-O2&quot;&lt;/span&gt;    &lt;span class=&quot;c1&quot;&gt;// for DEBUG, comment this line out&lt;/span&gt;
&lt;span class=&quot;c1&quot;&gt;//b.cppCompiler.args &quot;-g&quot;   // for DEBUG, uncomment this line&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;
&lt;p&gt;to&lt;/p&gt;
&lt;div class=&quot;language-groovy highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;c1&quot;&gt;//b.cppCompiler.args &quot;-O2&quot;  // for DEBUG, comment this line out&lt;/span&gt;
&lt;span class=&quot;n&quot;&gt;b&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;cppCompiler&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;args&lt;/span&gt; &lt;span class=&quot;s2&quot;&gt;&quot;-g&quot;&lt;/span&gt;     &lt;span class=&quot;c1&quot;&gt;// for DEBUG, uncomment this line&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Now we need to recompile the project.
Since we’ve only modified the decompiler code, only this part of the project will be rebuilt.&lt;/p&gt;
&lt;div class=&quot;language-bash highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;gradle buildGhidra
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;To test this approach, open an arbitrary executable in Ghidra and try to decompile any function.
The decompiler should now hang forever because it’s waiting for &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;debugger_present&lt;/code&gt; to be &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;true&lt;/code&gt;!&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2021-04-02-ghidra-decompiler-debugging/images/decompiler_hang.png&quot; alt=&quot;The decompiler window showing an indeterminate progress bar&quot; title=&quot;This may take a minute... 😉&quot; /&gt;&lt;/p&gt;

&lt;p&gt;We use &lt;a href=&quot;https://linux.die.net/man/1/pgrep&quot;&gt;pgrep&lt;/a&gt; to find the decompiler process and attach to it using gdb:&lt;/p&gt;
&lt;div class=&quot;language-bash highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;pgrep &lt;span class=&quot;nt&quot;&gt;-fn&lt;/span&gt; decomp
4367

&lt;span class=&quot;nb&quot;&gt;sudo &lt;/span&gt;gdb &lt;span class=&quot;nt&quot;&gt;-q&lt;/span&gt; path_to_repo/Ghidra/Features/Decompiler/build/os/linux64/decompile 4367
Reading symbols from path_to_repo/Ghidra/Features/Decompiler/build/os/linux64/decompile...
Attaching to program: path_to_repo/Ghidra/Features/Decompiler/build/os/linux64/decompile, process 4367
...
&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;gdb&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;set &lt;/span&gt;debugger_present &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; 1
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Even after setting &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;debugger_present&lt;/code&gt; to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;true&lt;/code&gt;, gdb keeps halting the program until we enter &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;c&lt;/code&gt; or &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;continue&lt;/code&gt;.
Before doing that, we’ll set a breakpoint at &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/472ad40077e598dfe01f65afcd0e8c3fd81c060b/Ghidra/Features/Decompiler/src/decompile/cpp/ghidra_process.cc#L497&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;GhidraDecompCapability::initialize&lt;/code&gt;&lt;/a&gt;:&lt;/p&gt;

&lt;div class=&quot;language-bash highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;gdb&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; b GhidraDecompCapability::initialize
Breakpoint 1 at 0x55b6d48e5f56: file path_to_repo/Ghidra/Features/Decompiler/src/decompile/cpp/ghidra_process.cc, line 499.
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;If we type &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;c&lt;/code&gt; to continue the program, it’ll hit the breakpoint we’ve just set.
We can now inspect and modify memory and then resume the program:&lt;/p&gt;
&lt;div class=&quot;language-bash highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;gdb&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; c
Continuing.

Breakpoint 1, GhidraDecompCapability::initialize &lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;this&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;=&lt;/span&gt;0x558714894618 &amp;lt;std::vector&amp;lt;PrintLanguageCapability&lt;span class=&quot;k&quot;&gt;*&lt;/span&gt;, std::allocator&amp;lt;PrintLanguageCapability&lt;span class=&quot;k&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;gt;&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;&amp;gt;&lt;/span&gt;::push_back&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;PrintLanguageCapability&lt;span class=&quot;k&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;amp;&amp;amp;)&lt;/span&gt;+50&amp;gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt;
    at path_to_repo/Ghidra/Features/Decompiler/src/decompile/cpp/ghidra_process.cc:499
&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;gdb&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; p commandmap
&lt;span class=&quot;nv&quot;&gt;$1&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; std::map with 0 elements
&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;gdb&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; c
Continuing.
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The decompile window in Ghidra should now show the decompilation results.&lt;/p&gt;

&lt;p&gt;We can automate this process using two scripts that we’ll call &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;gdb_init&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;debug.sh&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;gdb_init&lt;/code&gt; is a &lt;a href=&quot;https://sourceware.org/gdb/current/onlinedocs/gdb/Command-Files.html#Command-Files&quot;&gt;gdb command file&lt;/a&gt; we’ll pass to gdb using the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;-x&lt;/code&gt; flag.
It contains the commands to be run after attaching to the decompiler.&lt;/p&gt;

&lt;p&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;gdb_init&lt;/code&gt;:&lt;/p&gt;
&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;set debugger_present = 1

b GhidraDecompCapability::initialize

# uncomment the next line if you want to automatically continue the program
#c
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;debug.sh&lt;/code&gt; looks for the decompiler process and (if found) attaches to it.
It passes the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;gdb_init&lt;/code&gt; command file to gdb.&lt;/p&gt;

&lt;p&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;debug.sh&lt;/code&gt;:&lt;/p&gt;
&lt;div class=&quot;language-bash highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;c&quot;&gt;#!/bin/bash&lt;/span&gt;

&lt;span class=&quot;nv&quot;&gt;decompiler_path&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;=&lt;/span&gt;path_to_repo/Ghidra/Features/Decompiler/build/os/linux64/decompile

&lt;span class=&quot;nv&quot;&gt;pid&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;=&lt;/span&gt;&lt;span class=&quot;si&quot;&gt;$(&lt;/span&gt;pgrep &lt;span class=&quot;nt&quot;&gt;-fn&lt;/span&gt; &lt;span class=&quot;s2&quot;&gt;&quot;&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;$decompiler_path&lt;/span&gt;&lt;span class=&quot;s2&quot;&gt;&quot;&lt;/span&gt;&lt;span class=&quot;si&quot;&gt;)&lt;/span&gt;
&lt;span class=&quot;k&quot;&gt;if&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;[&lt;/span&gt; &lt;span class=&quot;nt&quot;&gt;-z&lt;/span&gt; &lt;span class=&quot;nv&quot;&gt;$pid&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;]&lt;/span&gt;
&lt;span class=&quot;k&quot;&gt;then
    &lt;/span&gt;&lt;span class=&quot;nb&quot;&gt;echo&lt;/span&gt; &lt;span class=&quot;s2&quot;&gt;&quot;No decompiler process found&quot;&lt;/span&gt;
    &lt;span class=&quot;nb&quot;&gt;exit &lt;/span&gt;1
&lt;span class=&quot;k&quot;&gt;fi

&lt;/span&gt;&lt;span class=&quot;nb&quot;&gt;echo&lt;/span&gt; &lt;span class=&quot;s2&quot;&gt;&quot;Attaching to decompiler process with pid &lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;$pid&lt;/span&gt;&lt;span class=&quot;s2&quot;&gt;&quot;&lt;/span&gt;
gdb &lt;span class=&quot;nt&quot;&gt;-q&lt;/span&gt; &lt;span class=&quot;nt&quot;&gt;-x&lt;/span&gt; gdb_init &lt;span class=&quot;s2&quot;&gt;&quot;&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;$decompiler_path&lt;/span&gt;&lt;span class=&quot;s2&quot;&gt;&quot;&lt;/span&gt; &lt;span class=&quot;nv&quot;&gt;$pid&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;This script can be invoked using &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;sudo ./debug.sh&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Pro-tip: if you want to debug the decompiler, it’s a good idea to read the decompiler documentation.
This documentation isn’t built by default, but you can build it by installing doxygen and running &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;make doc&lt;/code&gt; in &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Ghidra/Features/Decompiler/src/decompile/cpp&lt;/code&gt;.
The documentation will be written to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Ghidra/Features/Decompiler/src/decompile/doc&lt;/code&gt;.&lt;/p&gt;

&lt;h1 id=&quot;conclusion&quot;&gt;Conclusion&lt;/h1&gt;
&lt;p&gt;In this post we’ve looked at &lt;em&gt;one&lt;/em&gt; possible way of debugging a decompiler process created by Ghidra.
I’m sure there are many other ways to do this, but – after modifying the source code – this method is easy and works reliably.
A possible improvement to this method would be to only wait for &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;debugger_present&lt;/code&gt; to be set to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;true&lt;/code&gt; if an environment variable such as &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;GHIDRA_DECOMPILER_DEBUG&lt;/code&gt; is set to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;true&lt;/code&gt;.
That way you can conveniently disable the debugging functionality altogether using one simple command.
If you’ve got an alternative method, let me know!&lt;/p&gt;

&lt;p&gt;Happy debugging!&lt;/p&gt;

&lt;h1 id=&quot;footnotes&quot;&gt;Footnotes&lt;/h1&gt;

&lt;div class=&quot;footnotes&quot; role=&quot;doc-endnotes&quot;&gt;
  &lt;ol&gt;
    &lt;li id=&quot;fn:volatile&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;In the original version of this post, I forgot to mark &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;debugger_present&lt;/code&gt; as &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;volatile&lt;/code&gt;. While it seems to work fine with gcc, it’s better to mark it as &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;volatile&lt;/code&gt; to ensure the compiler doesn’t optimize &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;debugger_present&lt;/code&gt; away. Thanks to &lt;a href=&quot;https://www.reddit.com/user/pelrun/&quot;&gt;pelrun&lt;/a&gt; for pointing this out! &lt;a href=&quot;#fnref:volatile&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
  &lt;/ol&gt;
&lt;/div&gt;
</description>
        <pubDate>Fri, 02 Apr 2021 00:00:00 +0000</pubDate>
        <link>https://spinsel.dev/2021/04/02/ghidra-decompiler-debugging.html</link>
        <guid isPermaLink="true">https://spinsel.dev/2021/04/02/ghidra-decompiler-debugging.html</guid>
        
        <category>Ghidra</category>
        
        
      </item>
    
      <item>
        <title>Implementing a brainfuck CPU in Ghidra - part 4: Renaming the analyzer and adding a manual</title>
        <description>&lt;div class=&quot;blog-post-series-block&quot;&gt;This blog post is part of the series &lt;i&gt;Implementing a brainfuck CPU in Ghidra&lt;/i&gt;:

    &lt;ol&gt;&lt;li&gt;&lt;a href=&quot;/2020/06/17/ghidra-brainfuck-processor-1.html&quot;&gt; Setup and disassembly&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href=&quot;/2020/06/17/ghidra-brainfuck-processor-2.html&quot;&gt; Decompilation of pointer and arithmetic instructions&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href=&quot;/2020/06/17/ghidra-brainfuck-processor-3.html&quot;&gt; Decompilation of I/O and control flow instructions&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;b&gt; Renaming the analyzer and adding a manual (current post)&lt;/b&gt;&lt;/li&gt;&lt;li&gt;Recognizing common patterns (future post)&lt;/li&gt;&lt;/ol&gt;&lt;p&gt;More posts may be added to this series in the future.&lt;/p&gt;&lt;/div&gt;
&lt;p&gt;Now that our processor module can finally disassemble and decompile brainfuck binaries, we can make some slight improvements to the module. We’ll do two things in this blogpost: first we’ll rename the analyzer and then we add a processor manual&lt;/p&gt;

&lt;h1 id=&quot;renaming-the-analyzer&quot;&gt;Renaming the analyzer&lt;/h1&gt;
&lt;p&gt;Right now, the analyzer that resolves branch destinations is called &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BrainfuckAnalyzer.java&lt;/code&gt;. This name doesn’t really make it clear what it does. Maybe &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BranchDestinationResolver.java&lt;/code&gt; would be a better name, as it’s more descriptive.&lt;/p&gt;

&lt;p&gt;This sounds easy, right? Just right click &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BrainfuckAnalyzer.java&lt;/code&gt; and rename it to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BrainfuckAnalyzer.java&lt;/code&gt;. Don’t forget to also rename the class and constructor to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BranchDestinationResolver&lt;/code&gt;. But, it’s not &lt;em&gt;that&lt;/em&gt; easy or I wouldn’t have devoted half a blog post to it :)&lt;/p&gt;

&lt;p&gt;If we now restart Ghidra, the analyzer has disappeared from analysis window. There’s no &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BranchDestinationResolver&lt;/code&gt; or &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BrainfuckAnalyzer&lt;/code&gt; in the list. What happened?&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-07-27-ghidra-brainfuck-processor-4/images/analysis_options.png&quot; alt=&quot;Analysis window&quot; title=&quot;It's gone :(&quot; /&gt;&lt;/p&gt;

&lt;p&gt;As it turns out, Ghidra only shows analyzers that are valid extension points. An &lt;strong&gt;extension point&lt;/strong&gt; is a class that extends the functionality of Ghidra. There are two requirements for a class to be an extension point:&lt;/p&gt;

&lt;ol&gt;
  &lt;li&gt;It must (directly or indirectly) derive from the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ExtensionPoint&lt;/code&gt; class.&lt;/li&gt;
  &lt;li&gt;The containing file must have a valid extenstion point suffix.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;The first requirement is met. The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BranchDestinationResolver&lt;/code&gt; class indirectly extends &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ExtensionPoint&lt;/code&gt;&lt;sup id=&quot;fnref:deriv&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:deriv&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;1&lt;/a&gt;&lt;/sup&gt;. The problem is with the filename. By default only certain suffixes (there are about fifty) are recognized as extension point suffixes, the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Analyzer&lt;/code&gt; suffix among them. &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Resolver&lt;/code&gt; is not a valid extension point suffix, so Ghidra doesn’t recognize &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BranchDestinationResolver&lt;/code&gt; as an analyzer, while &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BrainfuckAnalyzer&lt;/code&gt; is fine because it ends with &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Analyzer&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;We could append a valid suffix to the analyzer name to ensure Ghidra recognizes it, but it would result in an akward name (e.g. &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BranchDestinationResolverAnalyzer&lt;/code&gt; or &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BranchDestinationAddressCorrelator&lt;/code&gt;). We could also drop the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Resolver&lt;/code&gt; suffix and use the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Analyzer&lt;/code&gt; suffix instead (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BranchDestinationAnalyzer&lt;/code&gt; sounds better). Instead of doing this, we can also register a new extension point suffix.&lt;/p&gt;

&lt;p&gt;To register a new extension point suffix, we create a file in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;data&lt;/code&gt; directory of the project called &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ExtensionPoint.manifest&lt;/code&gt;. It contains only one line:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;Resolver
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;That’s all. Ghidra recognizes the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ExtensionPoint.manifest&lt;/code&gt; file and registers all suffixes in the manifest (separated by newlines). This is also how the default extension points suffixes are registered. For example, the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Analyzer&lt;/code&gt; suffix is registered in &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Ghidra/Features/Base/data/ExtensionPoint.manifest&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;If we now start Ghidra and open the analysis window, the analyzer shows up again:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-07-27-ghidra-brainfuck-processor-4/images/analysis_options_resolver.png&quot; alt=&quot;Analysis window&quot; title=&quot;It's back again :)&quot; /&gt;&lt;/p&gt;

&lt;p&gt;This was a very brief look at extension points. The whole extension point mechanism deserves a post of its own. If you’re interested in how it works, I suggest looking at the &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Framework/Generic/src/main/java/ghidra/util/classfinder/ClassSearcher.java&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ClassSearcher&lt;/code&gt;&lt;/a&gt;, and &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Framework/Generic/src/main/java/ghidra/util/classfinder/ClassFinder.java&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ClassFinder&lt;/code&gt;&lt;/a&gt; classes.&lt;/p&gt;

&lt;h1 id=&quot;adding-a-manual&quot;&gt;Adding a manual&lt;/h1&gt;
&lt;p&gt;Now something different: adding a manual to the processor module. As said in the first post, a language in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.ldefs&lt;/code&gt; file can have a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;manualindexfile&lt;/code&gt; attribute pointing to a processor manual index file. A &lt;strong&gt;processor manual&lt;/strong&gt; consists of one or more PDF files that contain documentation for the instruction set. A &lt;strong&gt;processor manual index&lt;/strong&gt; maps instruction mnemonics to their corresponding page in the manual.&lt;/p&gt;

&lt;p&gt;The manual index is documented at &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/GhidraDocs/languages/manual_index.txt&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;GhidraDocs/languages/manual_index.txt&lt;/code&gt;&lt;/a&gt;, but the documentation is not fully complete. The code that loads the manual index file can be found &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/app/plugin/processors/sleigh/SleighLanguage.java#L1264&quot;&gt;here&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Suppose we’ve got a dummy manual, &lt;a href=&quot;/assets/2020-07-27-ghidra-brainfuck-processor-4/bfman.pdf&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;bfman.pdf&lt;/code&gt;&lt;/a&gt;. It’s manual index file would look like this:&lt;/p&gt;

&lt;p&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;data/manuals/brainfuck.idx&lt;/code&gt;:&lt;/p&gt;
&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;@ bfman.pdf [Brainfuck Manual]

&amp;gt;, 1
# the '&amp;lt;' instruction is intentionally omitted

+, 2
-, 2

,, 3
., 3

[, 4
], 4
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The first line starting with &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;@&lt;/code&gt; is called a file switch. It sets the current manual file. The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[Brainfuck Manual]&lt;/code&gt; part provides a description for this manual. It’s optional and is shown when Ghidra can’t find the manual file, so the user can locate the manual elsewhere. There can be multiple file switches in a manual index. This is useful when the processor manual spans over several volumes.&lt;/p&gt;

&lt;p&gt;As stated in the index file, the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;&lt;/code&gt; instruction is omitted. This is because the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;&lt;/code&gt; character has a special (undocumented) meaning. It can be used to import another index file. There’s no way to escape this character, which makes it impossible to create an entry for the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;&lt;/code&gt; instruction. The only way to get around this is to rename the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;&lt;/code&gt; instruction. For now, we’ll just omit the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;&lt;/code&gt; instruction.&lt;/p&gt;

&lt;p&gt;Also good to know (and again undocumented): a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;#&lt;/code&gt; indicates a comment.&lt;/p&gt;

&lt;p&gt;The only thing left to do now is to add the manual index file to the language definition in &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;brainfuck.ldefs&lt;/code&gt;. This is done by adding the following attribute to the language tag: &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;manualindexfile=&quot;../manuals/brainfuck.idx&quot;&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;That’s all there is to manual index files. If you now right-click an instruction and click &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Processor Manual...&lt;/code&gt;, Ghidra will show the documentation for that instruction!&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-07-27-ghidra-brainfuck-processor-4/images/processor_manual.png&quot; alt=&quot;Instruction context menu&quot; title=&quot;Click Processor Manual to open the docs&quot; /&gt;&lt;/p&gt;

&lt;p&gt;In this post, we’ve improved the usability of the processor module. Meanwhile, the module still produces poor decompilation output. Next time, we’ll look at improving the decompilation of our module. Hopefully, we’ll manage to produce better decompilations.&lt;/p&gt;

&lt;h1 id=&quot;footnotes&quot;&gt;Footnotes&lt;/h1&gt;

&lt;div class=&quot;footnotes&quot; role=&quot;doc-endnotes&quot;&gt;
  &lt;ol&gt;
    &lt;li id=&quot;fn:deriv&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BranchDestinationResolver ⊂ AbstractAnalyzer ⊂ Analyzer ⊂ ExtensionPoint&lt;/code&gt; &lt;a href=&quot;#fnref:deriv&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
  &lt;/ol&gt;
&lt;/div&gt;
</description>
        <pubDate>Mon, 27 Jul 2020 00:00:00 +0000</pubDate>
        <link>https://spinsel.dev/2020/07/27/ghidra-brainfuck-processor-4.html</link>
        <guid isPermaLink="true">https://spinsel.dev/2020/07/27/ghidra-brainfuck-processor-4.html</guid>
        
        <category>Ghidra</category>
        
        
      </item>
    
      <item>
        <title>Implementing a brainfuck CPU in Ghidra - part 3: Decompilation of I/O and control flow instructions</title>
        <description>&lt;div class=&quot;blog-post-series-block&quot;&gt;This blog post is part of the series &lt;i&gt;Implementing a brainfuck CPU in Ghidra&lt;/i&gt;:

    &lt;ol&gt;&lt;li&gt;&lt;a href=&quot;/2020/06/17/ghidra-brainfuck-processor-1.html&quot;&gt; Setup and disassembly&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href=&quot;/2020/06/17/ghidra-brainfuck-processor-2.html&quot;&gt; Decompilation of pointer and arithmetic instructions&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;b&gt; Decompilation of I/O and control flow instructions (current post)&lt;/b&gt;&lt;/li&gt;&lt;li&gt;&lt;a href=&quot;/2020/07/27/ghidra-brainfuck-processor-4.html&quot;&gt; Renaming the analyzer and adding a manual&lt;/a&gt;&lt;/li&gt;&lt;li&gt;Recognizing common patterns (future post)&lt;/li&gt;&lt;/ol&gt;&lt;p&gt;More posts may be added to this series in the future.&lt;/p&gt;&lt;/div&gt;
&lt;p&gt;This is already the third post in this series. This time we’ll complete the decompilation part of the processor module by adding semantics for the I/O (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;,&lt;/code&gt;) and control flow (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt;) instructions.&lt;/p&gt;

&lt;h1 id=&quot;io-instructions&quot;&gt;I/O instructions&lt;/h1&gt;
&lt;p&gt;The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.&lt;/code&gt; (output) and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;,&lt;/code&gt; (input) instructions can’t be described by regular p-code operations, as regular p-code operations operate only on varnodes. They don’t allow for modelling external input. Luckily, we can define custom p-code operations like this:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;define pcodeop in;
define pcodeop out;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;This code declares two custom p-code operations: &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;in&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;out&lt;/code&gt;. User-defined p-code operations can have any number of input varnodes and an additional output varnode. Ghidra will not (and cannot) make any assumptions about these operations; they are treated as black boxes. Because Ghidra can’t analyze these black boxes, you should always try to keep the number of user-defined p-code operations to a minimum.&lt;/p&gt;

&lt;p&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;in&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;out&lt;/code&gt; can be used in SLEIGH semantic statements using using functional syntax (calling them like a function, e.g. &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;f(x)&lt;/code&gt;). The following statements are all valid (assuming &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;x&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;a&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;b&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;c&lt;/code&gt; are defined):&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;x = in();
x = in(a);
in(a, b, c);
x = out()
x = out(a, b)
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;It is even valid to call an operation with one operand first and later with two:&lt;/p&gt;
&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;out(a);
...
out(a, b);
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Most of these don’t make sense. Only &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;x = in()&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;out(x)&lt;/code&gt; make sense. &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;in&lt;/code&gt; should not take any input and outputs one value. &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;out&lt;/code&gt; is the opposite: it takes exactly one input and does not return anything. There is no way to enforce this using the specification. It is the task of the language creator to do this.&lt;/p&gt;

&lt;p&gt;Something like this is not allowed:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;x, y = in()
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;This is because p-code operations can have at most one output varnode.&lt;/p&gt;

&lt;p&gt;Let’s see how we can use our newly defined p-code operations to define the semantics of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.&lt;/code&gt; instruction and later of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;,&lt;/code&gt; instruction. The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.&lt;/code&gt; instruction does the following: it takes the value of the current cell and outputs this value.&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;:. is op=0x4 {
    local c:2 = *[ram]ptr;
    out(c);
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;You can also write &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;out(*[ram]:2 ptr);&lt;/code&gt;, if you’re feeling brave. In my opinion, this reduces readability.&lt;/p&gt;

&lt;p&gt;The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;,&lt;/code&gt; instruction takes input and stores it in the current cell:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;:, is op=0x5
{
    local c:2 = in();
    *[ram]ptr = c;
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;(Or write &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;*[ram]:2 ptr = in();&lt;/code&gt;.)&lt;/p&gt;

&lt;p&gt;We can test these instructions using a simple program called &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;add3.bf&lt;/code&gt;. It takes user input, adds three to it and outputs the result:&lt;/p&gt;

&lt;div class=&quot;language-brainfuck highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nf&quot;&gt;,&lt;/span&gt;&lt;span class=&quot;c1&quot;&gt;      store user input
&lt;/span&gt;&lt;span class=&quot;nf&quot;&gt;+++&lt;/span&gt;&lt;span class=&quot;c1&quot;&gt;    add three
&lt;/span&gt;&lt;span class=&quot;nf&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;c1&quot;&gt;      output
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Compile it (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;./bfc.py add3.bf add3.bin&lt;/code&gt;) and open it in Ghidra. The disassembly will look like this:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-3/images/disassembly_add3.png&quot; alt=&quot;Disassembly of add3.bin&quot; /&gt;&lt;/p&gt;

&lt;p&gt;Here it can be seen that user-defined p-code operations in SLEIGH are converted to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;CALLOTHER&lt;/code&gt; operations in the p-code. These &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;CALLOTHER&lt;/code&gt; operations take the user-defined operation name as their first argument, followed by the arguments of that operation. More concretely, an operation like &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;out(c)&lt;/code&gt; gets converted to:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;CALLOTHER &quot;out&quot;, $U90
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Where &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;$U90&lt;/code&gt; is the varnode in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;unique&lt;/code&gt; address space corresponding to the symbol &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;c&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;In the decompilation, these user-defined p-code operations are represented by functions:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-3/images/decompilation_add3.png&quot; alt=&quot;Decompilation of add3.bin&quot; /&gt;&lt;/p&gt;

&lt;p&gt;An interesting thing about this decompilation is that the order of execution is not preserved. In the decompilation, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;out&lt;/code&gt; is called before the value is written to memory. An order-preserving decompilation may look like this:&lt;/p&gt;

&lt;div class=&quot;language-c highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;n&quot;&gt;sRam0000&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;in&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;();&lt;/span&gt;
&lt;span class=&quot;n&quot;&gt;sRam0000&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;+=&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;3&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;
&lt;span class=&quot;n&quot;&gt;out&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;sRam0000&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The decompiler is free to move statements around as long as it can prove the outcome is the same. In this case, the output is preserved: in both cases the result of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;in() + 3&lt;/code&gt; is written out using &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;out&lt;/code&gt; and written to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ram&lt;/code&gt; at address &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x0000&lt;/code&gt;.&lt;/p&gt;

&lt;h1 id=&quot;control-flow-instructions&quot;&gt;Control flow instructions&lt;/h1&gt;
&lt;p&gt;Implementing the I/O instructions was the easy part. The implementation of the control flow instructions is a bit more complex, because of the unusual branch implementation of brainfuck. Common architectures have branch instructions that encode an absolute or relative address for the CPU to branch to. Brainfuck doesn’t encode the branch destination in the instruction itself. Instead if it encounters &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt;, it may jump to the corresponding &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt;, depending on the current cell value. If it encounters a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt;, it jumps to the corresponding &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt;. Compare the following brainfuck code to its (unoptimized) ARM (ARMv6-M Thumb) equivalent (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;r0&lt;/code&gt; is &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ptr&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;r1&lt;/code&gt; is a temporary register to hold the current cell value):&lt;/p&gt;

&lt;p&gt;&lt;a href=&quot;https://github.com/spinsel/spinsel.dev/tree/master/assets/2020-06-17-ghidra-brainfuck-processor-3/source/control_flow_test.bf&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;control_flow_test.bf&lt;/code&gt;&lt;/a&gt;:&lt;/p&gt;
&lt;div class=&quot;language-brainfuck highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nf&quot;&gt;+-&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;[&lt;/span&gt;&lt;span class=&quot;nf&quot;&gt;-&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;]&lt;/span&gt;&lt;span class=&quot;nf&quot;&gt;+&lt;/span&gt;&lt;span class=&quot;c1&quot;&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;&lt;a href=&quot;https://github.com/spinsel/spinsel.dev/tree/master/assets/2020-06-17-ghidra-brainfuck-processor-3/source/control_flow_test_arm.s&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;control_flow_test_arm.s&lt;/code&gt;&lt;/a&gt;:&lt;/p&gt;
&lt;div class=&quot;language-armasm highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;c&quot;&gt;; +&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;ldr&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;[&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;r0&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;]&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;add&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;#&lt;/span&gt;&lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;str&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;[&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;r0&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;]&lt;/span&gt;

&lt;span class=&quot;c&quot;&gt;; -&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;ldr&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;[&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;r0&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;]&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;sub&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;#&lt;/span&gt;&lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;str&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;[&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;r0&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;]&lt;/span&gt;

&lt;span class=&quot;nl&quot;&gt;loop_start&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;:&lt;/span&gt;
&lt;span class=&quot;c&quot;&gt;; [&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;ldr&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;[&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;r0&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;]&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;cmp&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;#&lt;/span&gt;&lt;span class=&quot;mi&quot;&gt;0&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;beq&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;loop_end&lt;/span&gt;

&lt;span class=&quot;c&quot;&gt;; -&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;ldr&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;[&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;r0&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;]&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;sub&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;#&lt;/span&gt;&lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;str&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;[&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;r0&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;]&lt;/span&gt;

&lt;span class=&quot;c&quot;&gt;; ]&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;b&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;loop_start&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;loop_end&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;:&lt;/span&gt;

&lt;span class=&quot;c&quot;&gt;; +&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;ldr&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;[&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;r0&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;]&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;add&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;#&lt;/span&gt;&lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;
&lt;span class=&quot;nl&quot;&gt;str&lt;/span&gt; &lt;span class=&quot;nb&quot;&gt;r1&lt;/span&gt;&lt;span class=&quot;err&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;[&lt;/span&gt;&lt;span class=&quot;nv&quot;&gt;r0&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The ARM assembly may look complicated, but it produces a nice decompilation&lt;sup id=&quot;fnref:arm_decomp&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:arm_decomp&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;1&lt;/a&gt;&lt;/sup&gt;:&lt;/p&gt;

&lt;div class=&quot;language-c highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kt&quot;&gt;void&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;FUN_00010000&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;void&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;){&lt;/span&gt;
    &lt;span class=&quot;kt&quot;&gt;int&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;ptr&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;

    &lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;ptr&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;++&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;
    &lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;ptr&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;--&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;while&lt;/span&gt; &lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;ptr&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;!=&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;0&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt;
        &lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;ptr&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;--&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;

    &lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;ptr&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;

    &lt;span class=&quot;n&quot;&gt;halt_baddata&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;();&lt;/span&gt;
&lt;span class=&quot;p&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;b&lt;/code&gt; instruction looks like this in p-code:&lt;/p&gt;
&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;BRANCH *[ram]0x10006:4
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;beq&lt;/code&gt; instruction looks as follows:&lt;/p&gt;
&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;$Uefa0:1 = INT_NOTEQUAL ZR, 0:1
CBRANCH *[ram]0x10012:4, $Uefa0
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The p-code for these ARM instructions is very short because they have an almost one-to-one correspondence with their p-code operations. The control flow graph of the program looks like this:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-3/images/control_flow_graph_arm.png&quot; alt=&quot;Control flow graph of the test binary&quot; /&gt;&lt;/p&gt;

&lt;p&gt;Ghidra can easily calculate the branch destinations and then recover the loop-structure of this program. It is of great importance that Ghidra can compute the branch destination. If not, it can’t recover the structure of the program.&lt;/p&gt;

&lt;p&gt;The brainfuck variant of the program looks a lot simpler, but its p-code is more complicated. Let’s model the semantics of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt; instruction. We’ll restrict ourselves to the context of this program, which means that (a) there are just two control flow instructions in the entire program (one &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt; and one &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt;) and (b) the cell value at the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt; instruction is zero, so the cpu should always branch to the corresponding &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt; instruction.&lt;/p&gt;

&lt;p&gt;The following code searches for the next &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt; (opcode &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x7&lt;/code&gt;) and branches to it:&lt;/p&gt;
&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;:[ is op=0x6 {
    local addr:2 = inst_start + 1;

    &amp;lt;check&amp;gt;
    local instr:2 = *addr;
    if(instr == 0x7) goto &amp;lt;end&amp;gt;;
    addr = addr + 1;
    goto &amp;lt;check&amp;gt;;

    &amp;lt;end&amp;gt;
    goto [addr];
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;This produces the following decompilation for &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;control_flow_test.bf&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-c highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kt&quot;&gt;void&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;start&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;void&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;){&lt;/span&gt;
    &lt;span class=&quot;kt&quot;&gt;short&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;UNRECOVERED_JUMPTABLE&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;

    &lt;span class=&quot;cm&quot;&gt;/* WARNING: Could not recover jumptable at 0x0002. Too many branches */&lt;/span&gt;
    &lt;span class=&quot;cm&quot;&gt;/* WARNING: Treating indirect jump as call */&lt;/span&gt;
    &lt;span class=&quot;n&quot;&gt;UNRECOVERED_JUMPTABLE&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;short&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt;&lt;span class=&quot;mh&quot;&gt;0x3&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;while&lt;/span&gt; &lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;UNRECOVERED_JUMPTABLE&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;!=&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;7&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt;
        &lt;span class=&quot;n&quot;&gt;UNRECOVERED_JUMPTABLE&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;short&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)((&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;short&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;UNRECOVERED_JUMPTABLE&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;+&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;);&lt;/span&gt;

    &lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;code&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;UNRECOVERED_JUMPTABLE&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)();&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;return&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;
&lt;span class=&quot;p&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The control flow graph of this program consists of just one block, ending with a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BRANCHIND&lt;/code&gt; to an unknown destination:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-3/images/control_flow_pcode_graph.png&quot; alt=&quot;Control flow graph of the test binary&quot; /&gt;&lt;/p&gt;

&lt;p&gt;Clearly, Ghidra is unable to statically calculate the branch destination of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt; instruction, even though it is statically computable&lt;sup id=&quot;fnref:readonly&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:readonly&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;2&lt;/a&gt;&lt;/sup&gt;. Simper calculations in the semantics (with control flow constructs , but without loops) &lt;em&gt;are&lt;/em&gt; computed correctly by Ghidra. My guess is Ghidra doesn’t bother computing loops in p-code, although I have not really looked into this (yet). (If there is a way to compute this statically in SLEIGH semantics, please contact me!)&lt;/p&gt;

&lt;p&gt;It’s no use continuing to implement the semantics of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt; this way. We need another way to statically compute branch destinations that Ghidra &lt;em&gt;does&lt;/em&gt; understand. I came up with the following:&lt;/p&gt;

&lt;ol&gt;
  &lt;li&gt;Compute the branch destinations using an analyzer, written in Java&lt;/li&gt;
  &lt;li&gt;Write these destinations to memory that’s marked as read-only&lt;/li&gt;
  &lt;li&gt;The instruction semantics for the control flow instructions will consist of a check whether the cpu should branch, a load from memory and a branch to the loaded destination.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;We’ll call this memory that holds branch destinations &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;bdest&lt;/code&gt;. This memory can be created by adding the following to the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;default_memory_blocks&amp;gt;&lt;/code&gt; tag in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.pspec&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-xml highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nt&quot;&gt;&amp;lt;memory_block&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;name=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;bdest&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;start_address=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;bdest:0x0000&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;length=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;0x1000&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;mode=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;r&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;initialized=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;true&quot;&lt;/span&gt;&lt;span class=&quot;nt&quot;&gt;/&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Expose &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;bdest&lt;/code&gt; to SLEIGH by extending the address space definitions in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;define space bdest type=ram_space size=2 wordsize=2;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The last thing to do is to mark &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;bdest&lt;/code&gt; as read-only in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.cspec&lt;/code&gt;. Add this to the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;compiler_spec&amp;gt;&lt;/code&gt; tag:&lt;/p&gt;

&lt;div class=&quot;language-xml highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nt&quot;&gt;&amp;lt;readonly&amp;gt;&lt;/span&gt;
    &lt;span class=&quot;nt&quot;&gt;&amp;lt;range&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;space=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;bdest&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;first=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;0x0000&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;last=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;0x0fff&quot;&lt;/span&gt;&lt;span class=&quot;nt&quot;&gt;/&amp;gt;&lt;/span&gt;
&lt;span class=&quot;nt&quot;&gt;&amp;lt;/readonly&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Without this, the decompiler doesn’t assume that &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;bdest&lt;/code&gt; is read-only, even though
 it is marked as such in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.pspec&lt;/code&gt; (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;mode=&quot;r&quot;&lt;/code&gt;).&lt;/p&gt;

&lt;p&gt;Eclipse automatically created an analyzer for us when we selected analyzer in the project wizard during the project setup. It is called &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;BrainfuckAnalyzer.java&lt;/code&gt;. The functions &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;getDefaultEnablement&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;registerOptions&lt;/code&gt; can be removed, because this analyzer won’t use them. Change the constructor to this:&lt;/p&gt;

&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kd&quot;&gt;private&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;final&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;static&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;String&lt;/span&gt; &lt;span class=&quot;no&quot;&gt;NAME&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;s&quot;&gt;&quot;Brainfuck Branch Destination Resolver&quot;&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;
&lt;span class=&quot;kd&quot;&gt;private&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;final&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;static&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;String&lt;/span&gt; &lt;span class=&quot;no&quot;&gt;DESCRIPTION&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;s&quot;&gt;&quot;Computes branch destinations for control flow instructions ([ and ]) and writes them to bdest memory&quot;&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;
&lt;span class=&quot;o&quot;&gt;...&lt;/span&gt;
&lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;BrainfuckAnalyzer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;()&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;kd&quot;&gt;super&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;no&quot;&gt;NAME&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;no&quot;&gt;DESCRIPTION&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;AnalyzerType&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;BYTE_ANALYZER&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
    &lt;span class=&quot;n&quot;&gt;setDefaultEnablement&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kc&quot;&gt;true&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
    &lt;span class=&quot;n&quot;&gt;setSupportsOneTimeAnalysis&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kc&quot;&gt;true&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
    &lt;span class=&quot;n&quot;&gt;setPriority&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;AnalysisPriority&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;DISASSEMBLY&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;before&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;());&lt;/span&gt;
&lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The analyzer is marked as byte analyzer instead of instruction analyzer, because it operates on raw bytes &lt;em&gt;before&lt;/em&gt; they are converted to instructions so that Ghidra can correctly analyze branches. Read more about analyzer types in the &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Features/Base/src/main/java/ghidra/app/services/AnalyzerType.java&quot;&gt;source code&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;The next statements notify Ghidra that the analyzer should be enabled by default and that it supports one time (one-shot) analysis. One time analysis does not mean it can only be called once, but that it can be called at any time and not just during auto analysis. It is obvious that the analyzer should be called before disassembly. Hence the priority &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;DISASSEMBLY.before()&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;There are two functions left: &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;canAnalyze&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;added&lt;/code&gt;. We’ll get to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;canAnalyze&lt;/code&gt; first. This function tells Ghidra whether the analyzer can analyze the program. This analyzer should only analyze Brainfuck programs:&lt;/p&gt;

&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kd&quot;&gt;private&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;final&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;static&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;String&lt;/span&gt; &lt;span class=&quot;no&quot;&gt;PROCESSOR_NAME&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;s&quot;&gt;&quot;brainfuck&quot;&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;
&lt;span class=&quot;o&quot;&gt;...&lt;/span&gt;
&lt;span class=&quot;nd&quot;&gt;@Override&lt;/span&gt;
&lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kt&quot;&gt;boolean&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;canAnalyze&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;Program&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;program&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;nc&quot;&gt;String&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;procName&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;program&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getLanguage&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;().&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getProcessor&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;().&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;toString&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;();&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;return&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;procName&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;equals&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;no&quot;&gt;PROCESSOR_NAME&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
&lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;added&lt;/code&gt; is where the real magic happens. This function is called when bytes are added to the program or during auto or one-shot analysis. It’s responsible for the analysis. We’ll put the main logic in a function called &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;resolveBranchDests&lt;/code&gt; and call that function from &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;added&lt;/code&gt;, which catches and reports exceptions.&lt;/p&gt;

&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nd&quot;&gt;@Override&lt;/span&gt;
&lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kt&quot;&gt;boolean&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;added&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;Program&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;program&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;AddressSetView&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;set&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;TaskMonitor&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;monitor&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;MessageLog&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;log&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt;
        &lt;span class=&quot;kd&quot;&gt;throws&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CancelledException&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;try&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
        &lt;span class=&quot;k&quot;&gt;return&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;resolveBranchDests&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;program&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;monitor&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
    &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt; &lt;span class=&quot;k&quot;&gt;catch&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;CancelledException&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;e&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
        &lt;span class=&quot;k&quot;&gt;throw&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;e&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;
    &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt; &lt;span class=&quot;k&quot;&gt;catch&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;Exception&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;e&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
        &lt;span class=&quot;n&quot;&gt;log&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;appendException&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;e&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
        &lt;span class=&quot;k&quot;&gt;return&lt;/span&gt; &lt;span class=&quot;kc&quot;&gt;false&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;
    &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;
&lt;p&gt;This constructions throws &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;CancelledException&lt;/code&gt; (raised by &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;monitor.checkCanceled()&lt;/code&gt; when the user cancels the operation) and logs any other exceptions.&lt;/p&gt;

&lt;p&gt;Let’s write &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;resolveBranchDests&lt;/code&gt;. This function receives a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Program&lt;/code&gt; and a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;TaskMonitor&lt;/code&gt; and it can throw a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;CancelledException&lt;/code&gt; and a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;MemoryAccessException&lt;/code&gt;. The latter will be raised if the memory we’re trying to write (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;bdest&lt;/code&gt;) is uninitialized. It will not be thrown because we set &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;initialized=&quot;true&quot;&lt;/code&gt; in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.pspec&lt;/code&gt;. It is a checked exception, however, so we must catch it.&lt;/p&gt;

&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kd&quot;&gt;private&lt;/span&gt; &lt;span class=&quot;kt&quot;&gt;boolean&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;resolveLoops&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;Program&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;program&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;AddressSetView&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;set&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;TaskMonitor&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;monitor&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;MessageLog&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;log&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt;
        &lt;span class=&quot;kd&quot;&gt;throws&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CancelledException&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;MemoryAccessException&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;nc&quot;&gt;Memory&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;mem&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;program&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getMemory&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;();&lt;/span&gt;
    &lt;span class=&quot;nc&quot;&gt;MemoryBlock&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;rom&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;mem&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getBlock&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;rom&quot;&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
    &lt;span class=&quot;nc&quot;&gt;MemoryBlock&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;branchDests&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;mem&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getBlock&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;bdest&quot;&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;These lines get references to memory blocks we’ll be using.&lt;/p&gt;

&lt;p&gt;Make sure the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;bdest&lt;/code&gt; memory is big enough:&lt;/p&gt;
&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;k&quot;&gt;if&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;bdest&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getSize&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;()&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;&amp;lt;&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;rom&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getSize&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;())&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;throw&lt;/span&gt; &lt;span class=&quot;k&quot;&gt;new&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;AddressOutOfBoundsException&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;The bdest memory can't be smaller than the rom memory.&quot;&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Initialize the task monitor. We set the maximum progress equal to the size of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;rom&lt;/code&gt;, as we’ll be iterating over the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;rom&lt;/code&gt; memory. It isn’t necessary to use the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;TaskMonitor&lt;/code&gt;, but it provides a more user-friendly interface.&lt;/p&gt;
&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;n&quot;&gt;monitor&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;initialize&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;rom&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getSize&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Create a stack to keep track of addresses of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt; and iterate over the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;rom&lt;/code&gt;. Each iteration we update the monitor and get the current instruction byte. If it is an &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt;, we push the current address on the stack. If an &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt; is encountered. The address of the corresponding &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt; is popped from the stack. The branch destination of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt; is set to the address of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt;. The branch destination of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt; is set to the address of the instruction &lt;em&gt;following&lt;/em&gt; the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt;. (It should jump &lt;em&gt;over&lt;/em&gt;, but not &lt;em&gt;to&lt;/em&gt;, the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt;.)&lt;/p&gt;

&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nc&quot;&gt;Stack&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;Long&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;gt;&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;addrStack&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;k&quot;&gt;new&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;Stack&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;Long&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;gt;();&lt;/span&gt;
&lt;span class=&quot;k&quot;&gt;for&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;long&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;addr&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;0&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;addr&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;&amp;lt;&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;rom&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getSize&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;();&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;addr&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;++){&lt;/span&gt;
    &lt;span class=&quot;n&quot;&gt;monitor&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;checkCanceled&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;();&lt;/span&gt;
    &lt;span class=&quot;n&quot;&gt;monitor&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;incrementProgress&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;

    &lt;span class=&quot;kt&quot;&gt;byte&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;instr&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;readInstruction&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;rom&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;addr&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;switch&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;instr&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;){&lt;/span&gt;
        &lt;span class=&quot;k&quot;&gt;case&lt;/span&gt; &lt;span class=&quot;nl&quot;&gt;OPEN_LOOP:&lt;/span&gt;
            &lt;span class=&quot;n&quot;&gt;addrStack&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;push&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;addr&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
            &lt;span class=&quot;k&quot;&gt;break&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;
        
        &lt;span class=&quot;k&quot;&gt;case&lt;/span&gt; &lt;span class=&quot;nl&quot;&gt;CLOSE_LOOP:&lt;/span&gt;
            &lt;span class=&quot;k&quot;&gt;if&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;addrStack&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;empty&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;())&lt;/span&gt;
                &lt;span class=&quot;k&quot;&gt;throw&lt;/span&gt; &lt;span class=&quot;k&quot;&gt;new&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;UnmatchedBranchException&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;addr&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;

            &lt;span class=&quot;kt&quot;&gt;long&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;openInstr&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;addrStack&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;pop&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;();&lt;/span&gt;
            &lt;span class=&quot;n&quot;&gt;writeBranchDest&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;bdest&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;addr&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;openInstr&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
            &lt;span class=&quot;n&quot;&gt;writeBranchDest&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;bdest&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;openInstr&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;addr&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;+&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
            &lt;span class=&quot;k&quot;&gt;break&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;
    &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;

&lt;span class=&quot;k&quot;&gt;if&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(!&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;addrStack&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;empty&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;())&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;throw&lt;/span&gt; &lt;span class=&quot;k&quot;&gt;new&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;UnmatchedBranchException&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;();&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;If a branch is unmatched (has no corresponding &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt; or &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt;), a custom exception called &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;UnmatchedBranchException&lt;/code&gt; is raised.&lt;/p&gt;

&lt;p&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;UnbalancedLoopException.java&lt;/code&gt;:&lt;/p&gt;
&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kn&quot;&gt;package&lt;/span&gt; &lt;span class=&quot;nn&quot;&gt;brainfuck&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;

&lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;class&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;UnmatchedBranchException&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;extends&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;RuntimeException&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;UnmatchedBranchException&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;()&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
        &lt;span class=&quot;kd&quot;&gt;super&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;();&lt;/span&gt;
    &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;

    &lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;UnmatchedBranchException&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;long&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;address&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;){&lt;/span&gt;
        &lt;span class=&quot;kd&quot;&gt;super&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;Unmatched branch at address 0x&quot;&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;+&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;Long&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;toHexString&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;address&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;));&lt;/span&gt;
    &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The rest of the source code can be found &lt;a href=&quot;https://github.com/spinsel/spinsel.dev/tree/master/assets/2020-06-17-ghidra-brainfuck-processor-3/source&quot;&gt;here&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Once this is implemented, writing semantics for the control flow instructions is very easy. The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt; checks the current cell value. If it is non-zero, execution should continue at the next instruction and this instruction is essentially a NOP. If the cell is zero, a branch should be performed. The address is retrieved from &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;bdest&lt;/code&gt;.&lt;/p&gt;
&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;:[ is op=0x6 {
    local c:2 = *[ram]ptr;

    if(c != 0x0) goto &amp;lt;end&amp;gt;;
    local idx:2 = inst_start;
    local dest:2 = *[bdest]idx;
    goto [dest];
    
    &amp;lt;end&amp;gt;
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The semantics for &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt; are even easier. It just branches to the corresponding &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;:] is op=0x7 {
    local idx:2 = inst_start;
    local dest:2 = *[bdest]idx;
    goto [dest];
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;We could have also implemented semantics for &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt; to check the current cell value and perform a branch accordingly. The current implementation is functionally equivalent to that, is shorter and follows the construction that is commonly used in binaries emitted by compilers (arrows represent branch destinations):&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;┏━━━&amp;gt; compare
┃ ┌─&amp;lt; conditional branch
┃ │   code (condition false)
┗━│━&amp;lt; unconditional branch to compare
  └─&amp;gt; code (condition true)
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The produced flow control graph for the brainfuck binary after running the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Brainfuck Branch Destination Resolver&lt;/code&gt; analyzer is now identical to the graph produced for the ARM binary:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-3/images/control_flow_graph.png&quot; alt=&quot;Control flow graph of the test binary&quot; title=&quot;Look at that nice loop structure&quot; /&gt;&lt;/p&gt;

&lt;p&gt;It also produces a reasonable decompilation (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;c0&lt;/code&gt; is cell zero):&lt;/p&gt;

&lt;div class=&quot;language-c highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kt&quot;&gt;void&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;start&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;void&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;){&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;while&lt;/span&gt; &lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;c0&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;!=&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;0&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt;
        &lt;span class=&quot;n&quot;&gt;c0&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;--&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;

    &lt;span class=&quot;n&quot;&gt;c0&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;

    &lt;span class=&quot;n&quot;&gt;halt_baddata&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;();&lt;/span&gt;
&lt;span class=&quot;p&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The decompiler recognizes the redundancy of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;+-&lt;/code&gt; and it does not show up in the decompilation.&lt;/p&gt;

&lt;p&gt;That’s it! The decompiler is now able to decompile any compiled brainfuck binary. Call &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;bfc.py&lt;/code&gt; on your favorite brainfuck program and see what the decompilation looks like in Ghidra. One thing that will massively clean up the decompilation is recognizing common patterns. Right now &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[-]&lt;/code&gt; is decompiled to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;while(c!=0) c--;&lt;/code&gt;, while it could theoretically also be decompiled to the more concise &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;c=0;&lt;/code&gt;. This is something we’ll take a look at in a future post.&lt;/p&gt;

&lt;p&gt;&lt;a href=&quot;/2020/07/27/ghidra-brainfuck-processor-4.html&quot;&gt;Next time&lt;/a&gt;, we’ll make some small improvements to our processor module. See you then!&lt;/p&gt;

&lt;p&gt;You can find the final code for this post &lt;a href=&quot;https://github.com/spinsel/spinsel.dev/tree/master/assets/2020-06-17-ghidra-brainfuck-processor-3/source&quot;&gt;here&lt;/a&gt;.&lt;/p&gt;

&lt;h1 id=&quot;footnotes&quot;&gt;Footnotes&lt;/h1&gt;

&lt;div class=&quot;footnotes&quot; role=&quot;doc-endnotes&quot;&gt;
  &lt;ol&gt;
    &lt;li id=&quot;fn:arm_decomp&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;To reproduce this, assemble it using &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;arm-none-eabi-as -march=armv6-m -mthumb control_flow_test_arm.s -o control_flow_test_arm.bin&lt;/code&gt; (change &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;;&lt;/code&gt; to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;//&lt;/code&gt;) and open &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;control_flow_test_arm.bin&lt;/code&gt; it in Ghidra. &lt;a href=&quot;#fnref:arm_decomp&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
    &lt;li id=&quot;fn:readonly&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;Even marking &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;rom&lt;/code&gt; as read-only using the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;readonly&amp;gt;&lt;/code&gt; tag in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.cspec&lt;/code&gt; didn’t work. &lt;a href=&quot;#fnref:readonly&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
  &lt;/ol&gt;
&lt;/div&gt;
</description>
        <pubDate>Wed, 17 Jun 2020 00:00:00 +0000</pubDate>
        <link>https://spinsel.dev/2020/06/17/ghidra-brainfuck-processor-3.html</link>
        <guid isPermaLink="true">https://spinsel.dev/2020/06/17/ghidra-brainfuck-processor-3.html</guid>
        
        <category>Ghidra</category>
        
        
      </item>
    
      <item>
        <title>Implementing a brainfuck CPU in Ghidra - part 2: Decompilation of pointer and arithmetic instructions</title>
        <description>&lt;div class=&quot;blog-post-series-block&quot;&gt;This blog post is part of the series &lt;i&gt;Implementing a brainfuck CPU in Ghidra&lt;/i&gt;:

    &lt;ol&gt;&lt;li&gt;&lt;a href=&quot;/2020/06/17/ghidra-brainfuck-processor-1.html&quot;&gt; Setup and disassembly&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;b&gt; Decompilation of pointer and arithmetic instructions (current post)&lt;/b&gt;&lt;/li&gt;&lt;li&gt;&lt;a href=&quot;/2020/06/17/ghidra-brainfuck-processor-3.html&quot;&gt; Decompilation of I/O and control flow instructions&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href=&quot;/2020/07/27/ghidra-brainfuck-processor-4.html&quot;&gt; Renaming the analyzer and adding a manual&lt;/a&gt;&lt;/li&gt;&lt;li&gt;Recognizing common patterns (future post)&lt;/li&gt;&lt;/ol&gt;&lt;p&gt;More posts may be added to this series in the future.&lt;/p&gt;&lt;/div&gt;
&lt;p&gt;In the &lt;a href=&quot;/2020/06/17/ghidra-brainfuck-processor-1.html&quot;&gt;previous post&lt;/a&gt; we created a processor module for a compiled version of brainfuck. Right now, it can only disassemble brainfuck binaries, but not decompile them. In this post we’ll take a look at the decompilation part of the processor module. More specifically, we’ll implement the pointer (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;gt;&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;&lt;/code&gt;) and arithmetic (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;+&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;-&lt;/code&gt;) instructions. We’ll handle the other instructions later.&lt;/p&gt;

&lt;h1 id=&quot;auto-analysis&quot;&gt;Auto analysis&lt;/h1&gt;
&lt;p&gt;Before we get to writing semantics for the instructions, let’s first address a problem from the previous post: the auto analysis does not disassemble the binary.&lt;/p&gt;

&lt;p&gt;When a binary is opened with the code browser, Ghidra asks if it should perform auto analysis on the binary. Upon clicking yes the analysis options menu opens, showing all the available analyzers for this binary. Among these is the &lt;em&gt;Disassemble Entry Points&lt;/em&gt; analyzer:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-2/images/analysis_disas_entry_points.png&quot; alt=&quot;The Disassemble Entry Points analyzer&quot; /&gt;&lt;/p&gt;

&lt;p&gt;The purpose of this analyzer is disassembling code at the entry points of the binary. If we mark address &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x0000&lt;/code&gt; as an entry point, this analyzer should automatically disassemble it when we perform the auto analysis. Marking entry points is very simple, though there is no documentation on it. Add the following code to the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;processor_spec&amp;gt;&lt;/code&gt; tag in &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;brainfuck.pspec&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-xml highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nt&quot;&gt;&amp;lt;default_symbols&amp;gt;&lt;/span&gt;
    &lt;span class=&quot;nt&quot;&gt;&amp;lt;symbol&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;name=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;start&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;address=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;rom:0x0000&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;type=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;code&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;entry=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;true&quot;&lt;/span&gt;&lt;span class=&quot;nt&quot;&gt;/&amp;gt;&lt;/span&gt;
&lt;span class=&quot;nt&quot;&gt;&amp;lt;/default_symbols&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;This creates a symbol &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;start&lt;/code&gt; (you can rename it) at address &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x0000&lt;/code&gt; and marks it as entry point. If we now delete &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;mul2.bin&lt;/code&gt; from Ghidra, reimport it&lt;sup id=&quot;fnref:reimport&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:reimport&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;1&lt;/a&gt;&lt;/sup&gt; and run the auto analysis, the binary will be decompiled automatically. The stack analyzer throws an error, because there is no stack. This is safe to ignore. (Optionally, this analyzer can be disabled in the analysis options menu.)&lt;/p&gt;

&lt;h1 id=&quot;pointer-instructions&quot;&gt;Pointer instructions&lt;/h1&gt;
&lt;p&gt;The semantics of the pointer instructions (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;gt;&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;&lt;/code&gt;) are the simplest to implement. Let’s implement the semantics of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;gt;&lt;/code&gt; first. The semantics of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;&lt;/code&gt; can be implemented very similarly.&lt;/p&gt;

&lt;p&gt;The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;gt;&lt;/code&gt; instruction adds 1 to the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ptr&lt;/code&gt; register. This can be represented using the SLEIGH operator &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;+&lt;/code&gt;&lt;sup id=&quot;fnref:sleigh_spec&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:sleigh_spec&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;2&lt;/a&gt;&lt;/sup&gt;:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;:&amp;gt; is op=0x0 {
    ptr = ptr + 1;
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The semantics for &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;&lt;/code&gt; are almost identical, except that the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;+&lt;/code&gt; is now a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;-&lt;/code&gt;:&lt;/p&gt;
&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;:&amp;lt; is op=0x1 {
    ptr = ptr - 1;
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;h1 id=&quot;arithmetic-instructions&quot;&gt;Arithmetic instructions&lt;/h1&gt;
&lt;p&gt;The arithmetic instructions (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;+&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;-&lt;/code&gt;) are slightly more complex than the pointer instructions. They do not operate on a register, but on memory (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ram&lt;/code&gt;) pointed to by the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ptr&lt;/code&gt; register. The arithmetic instructions can be broken up into three operations:&lt;/p&gt;
&lt;ol&gt;
  &lt;li&gt;Load the value of the current cell from &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ram&lt;/code&gt; into a temporary variable (let’s name it &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;c&lt;/code&gt; for cell). In SLEIGH this looks like: &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;local c:2 = *[ram]ptr;&lt;/code&gt;&lt;/li&gt;
  &lt;li&gt;Increment or decrement the cell value by one: &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;c = c + 1&lt;/code&gt; or &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;c = c - 1&lt;/code&gt;&lt;/li&gt;
  &lt;li&gt;Store the new value in the current cell: &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;*[ram]ptr = c;&lt;/code&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Thus, we have:&lt;/p&gt;
&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;:+ is op=0x2 {
    local c:2 = *[ram]ptr;
    c = c + 1;
    *[ram]ptr = c;
}

:- is op=0x3 {
    local c:2 = *[ram]ptr;
    c = c - 1;
    *[ram]ptr = c;
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;h1 id=&quot;p-code-and-varnodes&quot;&gt;P-code and varnodes&lt;/h1&gt;
&lt;p&gt;&lt;em&gt;This section covers the internal representation of instruction semantics in Ghidra. It isn’t strictly necessary to understand this in order to create a processor module, so you may skip it. I do advise you to read it though, as it can be very useful to have some knowledge of the underlying representation that Ghidra uses.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;As described in the previous post, Ghidra doesn’t use the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt; directly. Instead it uses the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.sla&lt;/code&gt; file, which is compiled from the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt; file by the SLEIGH compiler&lt;sup id=&quot;fnref:slaspec_comp&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:slaspec_comp&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;3&lt;/a&gt;&lt;/sup&gt;. The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt; is readable and human-friendly, while the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.sla&lt;/code&gt; is very verbose and more machine-friendly. Similarly, Ghidra doesn’t use SLEIGH operators and symbols directly to describe instructions, but p-code operations and varnodes.&lt;/p&gt;

&lt;p&gt;While the SLEIGH operators have a C-like syntax, p-code operations have an assembly-like syntax. Consider the following SLEIGH semantics, for example:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;local x:2;
x = 36;
x = x + 44;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;This may be translated to the following p-code&lt;sup id=&quot;fnref:pcode_ref&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:pcode_ref&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;4&lt;/a&gt;&lt;/sup&gt;:&lt;/p&gt;
&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;$U10:2 = COPY 36:2
$U10:2 = INT_ADD $U10, 44:2
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The SLEIGH compiler has created a varnode in the &lt;strong&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;unique&lt;/code&gt;&lt;/strong&gt; address space for the temporary symbol &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;x&lt;/code&gt; in the SLEIGH semantics. This varnode starts at address &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x10&lt;/code&gt;, has a size of 2 bytes and is denoted by &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;$U10&lt;/code&gt; or &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;$U10:2&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;The first operation, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;COPY&lt;/code&gt;, copies the value &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;36&lt;/code&gt; into &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;$U10&lt;/code&gt;. The second operation, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;INT_ADD&lt;/code&gt;, adds 44 to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;$U10&lt;/code&gt; and stores the result in &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;$U10&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Now that we know more about the translation from SLEIGH semantics to p-code, let’s view the generated p-code for our implemented SLEIGH semantics.&lt;/p&gt;

&lt;p&gt;If we open &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;mul2.bin&lt;/code&gt; in the code browser, we can view the p-code of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;gt;&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;+&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;-&lt;/code&gt; instructions by enabling the p-code field in the listing. First, click the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Edit the Listing fields&lt;/code&gt; button in the top right corner of the listing. The icon looks like a wall above an arrow:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-2/images/edit_listing.png&quot; alt=&quot;The 'Edit the Listing fields' button&quot; /&gt;&lt;/p&gt;

&lt;p&gt;A menu should open now. Click the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Instruction/Data&lt;/code&gt; tab:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-2/images/edit_listing_pcode.png&quot; alt=&quot;'Instruction/Data' tab in the 'Edit the Listing fields' menu&quot; /&gt;&lt;/p&gt;

&lt;p&gt;Right-click the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;PCode&lt;/code&gt; field and enable it. The listing now shows the p-code for every instruction that has p-code associated with it:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-2/images/listing.png&quot; alt=&quot;Listing with p-code&quot; /&gt;&lt;/p&gt;

&lt;p&gt;You may also enable the more verbose raw p-code. To do this go to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Edit → Tool Options...&lt;/code&gt;, then &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Listing Fields → Pcode Field&lt;/code&gt; and enable the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Display Raw Pcode&lt;/code&gt; option. The raw p-code for the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;+&lt;/code&gt; looks like this:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-2/images/raw_pcode.png&quot; alt=&quot;Raw p-code&quot; /&gt;&lt;/p&gt;

&lt;p&gt;You’ll rarely need to look at (raw) p-code during disassembly and decompilation of real-world programs. Still, it can be useful to have this field enabled during the development of a processor module, when emulating code or developing abstract analyzers. In most other cases you needn’t worry about these low-level details.&lt;/p&gt;

&lt;h1 id=&quot;decompilation&quot;&gt;Decompilation&lt;/h1&gt;
&lt;p&gt;Ghidra should now be able to decompile any brainfuck programs that use (only) the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;gt;&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;+&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;-&lt;/code&gt; instructions. Here is such a program, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;mark_uneven.bf&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-brainfuck highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nb&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span class=&quot;nf&quot;&gt;+&lt;/span&gt;&lt;span class=&quot;nb&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span class=&quot;c1&quot;&gt;
&lt;/span&gt;&lt;span class=&quot;nb&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span class=&quot;nf&quot;&gt;+&lt;/span&gt;&lt;span class=&quot;nb&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span class=&quot;c1&quot;&gt;
&lt;/span&gt;&lt;span class=&quot;nb&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span class=&quot;nf&quot;&gt;+&lt;/span&gt;&lt;span class=&quot;nb&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span class=&quot;c1&quot;&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;This program increments the first three cells that have an uneven address. It’s not particularly useful, but it only uses instructions that we have described the semantics of.&lt;/p&gt;

&lt;p&gt;We can compile it (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;./bfc.py mark_uneven.bf mark_uneven.bin&lt;/code&gt;) and load it into Ghidra. Thanks to the entry point definition in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.pspec&lt;/code&gt;, Ghidra creates a function called &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;start&lt;/code&gt; at &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x0000&lt;/code&gt; and disassembles it. When we click the function, the decompile window should show a decompilation. Unfortunately this is not what happens. What happens is that the decompiler shows an error:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-2/images/decompiler_error_stack.png&quot; alt=&quot;The decompiler shows an error&quot; /&gt;&lt;/p&gt;

&lt;p&gt;This is because of the following bug: the decompiler refers to the stack&lt;sup id=&quot;fnref:stack_ref&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:stack_ref&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;5&lt;/a&gt;&lt;/sup&gt;, but we haven’t specified one, because there is no stack in brainfuck&lt;sup id=&quot;fnref:stack_bug&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:stack_bug&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;6&lt;/a&gt;&lt;/sup&gt;. This causes the decompiler to crash. To work around this, we can create a dummy register and address space in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;define space dummy_space type=ram_space size=2 wordsize=2;
...
define register offset=0x00 size=2 [pc ptr dummy_reg];
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;We’ll use &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;dummy_space&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;dummy_reg&lt;/code&gt; anytime a register or address space is required that doesn’t exist in the brainfuck architecture. The stack pointer can be defined by adding the following code to the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;compiler_spec&amp;gt;&lt;/code&gt; tag in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.cspec&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-xml highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nt&quot;&gt;&amp;lt;stackpointer&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;register=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;dummy_reg&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;space=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;dummy_space&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;growth=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;negative&quot;&lt;/span&gt;&lt;span class=&quot;nt&quot;&gt;/&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;We’re not done yet (but almost, so don’t worry!). If we’d run the decompiler now, it would - again - show an error:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-2/images/decompiler_error_addr.png&quot; alt=&quot;The decompiler shows an error&quot; /&gt;&lt;/p&gt;

&lt;p&gt;This error is more descriptive than the previous one: the decompiler won’t decompile instructions at address &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x0000&lt;/code&gt;, because the memory hasn’t been marked as global. Any memory &lt;em&gt;not&lt;/em&gt; marked as global is assumed to be temporary. Hence, it is important that we mark &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;rom&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ram&lt;/code&gt; as global. Add the following code to the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;compiler_spec&amp;gt;&lt;/code&gt; tag in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.cspec&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-xml highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nt&quot;&gt;&amp;lt;global&amp;gt;&lt;/span&gt;
    &lt;span class=&quot;nt&quot;&gt;&amp;lt;range&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;space=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;rom&quot;&lt;/span&gt;&lt;span class=&quot;nt&quot;&gt;/&amp;gt;&lt;/span&gt;
    &lt;span class=&quot;nt&quot;&gt;&amp;lt;range&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;space=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;ram&quot;&lt;/span&gt;&lt;span class=&quot;nt&quot;&gt;/&amp;gt;&lt;/span&gt;
&lt;span class=&quot;nt&quot;&gt;&amp;lt;/global&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;While we’re at it, we can also add &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ram&lt;/code&gt; memory to the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.pspec&lt;/code&gt; so that it shows up in the program tree. (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;rom&lt;/code&gt; is already shown in the program tree, because it is the default address space.) Add this to the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;processor_spec&amp;gt;&lt;/code&gt; tag in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.pspec&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-xml highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nt&quot;&gt;&amp;lt;default_memory_blocks&amp;gt;&lt;/span&gt;
    &lt;span class=&quot;nt&quot;&gt;&amp;lt;memory_block&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;name=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;ram&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;start_address=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;ram:0x0000&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;length=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;0x1000&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;mode=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;rw&quot;&lt;/span&gt;&lt;span class=&quot;nt&quot;&gt;/&amp;gt;&lt;/span&gt;
&lt;span class=&quot;nt&quot;&gt;&amp;lt;/default_memory_blocks&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Now, the decompiler is able to decompile the binary:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-2/images/decompilation.png&quot; alt=&quot;Decompilation of mark_uneven.bin&quot; /&gt;&lt;/p&gt;

&lt;p&gt;It shows two warnings, because the function unexpectedly terminates, instead of returning, endlessly looping or calling to a non-returning function (e.g. &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;exit&lt;/code&gt;). These warnings can be safely ignored.&lt;/p&gt;

&lt;h1 id=&quot;cleaning-up-decompilation&quot;&gt;Cleaning up decompilation&lt;/h1&gt;
&lt;p&gt;The current decompilation doesn’t look very good, but we can improve it. The increments are represented in the decompilation by:&lt;/p&gt;

&lt;div class=&quot;language-c highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;short&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;in_ptr&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;+&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;x&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;short&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;*&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;in_ptr&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;+&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;x&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;+&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;This can be drastically improved by assigning an initial value to the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ptr&lt;/code&gt; register. This value is called an &lt;strong&gt;assumption&lt;/strong&gt;. Press &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ctrl + R&lt;/code&gt; on the start of the function and set the value of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ptr (16)&lt;/code&gt; to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0&lt;/code&gt;. The decompilation looks a lot better now:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-2/images/decompilation_with_assumption.png&quot; alt=&quot;Decompilation of mark_uneven.bin after assuming ptr to be 0&quot; /&gt;&lt;/p&gt;

&lt;p&gt;Instead of setting the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ptr&lt;/code&gt; value to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0&lt;/code&gt; for every brainfuck binary we want to disassemble, we can also add some code to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;processor_spec&amp;gt;&lt;/code&gt; in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;processor_spec&amp;gt;&lt;/code&gt; tag of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.pspec&lt;/code&gt; (or &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.cspec&lt;/code&gt;, which also accepts the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;context_data&amp;gt;&lt;/code&gt; tag):&lt;/p&gt;

&lt;div class=&quot;language-xml highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nt&quot;&gt;&amp;lt;context_data&amp;gt;&lt;/span&gt;
    &lt;span class=&quot;nt&quot;&gt;&amp;lt;tracked_set&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;space=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;rom&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;first=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;0x0000&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;last=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;0x0000&quot;&lt;/span&gt;&lt;span class=&quot;nt&quot;&gt;&amp;gt;&lt;/span&gt;
        &lt;span class=&quot;nt&quot;&gt;&amp;lt;set&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;name=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;ptr&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;val=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;0&quot;&lt;/span&gt;&lt;span class=&quot;nt&quot;&gt;/&amp;gt;&lt;/span&gt;
    &lt;span class=&quot;nt&quot;&gt;&amp;lt;/tracked_set&amp;gt;&lt;/span&gt;
&lt;span class=&quot;nt&quot;&gt;&amp;lt;/context_data&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;This code lets Ghidra assume that the value of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ptr&lt;/code&gt; equals &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0&lt;/code&gt; at the function starting at address &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x0000&lt;/code&gt;, also known as the entry point in this case.&lt;/p&gt;

&lt;p&gt;If we now reimport the binary, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ptr&lt;/code&gt; is automatically assumed to be &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0&lt;/code&gt; at address &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x0000&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;The final step in cleaning up the decompilation is marking the first three uneven addresses as data (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;uint16_t&lt;/code&gt; or &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ushort&lt;/code&gt;) and naming them. This results in the following readable decompilation:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-2/images/decompilation_data_marked.png&quot; alt=&quot;Decompilation of mark_uneven.bin after marking addresses as data&quot; /&gt;&lt;/p&gt;

&lt;p&gt;An even better decompilation would be the following:&lt;/p&gt;

&lt;div class=&quot;language-c highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kt&quot;&gt;void&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;start&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;void&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;){&lt;/span&gt;
    &lt;span class=&quot;n&quot;&gt;uneven_1&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;
    &lt;span class=&quot;n&quot;&gt;uneven_3&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;
    &lt;span class=&quot;n&quot;&gt;uneven_5&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;mi&quot;&gt;1&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;;&lt;/span&gt;
&lt;span class=&quot;p&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;This would require Ghidra to assume that &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ram&lt;/code&gt; is zero at address &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x0000&lt;/code&gt;. I don’t think this is possible. (I hope &lt;a href=&quot;https://meta.wikimedia.org/wiki/Cunningham%27s_Law&quot;&gt;Cunningham’s Law&lt;/a&gt; holds in this case and someone proves me wrong.)&lt;/p&gt;

&lt;p&gt;That’s it for this post. We’ve implemented decompilation of the pointer and arithmetic instructions and cleaned up the decompilation. We’ve also taken a quick look at Ghidra’s internal representation of instruction semantics (p-code). In the &lt;a href=&quot;/2020/06/17/ghidra-brainfuck-processor-3.html&quot;&gt;next post&lt;/a&gt;, we’ll complete the semantics for the brainfuck instruction set by writing code for the I/O (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;,&lt;/code&gt;) and control flow (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt;) instructions. See you then!&lt;/p&gt;

&lt;p&gt;You can find the final code for this post &lt;a href=&quot;https://github.com/spinsel/spinsel.dev/tree/master/assets/2020-06-17-ghidra-brainfuck-processor-2/source&quot;&gt;here&lt;/a&gt;.&lt;/p&gt;

&lt;h1 id=&quot;footnotes&quot;&gt;Footnotes&lt;/h1&gt;

&lt;div class=&quot;footnotes&quot; role=&quot;doc-endnotes&quot;&gt;
  &lt;ol&gt;
    &lt;li id=&quot;fn:reimport&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;From now on it is assumed that you reimport binaries everytime a change is made to the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.ldefs&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.pspec&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.cspec&lt;/code&gt; and in some cases even the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt;. &lt;a href=&quot;#fnref:reimport&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
    &lt;li id=&quot;fn:sleigh_spec&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;Refer to &lt;a href=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-1/ghidra_docs/language_spec/html/sleigh_constructors.html#sleigh_semantic_section&quot;&gt;&lt;em&gt;SLEIGH - 7.7. The Semantic Section&lt;/em&gt;&lt;/a&gt; for information on the semantics section of constructors. &lt;a href=&quot;#fnref:sleigh_spec&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
    &lt;li id=&quot;fn:slaspec_comp&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;This compilation is done automatically by Ghidra when it encounters a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt;, so there is no need for us to compile it. &lt;a href=&quot;#fnref:slaspec_comp&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
    &lt;li id=&quot;fn:pcode_ref&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;See the &lt;a href=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-1/ghidra_docs/language_spec/html/pcoderef.html&quot;&gt;&lt;em&gt;P-Code Reference Manual&lt;/em&gt;&lt;/a&gt; and &lt;a href=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-1/ghidra_docs/language_spec/html/sleigh_ref.html&quot;&gt;&lt;em&gt;SLEIGH - 9. P-code Tables&lt;/em&gt;&lt;/a&gt;, both part of the &lt;a href=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-1/ghidra_docs/language_spec/index.html&quot;&gt;&lt;em&gt;Ghidra Language Specification&lt;/em&gt;&lt;/a&gt;. &lt;a href=&quot;#fnref:pcode_ref&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
    &lt;li id=&quot;fn:stack_ref&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;The decompiler dereferences pointers to the stack space in a &lt;em&gt;lot&lt;/em&gt; of places. For example, &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Features/Decompiler/src/decompile/cpp/coreaction.cc#L1644&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;coreaction.cc:1644&lt;/code&gt;&lt;/a&gt; calls a function &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;gather&lt;/code&gt; with a pointer to the stack space. Since there is no stack space defined, this pointer is &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;NULL&lt;/code&gt;. &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;gather&lt;/code&gt; dereferences the pointer at &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Features/Decompiler/src/decompile/cpp/varmap.cc#L542&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;varmap.cc:542&lt;/code&gt;&lt;/a&gt;.  The dereference of this &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;NULL&lt;/code&gt; pointer will result in a &lt;a href=&quot;https://en.wikipedia.org/wiki/Segmentation_fault&quot;&gt;segmentation fault&lt;/a&gt;: The decompiler dies. &lt;a href=&quot;#fnref:stack_ref&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
    &lt;li id=&quot;fn:stack_bug&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;It could be argued whether this is really a bug, as virtually every architecture uses a stack. &lt;a href=&quot;#fnref:stack_bug&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
  &lt;/ol&gt;
&lt;/div&gt;
</description>
        <pubDate>Wed, 17 Jun 2020 00:00:00 +0000</pubDate>
        <link>https://spinsel.dev/2020/06/17/ghidra-brainfuck-processor-2.html</link>
        <guid isPermaLink="true">https://spinsel.dev/2020/06/17/ghidra-brainfuck-processor-2.html</guid>
        
        <category>Ghidra</category>
        
        
      </item>
    
      <item>
        <title>Implementing a brainfuck CPU in Ghidra - part 1: Setup and disassembly</title>
        <description>&lt;div class=&quot;blog-post-series-block&quot;&gt;This blog post is part of the series &lt;i&gt;Implementing a brainfuck CPU in Ghidra&lt;/i&gt;:

    &lt;ol&gt;&lt;li&gt;&lt;b&gt; Setup and disassembly (current post)&lt;/b&gt;&lt;/li&gt;&lt;li&gt;&lt;a href=&quot;/2020/06/17/ghidra-brainfuck-processor-2.html&quot;&gt; Decompilation of pointer and arithmetic instructions&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href=&quot;/2020/06/17/ghidra-brainfuck-processor-3.html&quot;&gt; Decompilation of I/O and control flow instructions&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href=&quot;/2020/07/27/ghidra-brainfuck-processor-4.html&quot;&gt; Renaming the analyzer and adding a manual&lt;/a&gt;&lt;/li&gt;&lt;li&gt;Recognizing common patterns (future post)&lt;/li&gt;&lt;/ol&gt;&lt;p&gt;More posts may be added to this series in the future.&lt;/p&gt;&lt;/div&gt;
&lt;p&gt;Ghidra supports quite some processors out of the box, but if you come across a somewhat obscure architecture, chances are you’ll have to write the processor module yourself (if someone else hasn’t published it on the internet already). At first glance, it may seem daunting: it’s not clear where to start and the documentation is often lacking. That’s why I decided to write this blog post series. The goal is to create a Ghidra processor module for a compiled version of the esoteric programming language brainfuck, from scratch. The sources I used are the &lt;em&gt;Ghidra Language Specification&lt;/em&gt;&lt;sup id=&quot;fnref:lang_spec&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:lang_spec&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;1&lt;/a&gt;&lt;/sup&gt;, the &lt;em&gt;Compiler Specification&lt;/em&gt;&lt;sup id=&quot;fnref:comp_spec&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:comp_spec&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;2&lt;/a&gt;&lt;/sup&gt; and the source code&lt;sup id=&quot;fnref:ghidra_git&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:ghidra_git&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;3&lt;/a&gt;&lt;/sup&gt;.&lt;/p&gt;

&lt;h1 id=&quot;brainfuck&quot;&gt;Brainfuck&lt;/h1&gt;
&lt;p&gt;Brainfuck is a very minimal language consisting of only eight instructions. See the &lt;a href=&quot;https://en.wikipedia.org/wiki/Brainfuck#Language_design&quot;&gt;wikipedia page&lt;/a&gt; for a full description of the language. My brainfuck variant deviates slightly from the original:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;The memory array is called &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ram&lt;/code&gt; memory and consists of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x10000&lt;/code&gt; 16-bit cells. The pointer &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ptr&lt;/code&gt; (16-bit) points to the current cell.&lt;/li&gt;
  &lt;li&gt;
    &lt;p&gt;Instructions are compiled to a binary format, using the following translation table:&lt;/p&gt;

    &lt;table class=&quot;small-table&quot;&gt;
      &lt;thead&gt;
        &lt;tr&gt;
          &lt;th&gt;Instruction&lt;/th&gt;
          &lt;th&gt;Opcode&lt;/th&gt;
        &lt;/tr&gt;
      &lt;/thead&gt;
      &lt;tbody&gt;
        &lt;tr&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;gt;&lt;/code&gt;&lt;/td&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x0&lt;/code&gt;&lt;/td&gt;
        &lt;/tr&gt;
        &lt;tr&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;&lt;/code&gt;&lt;/td&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x1&lt;/code&gt;&lt;/td&gt;
        &lt;/tr&gt;
        &lt;tr&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;+&lt;/code&gt;&lt;/td&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x2&lt;/code&gt;&lt;/td&gt;
        &lt;/tr&gt;
        &lt;tr&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;-&lt;/code&gt;&lt;/td&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x3&lt;/code&gt;&lt;/td&gt;
        &lt;/tr&gt;
        &lt;tr&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.&lt;/code&gt;&lt;/td&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x4&lt;/code&gt;&lt;/td&gt;
        &lt;/tr&gt;
        &lt;tr&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;,&lt;/code&gt;&lt;/td&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x5&lt;/code&gt;&lt;/td&gt;
        &lt;/tr&gt;
        &lt;tr&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;[&lt;/code&gt;&lt;/td&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x6&lt;/code&gt;&lt;/td&gt;
        &lt;/tr&gt;
        &lt;tr&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;]&lt;/code&gt;&lt;/td&gt;
          &lt;td&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x7&lt;/code&gt;&lt;/td&gt;
        &lt;/tr&gt;
      &lt;/tbody&gt;
    &lt;/table&gt;

    &lt;p&gt;Compiled instructions are 8-bit wide. The four least significant bits make up the opcode, the other bits are unspecified and should be set to zero.&lt;/p&gt;
  &lt;/li&gt;
  &lt;li&gt;Compiled instructions live in &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;rom&lt;/code&gt; memory. The program counter &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;pc&lt;/code&gt; (16-bit) points to the current instruction.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;I created a simple brainfuck compiler (&lt;a href=&quot;https://github.com/spinsel/spinsel.dev/tree/master/assets/2020-06-17-ghidra-brainfuck-processor-1/source/brainfuck/bfc.py&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;bfc.py&lt;/code&gt;&lt;/a&gt;) that takes a brainfuck file and outputs a binary. Non-instruction characters (anything but &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;gt;&amp;lt;+-.,[]&lt;/code&gt;) are interpreted as comments and will not be compiled. I didn’t bother to write a VM that executes compiled brainfuck, although it wouldn’t be hard to write yourself. (If you do, I’d love to see it.)&lt;/p&gt;

&lt;p&gt;Let’s compile a simple program to see the compiler in action. &lt;a href=&quot;https://github.com/spinsel/spinsel.dev/tree/master/assets/2020-06-17-ghidra-brainfuck-processor-1/source/brainfuck/mul2.bf&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;mul2.bf&lt;/code&gt;&lt;/a&gt; takes some user input, multiplies it by two and prints the result. The source code is as follows:&lt;/p&gt;

&lt;div class=&quot;language-brainfuck highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nf&quot;&gt;,&lt;/span&gt;&lt;span class=&quot;c1&quot;&gt;          store user input in #0
&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;[&lt;/span&gt;&lt;span class=&quot;nb&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span class=&quot;nf&quot;&gt;++&lt;/span&gt;&lt;span class=&quot;nb&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span class=&quot;nf&quot;&gt;-&lt;/span&gt;&lt;span class=&quot;p&quot;&gt;]&lt;/span&gt;&lt;span class=&quot;c1&quot;&gt;    #1 = #0 * 2
&lt;/span&gt;&lt;span class=&quot;nb&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span class=&quot;nf&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;c1&quot;&gt;         move to #1 and print its content
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Compile it to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;mul2.bin&lt;/code&gt; and show the generated binary:&lt;/p&gt;

&lt;div class=&quot;language-bash highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nv&quot;&gt;$ &lt;/span&gt;./bfc.py mul2.bf mul2.bin
&lt;span class=&quot;nv&quot;&gt;$ &lt;/span&gt;hexdump &lt;span class=&quot;nt&quot;&gt;-C&lt;/span&gt; mul2.bin
00000000  05 06 00 02 02 01 03 07  00 04                    |..........|
0000000a
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The rest of this blog post series will be dedicated to reversing and analyzing compiled brainfuck binaries like &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;mul2.bin&lt;/code&gt;.&lt;/p&gt;

&lt;h1 id=&quot;preparation&quot;&gt;Preparation&lt;/h1&gt;
&lt;p&gt;We’ll be using &lt;a href=&quot;https://www.eclipse.org/downloads/&quot;&gt;Eclipse&lt;/a&gt; to create the processor module. After installing Eclipse, we’re ready to add the GhidraDev extension to Eclipse. The extension can be found in &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Extensions/Eclipse/GhidraDev/&lt;/code&gt; in the Ghidra installation directory, along with some documentation on how to install this extension. The extension can be added by opening the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Help → Install New Software...&lt;/code&gt; menu in Eclipse and selecting the GhidraDev zip. The documentation covers this in more detail.&lt;/p&gt;

&lt;p&gt;Although we’re using Eclipse for development, you can use any other IDE of your preference for &lt;em&gt;editing&lt;/em&gt; the files. I recommend VS Code with the &lt;a href=&quot;https://marketplace.visualstudio.com/items?itemName=CarloMaragno.sleighighlight&quot;&gt;SleigHighlight&lt;/a&gt; extension for syntax highlighting of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt; files. XML syntax highlighting of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.ldefs&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.pspec&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.cspec&lt;/code&gt; files is done in VS Code by marking them as XML in the bottom right corner. This is not required, it just eases the development of processor modules.&lt;/p&gt;

&lt;h1 id=&quot;creating-a-project&quot;&gt;Creating a project&lt;/h1&gt;

&lt;p&gt;Create a new project by going to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;File → New → Project&lt;/code&gt; and select the Ghidra Module Project wizard 🧙.&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-1/images/project_wizard.png&quot; alt=&quot;Expand the Ghidra folder and select Ghidra Module Project&quot; title=&quot;Select the Ghidra Module Project wizard&quot; /&gt;&lt;/p&gt;

&lt;p&gt;Specify a name and directory for this project and hit next. The next screen lets us choose the components we want the wizard to add to our project. We only need the analyzer and the processor. Disable the others.&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-1/images/project_template.png&quot; alt=&quot;&quot; title=&quot;Select the analyzer and processor&quot; /&gt;&lt;/p&gt;

&lt;p&gt;If you haven’t used Eclipse with Ghidra before, you’ll need to specify the root directory of your Ghidra installation and hit next. The last step lets us enable Python support. We don’t need this, so leave the checkbox unchecked.&lt;/p&gt;

&lt;p&gt;Then hit finish. We’ve now created our Ghidra project!&lt;/p&gt;

&lt;h1 id=&quot;creating-the-language-definitions&quot;&gt;Creating the language definitions&lt;/h1&gt;
&lt;p&gt;The processor lives in &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;data/languages&lt;/code&gt;. The wizard has already populated this folder with definitions for the (hypothetical) skel processor, which are of no use to us. Delete these files.&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-1/images/languages_content.png&quot; alt=&quot;&quot; title=&quot;Delete the skel processor definitions&quot; /&gt;&lt;/p&gt;

&lt;p&gt;In Ghidra you don’t define processors, but languages instead. A &lt;strong&gt;language&lt;/strong&gt; specifies a variant of a processor family. For example, &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Processors/x86/data/languages/x86.ldefs&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;x86.ldefs&lt;/code&gt;&lt;/a&gt; contains specifications for 16-bit, 32-bit and 64-bit variants of the x86 processor architecture. Ghidra interprets all files with an &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.ldefs&lt;/code&gt; extension as a language definitions file&lt;sup id=&quot;fnref:lang_prov&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:lang_prov&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;4&lt;/a&gt;&lt;/sup&gt;. The format of this file is not really documented, but there is an XML schema file (written in &lt;a href=&quot;https://en.wikipedia.org/wiki/RELAX_NG&quot;&gt;RELAX NG&lt;/a&gt;) that describes the structure of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.ldefs&lt;/code&gt; files: &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Framework/SoftwareModeling/data/languages/language_definitions.rxg&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;language_definitions.rxg&lt;/code&gt;&lt;/a&gt;. Using this schema we can compose &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;brainfuck.ldefs&lt;/code&gt; (create a new file using &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Right click on languages → New → File&lt;/code&gt;):&lt;/p&gt;

&lt;div class=&quot;language-xml highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;cp&quot;&gt;&amp;lt;?xml version=&quot;1.0&quot; encoding=&quot;UTF-8&quot;?&amp;gt;&lt;/span&gt;

&lt;span class=&quot;nt&quot;&gt;&amp;lt;language_definitions&amp;gt;&lt;/span&gt;
    &lt;span class=&quot;nt&quot;&gt;&amp;lt;language&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;processor=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;brainfuck&quot;&lt;/span&gt;
              &lt;span class=&quot;na&quot;&gt;endian=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;little&quot;&lt;/span&gt;
              &lt;span class=&quot;na&quot;&gt;size=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;16&quot;&lt;/span&gt;
              &lt;span class=&quot;na&quot;&gt;variant=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;default&quot;&lt;/span&gt;
              &lt;span class=&quot;na&quot;&gt;version=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;1.0&quot;&lt;/span&gt;
              &lt;span class=&quot;na&quot;&gt;slafile=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;brainfuck.sla&quot;&lt;/span&gt;
              &lt;span class=&quot;na&quot;&gt;processorspec=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;brainfuck.pspec&quot;&lt;/span&gt;
              &lt;span class=&quot;na&quot;&gt;id=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;brainfuck:2:default&quot;&lt;/span&gt;&lt;span class=&quot;nt&quot;&gt;&amp;gt;&lt;/span&gt;
        &lt;span class=&quot;nt&quot;&gt;&amp;lt;description&amp;gt;&lt;/span&gt;brainfuck&lt;span class=&quot;nt&quot;&gt;&amp;lt;/description&amp;gt;&lt;/span&gt;
        &lt;span class=&quot;nt&quot;&gt;&amp;lt;compiler&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;name=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;default&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;spec=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;brainfuck.cspec&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;id=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;default&quot;&lt;/span&gt;&lt;span class=&quot;nt&quot;&gt;/&amp;gt;&lt;/span&gt;
    &lt;span class=&quot;nt&quot;&gt;&amp;lt;/language&amp;gt;&lt;/span&gt;
&lt;span class=&quot;nt&quot;&gt;&amp;lt;/language_definitions&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;There is only one variant of the brainfuck processor, so we only specify one language. The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;language&amp;gt;&lt;/code&gt; tag has a few required attributes that define the most important properties of the processor variant. One thing to note is the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;processorspec&lt;/code&gt; attribute. This attribute points to a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.pspec&lt;/code&gt; file, which specifies the processor. The file specified in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.sla&lt;/code&gt; file is responsible for providing Ghidra information about the disassembly and decompilation of machine code. Optionally, you can add a processor manual using the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;manualindexfile&lt;/code&gt; attribute. This will be covered in a future post.&lt;/p&gt;

&lt;p&gt;A &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;language&amp;gt;&lt;/code&gt; tag must contain a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;description&amp;gt;&lt;/code&gt; subtag and at least one &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;compiler&amp;gt;&lt;/code&gt; subtag (but you may specify more). The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;compiler&amp;gt;&lt;/code&gt; tag points to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;brainfuck.cspec&lt;/code&gt;, which describes specific information about the compiler. There are some other tags you can include, but they are not interesting for now.&lt;/p&gt;

&lt;h1 id=&quot;the-processor-specification&quot;&gt;The processor specification&lt;/h1&gt;
&lt;p&gt;The structure of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.pspec&lt;/code&gt; file is described by &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Framework/SoftwareModeling/data/languages/processor_spec.rxg&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;processor_spec.rxg&lt;/code&gt;&lt;/a&gt;. There is no official documentation. The file can contain a bunch of tags describing the memory and registers of the processor, all of which are optional. We’ll leave it empty for now:&lt;/p&gt;

&lt;div class=&quot;language-xml highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;cp&quot;&gt;&amp;lt;?xml version=&quot;1.0&quot; encoding=&quot;UTF-8&quot;?&amp;gt;&lt;/span&gt;

&lt;span class=&quot;nt&quot;&gt;&amp;lt;processor_spec&amp;gt;&lt;/span&gt;
&lt;span class=&quot;nt&quot;&gt;&amp;lt;/processor_spec&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;h1 id=&quot;the-compiler-specification&quot;&gt;The compiler specification&lt;/h1&gt;
&lt;p&gt;The layout and purpose of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.cspec&lt;/code&gt; file is pretty well&lt;sup id=&quot;fnref:cspec_doc_note&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:cspec_doc_note&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;5&lt;/a&gt;&lt;/sup&gt; documented in the &lt;em&gt;Compiler Specification&lt;/em&gt;:&lt;/p&gt;

&lt;blockquote&gt;
  &lt;p&gt;The compiler specification is a required part of a Ghidra language module for supporting disassembly and analysis of a particular processor. Its purpose is to encode information about a target binary which is specific to the compiler that generated that binary. Within Ghidra, the SLEIGH specification allows the decoding of machine instructions for a particular processor, like Intel x86, but more than one compiler can produce those instructions. For a particular target binary, understanding details about the specific compiler used to build it is important to the reverse engineering process. The compiler specification fills this need, allowing concepts like parameter passing conventions and stack mechanisms to be formally described.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Only the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;lt;default_proto&amp;gt;&lt;/code&gt; tag is required. This tag describes the default calling convention (&lt;strong&gt;prototype&lt;/strong&gt;) for this compiler. Brainfuck has branches, but it doesn’t have calls, so there is not really a prototype. We create a prototype as minimal as possible:&lt;/p&gt;

&lt;div class=&quot;language-xml highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;cp&quot;&gt;&amp;lt;?xml version=&quot;1.0&quot; encoding=&quot;UTF-8&quot;?&amp;gt;&lt;/span&gt;

&lt;span class=&quot;nt&quot;&gt;&amp;lt;compiler_spec&amp;gt;&lt;/span&gt;
    &lt;span class=&quot;nt&quot;&gt;&amp;lt;default_proto&amp;gt;&lt;/span&gt;
        &lt;span class=&quot;nt&quot;&gt;&amp;lt;prototype&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;name=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;default&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;extrapop=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;unknown&quot;&lt;/span&gt; &lt;span class=&quot;na&quot;&gt;stackshift=&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;0&quot;&lt;/span&gt;&lt;span class=&quot;nt&quot;&gt;&amp;gt;&lt;/span&gt;
            &lt;span class=&quot;nt&quot;&gt;&amp;lt;input&amp;gt;&amp;lt;/input&amp;gt;&lt;/span&gt;
            &lt;span class=&quot;nt&quot;&gt;&amp;lt;output&amp;gt;&amp;lt;/output&amp;gt;&lt;/span&gt;
        &lt;span class=&quot;nt&quot;&gt;&amp;lt;/prototype&amp;gt;&lt;/span&gt;
    &lt;span class=&quot;nt&quot;&gt;&amp;lt;/default_proto&amp;gt;&lt;/span&gt;
&lt;span class=&quot;nt&quot;&gt;&amp;lt;/compiler_spec&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Be sure to read the &lt;em&gt;Compiler Specification&lt;/em&gt; and &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Framework/SoftwareModeling/data/languages/compiler_spec.rxg&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;compiler_spec.rxg&lt;/code&gt;&lt;/a&gt; for more detailed information.&lt;/p&gt;

&lt;h1 id=&quot;the-language-specification&quot;&gt;The language specification&lt;/h1&gt;
&lt;p&gt;The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.sla&lt;/code&gt; file describes the instruction set and makes it possible for Ghidra to disassemble and decompile binaries. The file contains information for both disassembly and decompilation. The file describes the translation from machine code to a textual representation of each instruction (mnemonic, operands, etc.) for the disassembly. It also describes how these instructions affect memory and registers using an intermediate language called &lt;strong&gt;p-code&lt;/strong&gt;. P-code operations operate on &lt;strong&gt;varnodes&lt;/strong&gt;, which are generalizations of memory. A CPU register is a varnode, as well as a word or halfword in memory. The information in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.sla&lt;/code&gt; is used by the decompiler to construct the decompiled code.&lt;/p&gt;

&lt;p&gt;Writing &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.sla&lt;/code&gt; files manually is very tedious. (Just look at &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;6502.sla&lt;/code&gt; if you don’t believe me.) Luckily, you don’t have to write &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.sla&lt;/code&gt; files by hand. You can write &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt; files instead, which are much more pleasant to write and maintain. (Compare &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;6502.slaspec&lt;/code&gt; to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;6502.sla&lt;/code&gt; in terms of readability.) These &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt; files are automatically compiled to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.sla&lt;/code&gt; files by Ghidra.&lt;/p&gt;

&lt;p&gt;The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt; is very well documented by the &lt;em&gt;Ghidra Language Specification&lt;/em&gt;, so I will not go too deeply into the syntax of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt;. Refer to the official specification for that.&lt;/p&gt;

&lt;p&gt;The very first step is to create &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;brainfuck.slaspec&lt;/code&gt;. Ghidra will compile this to &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;brainfuck.sla&lt;/code&gt;, which is referred to by the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.ldefs&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.slaspec&lt;/code&gt; files always start by defining the endianness of the processor, usually followed by an instruction alignment definition. The brainfuck processor is little endian and instructions are aligned to a 1-byte boundary (which is equivalent to no alignment, but let’s define it anyway):&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;define endian=little;
define alignment=1;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The next step is to define the address spaces:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;define space register  type=register_space  size=2  wordsize=2;
define space ram       type=ram_space       size=2  wordsize=2;
define space rom       type=ram_space       size=2  wordsize=1  default;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;This is rather straightforward, except for one thing: the &lt;em&gt;Ghidra Language Specification&lt;/em&gt; mentions the space type &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;rom_space&lt;/code&gt;, but this type does not exist&lt;sup id=&quot;fnref:rom_space&quot; role=&quot;doc-noteref&quot;&gt;&lt;a href=&quot;#fn:rom_space&quot; class=&quot;footnote&quot; rel=&quot;footnote&quot;&gt;6&lt;/a&gt;&lt;/sup&gt;. Using this space type will result in a crash. That’s why &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;rom&lt;/code&gt; is defined as &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ram_space&lt;/code&gt;, instead of &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;rom_space&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;rom&lt;/code&gt; space is marked as default. This causes the binary to be loaded into the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;rom&lt;/code&gt; space. Note that the registers get their own address space.&lt;/p&gt;

&lt;p&gt;Then we define registers in the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;register&lt;/code&gt; space:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;define register offset=0x00 size=2 [pc ptr];
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;We can refer to these defined address spaces and registers in the instructions, but before we can define those instructions, we have to define a token. A &lt;strong&gt;token&lt;/strong&gt; specifies the layout of an instruction or a part of it (in variable length instructions). Instructions in the brainfuck instruction set are very simple. The four least significant bits ([0,3]) define the opcode of the instruction. The other bits are undefined. Our token looks like this:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;define token instr(8)
    op = (0, 3)
;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;We can now finally define the instructions themselves. For now we’ll only define the translation from machine code to the textual representation (disassembly) and not their semantics (decompilation). This is very simple. The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;gt;&lt;/code&gt; instruction looks like this:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;:&amp;gt; is op=0x0 {}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Let’s break this down. The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;:&lt;/code&gt; indicates that this ‘translation’, more formally called a &lt;strong&gt;constructor&lt;/strong&gt;, should be added to the root instruction table. All instructions live in this table. Subtables can be used for constructing more complex instructions, which you can read about in the &lt;em&gt;Ghidra Language Specification&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;After the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;:&lt;/code&gt; comes the textual representation, formally called the &lt;strong&gt;display section&lt;/strong&gt;, of the instruction. For this instruction, this is simply &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;gt;&lt;/code&gt;. If an instruction has operands they can also be specified here (&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;add op1, op2&lt;/code&gt;, for example).&lt;/p&gt;

&lt;p&gt;The display section is followed by the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;is&lt;/code&gt; keyword, which itself is followed by the &lt;strong&gt;bit pattern section&lt;/strong&gt;. The bit pattern section is used to match the bits of the machine code to constructors. The bit pattern section for this instruction (and all other brainfuck instructions) consists of one constrain: the opcode is &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;0x0&lt;/code&gt;. No more is needed to identify the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;&amp;gt;&lt;/code&gt; instruction.&lt;/p&gt;

&lt;p&gt;Constructors end with a semantic section, surrounded by curly braces ({}). This section describes how instructions manipulate memory and registers. We leave it empty for now.&lt;/p&gt;

&lt;p&gt;All constructors for compiled brainfuck instructions can be defined like this:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;:&amp;gt; is op=0x0 {}
:&amp;lt; is op=0x1 {}

:+ is op=0x2 {}
:- is op=0x3 {}

:. is op=0x4 {}
:, is op=0x5 {}

:[ is op=0x6 {}
:] is op=0x7 {}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;h1 id=&quot;testing&quot;&gt;Testing&lt;/h1&gt;
&lt;p&gt;This is all that’s needed to describe the language, processor, compiler and instruction set. We can now test it. Hit the debug button in the toolbar to start a debugged instance of Ghidra with our module automatically loaded in.&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-1/images/debug_menu.png&quot; alt=&quot;&quot; title=&quot;Hit the bug-like icon to start a debugging session&quot; /&gt;&lt;/p&gt;

&lt;p&gt;Create a new project in Ghidra and give it a name. Now we need a brainfuck file to disassemble. I’ll be using the previously generated &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;mul2.bin&lt;/code&gt;. Drag the binary into Ghidra and open it with the code browser. Ghidra asks if it should analyze the file. It doesn’t matter whether you choose yes or no, because we haven’t told Ghidra how to auto-analyze brainfuck binaries. Nothing will happen if you click yes.&lt;/p&gt;

&lt;p&gt;The listing view shows the bytes of our binary. To disassemble them press &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;D&lt;/code&gt; at the first address. The listing will now show the disassembly of our binary, which should look similar to this:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-1/images/disassembly.png&quot; alt=&quot;&quot; title=&quot;Disassembly of our brainfuck binary&quot; /&gt;&lt;/p&gt;

&lt;p&gt;Hooray! We’ve now created an overcomplicated brainfuck disassembler that could be replaced by a few lines of python code. This seems like a huge overkill, but in the &lt;a href=&quot;/2020/06/17/ghidra-brainfuck-processor-2.html&quot;&gt;next post&lt;/a&gt; we’ll look at getting the decompiler to work so we can do some real reversing on brainfuck binaries. See you then!&lt;/p&gt;

&lt;p&gt;You can find the final code for this post &lt;a href=&quot;https://github.com/spinsel/spinsel.dev/tree/master/assets/2020-06-17-ghidra-brainfuck-processor-1/source&quot;&gt;here&lt;/a&gt;.&lt;/p&gt;

&lt;h1 id=&quot;footnotes&quot;&gt;Footnotes&lt;/h1&gt;

&lt;div class=&quot;footnotes&quot; role=&quot;doc-endnotes&quot;&gt;
  &lt;ol&gt;
    &lt;li id=&quot;fn:lang_spec&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;See &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;docs/languages/&lt;/code&gt; in your Ghidra installation. Online (compiled) version available &lt;a href=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-1/ghidra_docs/language_spec/index.html&quot;&gt;here&lt;/a&gt;. &lt;a href=&quot;#fnref:lang_spec&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
    &lt;li id=&quot;fn:comp_spec&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;See &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/tree/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Features/Decompiler/src/main/doc&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Ghidra/Features/Decompiler/​src/main/doc/&lt;/code&gt;&lt;/a&gt; in the source code. You’ll have to compile these yourself (see &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/issues/472&quot;&gt;issue #472&lt;/a&gt;). Online (compiled) version available &lt;a href=&quot;/assets/2020-06-17-ghidra-brainfuck-processor-1/ghidra_docs/compiler_spec/index.html&quot;&gt;here&lt;/a&gt;. &lt;a href=&quot;#fnref:comp_spec&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
    &lt;li id=&quot;fn:ghidra_git&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;&lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/commit/eaf6ab250df63652cd455f0c051ce7e03f4f641b&quot;&gt;NationalSecurityAgency/ghidra on GitHub, commit &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;eaf6ab2&lt;/code&gt;&lt;/a&gt;. It may not be the latest commit by the time you’re reading this. &lt;a href=&quot;#fnref:ghidra_git&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
    &lt;li id=&quot;fn:lang_prov&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;The &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/app/plugin/processors/sleigh/SleighLanguageProvider.java#L40&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;SleighLanguageProvider&lt;/code&gt;&lt;/a&gt; is responsible for &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/app/plugin/processors/sleigh/SleighLanguageProvider.java#L73&quot;&gt;finding&lt;/a&gt; and &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/app/plugin/processors/sleigh/SleighLanguageProvider.java#L80&quot;&gt;parsing&lt;/a&gt; these &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;.ldefs&lt;/code&gt; files. &lt;a href=&quot;#fnref:lang_prov&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
    &lt;li id=&quot;fn:cspec_doc_note&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;AFAIK, the following valid tags are not documented in the &lt;em&gt;Compiler Specification&lt;/em&gt;: &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;spacebase&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;deadcodedelay&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;segmentop&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;resolveprototype&lt;/code&gt;, &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;eval_current_prototype&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;eval_called_prototype&lt;/code&gt;. Some of them are documented elsewhere. There might be other subtle differences between the docs and the code. &lt;a href=&quot;#fnref:cspec_doc_note&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
    &lt;li id=&quot;fn:rom_space&quot; role=&quot;doc-endnote&quot;&gt;
      &lt;p&gt;See &lt;a href=&quot;https://github.com/NationalSecurityAgency/ghidra/blob/eaf6ab250df63652cd455f0c051ce7e03f4f641b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/pcodeCPort/slgh_compile/space_class.java#L21&quot;&gt;&lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;space_class.java&lt;/code&gt;&lt;/a&gt;. Only &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;register_space&lt;/code&gt; and &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;ram_space&lt;/code&gt; are defined. &lt;a href=&quot;#fnref:rom_space&quot; class=&quot;reversefootnote&quot; role=&quot;doc-backlink&quot;&gt;&amp;#8617;&lt;/a&gt;&lt;/p&gt;
    &lt;/li&gt;
  &lt;/ol&gt;
&lt;/div&gt;
</description>
        <pubDate>Wed, 17 Jun 2020 00:00:00 +0000</pubDate>
        <link>https://spinsel.dev/2020/06/17/ghidra-brainfuck-processor-1.html</link>
        <guid isPermaLink="true">https://spinsel.dev/2020/06/17/ghidra-brainfuck-processor-1.html</guid>
        
        <category>Ghidra</category>
        
        
      </item>
    
  </channel>
</rss>
