summaryrefslogtreecommitdiff
path: root/Content/posts/2023-10-04-bomb-lab.md
diff options
context:
space:
mode:
Diffstat (limited to 'Content/posts/2023-10-04-bomb-lab.md')
-rw-r--r--Content/posts/2023-10-04-bomb-lab.md181
1 files changed, 181 insertions, 0 deletions
diff --git a/Content/posts/2023-10-04-bomb-lab.md b/Content/posts/2023-10-04-bomb-lab.md
new file mode 100644
index 0000000..4919f61
--- /dev/null
+++ b/Content/posts/2023-10-04-bomb-lab.md
@@ -0,0 +1,181 @@
+---
+date: 2023-10-04 13:12
+description: Introduction, Phase 1 and Phase 2 of Bomb Lab for CSCI 2400 Lab - 2
+tags: gdb, reverse-engineering, c++, csci2400, assembly
+---
+
+# Bomb Lab
+
+## Introduction
+
+Lab 2 for CSCI 2400 - Computer Systems.
+
+## Phase 1
+
+```
+jovyan@jupyter-nach6988:~/lab2-bomblab-navanchauhan/bombbomb$ gdb -ex 'break phase_1' -ex 'break explode_bomb' -ex 'run' ./bomb
+GNU gdb (Ubuntu 12.1-0ubuntu1~22.04) 12.1
+Copyright (C) 2022 Free Software Foundation, Inc.
+License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
+This is free software: you are free to change and redistribute it.
+There is NO WARRANTY, to the extent permitted by law.
+Type "show copying" and "show warranty" for details.
+This GDB was configured as "x86_64-linux-gnu".
+Type "show configuration" for configuration details.
+For bug reporting instructions, please see:
+<https://www.gnu.org/software/gdb/bugs/>.
+Find the GDB manual and other documentation resources online at:
+ <http://www.gnu.org/software/gdb/documentation/>.
+
+For help, type "help".
+Type "apropos word" to search for commands related to "word"...
+Reading symbols from ./bomb...
+Breakpoint 1 at 0x15c7
+Breakpoint 2 at 0x1d4a
+Starting program: /home/jovyan/lab2-bomblab-navanchauhan/bombbomb/bomb
+[Thread debugging using libthread_db enabled]
+Using host libthread_db library "/lib/x86_64-linux-gnu/libthread_db.so.1".
+Welcome to my fiendish little bomb. You have 6 phases with
+which to blow yourself up. Have a nice day!
+test string
+
+Breakpoint 1, 0x00005555555555c7 in phase_1 ()
+(gdb) dias phase_1
+Undefined command: "dias". Try "help".
+(gdb) disas phase_1
+Dump of assembler code for function phase_1:
+=> 0x00005555555555c7 <+0>: endbr64
+ 0x00005555555555cb <+4>: sub $0x8,%rsp
+ 0x00005555555555cf <+8>: lea 0x1b7a(%rip),%rsi # 0x555555557150
+ 0x00005555555555d6 <+15>: call 0x555555555b31 <strings_not_equal>
+ 0x00005555555555db <+20>: test %eax,%eax
+ 0x00005555555555dd <+22>: jne 0x5555555555e4 <phase_1+29>
+ 0x00005555555555df <+24>: add $0x8,%rsp
+ 0x00005555555555e3 <+28>: ret
+ 0x00005555555555e4 <+29>: call 0x555555555d4a <explode_bomb>
+ 0x00005555555555e9 <+34>: jmp 0x5555555555df <phase_1+24>
+End of assembler dump.
+(gdb) print 0x555555557150
+$1 = 93824992244048
+(gdb) x/1s 0x555555557150
+0x555555557150: "Controlling complexity is the essence of computer programming."
+(gdb)
+```
+
+## Phase 2
+
+```
+Phase 1 defused. How about the next one?
+1 2 3 4 5 6
+
+Breakpoint 1, 0x00005555555555eb in phase_2 ()
+(gdb) disas
+Dump of assembler code for function phase_2:
+=> 0x00005555555555eb <+0>: endbr64
+ 0x00005555555555ef <+4>: push %rbp
+ 0x00005555555555f0 <+5>: push %rbx
+ 0x00005555555555f1 <+6>: sub $0x28,%rsp
+ 0x00005555555555f5 <+10>: mov %rsp,%rsi
+ 0x00005555555555f8 <+13>: call 0x555555555d97 <read_six_numbers>
+ 0x00005555555555fd <+18>: cmpl $0x0,(%rsp)
+ 0x0000555555555601 <+22>: js 0x55555555560d <phase_2+34>
+ 0x0000555555555603 <+24>: mov %rsp,%rbp
+ 0x0000555555555606 <+27>: mov $0x1,%ebx
+ 0x000055555555560b <+32>: jmp 0x555555555620 <phase_2+53>
+ 0x000055555555560d <+34>: call 0x555555555d4a <explode_bomb>
+ 0x0000555555555612 <+39>: jmp 0x555555555603 <phase_2+24>
+ 0x0000555555555614 <+41>: add $0x1,%ebx
+ 0x0000555555555617 <+44>: add $0x4,%rbp
+ 0x000055555555561b <+48>: cmp $0x6,%ebx
+ 0x000055555555561e <+51>: je 0x555555555631 <phase_2+70>
+ 0x0000555555555620 <+53>: mov %ebx,%eax
+ 0x0000555555555622 <+55>: add 0x0(%rbp),%eax
+ 0x0000555555555625 <+58>: cmp %eax,0x4(%rbp)
+ 0x0000555555555628 <+61>: je 0x555555555614 <phase_2+41>
+ 0x000055555555562a <+63>: call 0x555555555d4a <explode_bomb>
+ 0x000055555555562f <+68>: jmp 0x555555555614 <phase_2+41>
+ 0x0000555555555631 <+70>: add $0x28,%rsp
+ 0x0000555555555635 <+74>: pop %rbx
+ 0x0000555555555636 <+75>: pop %rbp
+ 0x0000555555555637 <+76>: ret
+End of assembler dump.
+(gdb)
+```
+
+```
+ 0x00005555555555fd <+18>: cmpl $0x0,(%rsp)
+ 0x0000555555555601 <+22>: js 0x55555555560d <phase_2+34>
+...
+ 0x000055555555560d <+34>: call 0x555555555d4a <explode_bomb>
+```
+
+The program first compares if the first number is not 0. If the number is not 0, then the `cmpl` instruction returns a negative value. The `js` instruction stands for jump if sign -> causing a jump to the specified address if the sign bit is set. This would result in the explode_bomb function being called.
+
+
+```
+ 0x0000555555555603 <+24>: mov %rsp,%rbp
+ 0x0000555555555606 <+27>: mov $0x1,%ebx
+```
+
+`%rsp` in x86-64 asm, is the stack pointer i.e. it points to the top of the current stack frame. Since the program just read six numbers, the top of the stack (`%rsp`) contains the address of the first number.
+
+
+By executing `mov %rsp,%rbp` we are setting the base pointer (`%rbp`) to point to this address.
+
+Now, for the second instruction `mov $0x1,%ebx`, we are initalising the `%ebx` register with the value 1. Based on the assembly code, you can see that this is being used as a counter/index for the loop.
+
+
+```
+ 0x000055555555560b <+32>: jmp 0x555555555620 <phase_2+53>
+```
+
+The program now jumps to <phase_2+53>
+
+```
+ 0x0000555555555620 <+53>: mov %ebx,%eax
+ 0x0000555555555622 <+55>: add 0x0(%rbp),%eax
+ 0x0000555555555625 <+58>: cmp %eax,0x4(%rbp)
+ 0x0000555555555628 <+61>: je 0x555555555614 <phase_2+41>
+```
+
+Here, the value from `%ebx` is copied to the `%eax` register. For this iteration, the value should be 1.
+
+Then, the value at the memory location pointed by `%rbp` is added to the value in `%eax`. For now, 0 is added (the first number that we read).
+
+`cmp %eax,0x4(%rbp)` - The instruction compares the value in %eax to the value at the memory address `%rbp + 4`. Since Integers in this context are stored using a word of memory of 4 bytes, this indicates it checks against the second number in the sequence.
+
+`je 0x555555555614 <phase_2+41>` - The program will jump to `phase_2+41` if the previous `cmp` instruction determined the values as equal.
+
+```
+ 0x0000555555555614 <+41>: add $0x1,%ebx
+ 0x0000555555555617 <+44>: add $0x4,%rbp
+ 0x000055555555561b <+48>: cmp $0x6,%ebx
+ 0x000055555555561e <+51>: je 0x555555555631 <phase_2+70>
+ 0x0000555555555620 <+53>: mov %ebx,%eax
+ 0x0000555555555622 <+55>: add 0x0(%rbp),%eax
+ 0x0000555555555625 <+58>: cmp %eax,0x4(%rbp)
+ 0x0000555555555628 <+61>: je 0x555555555614 <phase_2+41>
+```
+
+Here, we can see that the program increments `%ebx` by 1, adds a 4 byte offset to `%rbp` (the number we will be matching now), and checks if `%ebx` is equal to 6. If it is, it breaks the loop and jumps to `<phase_2+70>` succesfully finishing this stage.
+
+Now, given that we know the first two numbers in the sequence are `0 1`, we can calculate the other numbers by following the pattern of adding the counter and the value of the previous number.
+
+Thus,
+
+* 3rd number = 1 (previous value) + 2 = 3
+* 4th number = 3 (prev value) + 3 = 6
+* 5th number = 6 (prev value) + 4 = 10
+* 6th number = 10 (prev value) + 5 = 15
+
+
+```
+...
+Phase 1 defused. How about the next one?
+0 1 3 6 10 15
+
+Breakpoint 1, 0x00005555555555eb in phase_2 ()
+(gdb) continue
+Continuing.
+That's number 2. Keep going!
+```