# Assembly analysis for override
# level00
```
objdump -M intel -d level00
objdump -s -j .data level00 -> -s stands for full content, -j stands for section
```
## main
```
8048494: 55 push ebp
8048495: 89 e5 mov ebp,esp
8048497: 83 e4 f0 and esp,0xfffffff0
```
- `8048494` to `8048494` Sets up the stack frame by moving the stack pointers away from the parents esp to the current ebp
- `8048497` Stack alignment to the closes 8 bytes. The esp moves up by 8 bytes.
---
```
804849a: 83 ec 20 sub esp,0x20
804849d: c7 04 24 f0 85 04 08 mov DWORD PTR [esp],0x80485f0
80484a4: e8 e7 fe ff ff call 8048390 <puts@plt>
80484a9: c7 04 24 14 86 04 08 mov DWORD PTR [esp],0x8048614
80484b0: e8 db fe ff ff call 8048390 <puts@plt>
80484b5: c7 04 24 f0 85 04 08 mov DWORD PTR [esp],0x80485f0
80484bc: e8 cf fe ff ff call 8048390 <puts@plt>
```
- `804849a` bulk allocates 32 bytes in the stack
- `804849d - 804849d` calls
```
puts("***********************************");
puts ("-Level00 -");
puts("***********************************");
```
---
```
80484c1: b8 2c 86 04 08 mov eax,0x804862c
80484c6: 89 04 24 mov DWORD PTR [esp],eax
80484c9: e8 b2 fe ff ff call 8048380 <printf@plt>
```
- `80484c1 - 80484c9` calls printf("Password: ")
---
```
80484ce: b8 36 86 04 08 mov eax,0x8048636
80484d3: 8d 54 24 1c lea edx,[esp+0x1c]
80484d7: 89 54 24 04 mov DWORD PTR [esp+0x4],edx
80484db: 89 04 24 mov DWORD PTR [esp],eax
80484de: e8 ed fe ff ff call 80483d0 <__isoc99_scanf@plt>
80484e3: 8b 44 24 1c mov eax,DWORD PTR [esp+0x1c]
80484e7: 3d 9c 14 00 00 cmp eax,0x149c
```
- `80484ce` prepares the "%d" string in eax
- `80484d3` loads a variable (pointer is at esp + 0x1c) to edx, which will be used by scanf later. Lets call this `input`
- `80484d7 - 80484de` Calls
```
in_buf = scanf("%d", &input);
```
- `80484e3 - 80484e7` derefrences the pointer to `input` and compares it with 5276
---
```
80484ec: 75 1f jne 804850d <main+0x79>
80484ee: c7 04 24 39 86 04 08 mov DWORD PTR [esp],0x8048639
80484f5: e8 96 fe ff ff call 8048390 <puts@plt>
80484fa: c7 04 24 49 86 04 08 mov DWORD PTR [esp],0x8048649
8048501: e8 9a fe ff ff call 80483a0 <system@plt>
8048506: b8 00 00 00 00 mov eax,0x0
804850b: eb 11 jmp 804851e <main+0x8a>
804850d: c7 04 24 51 86 04 08 mov DWORD PTR [esp],0x8048651
8048514: e8 77 fe ff ff call 8048390 <puts@plt>
8048519: b8 01 00 00 00 mov eax,0x1
804851e: c9 leave
804851f: c3 ret
```
- `80484ec` if the comparison is not equal, jump to `804850d`
- `80484ee - 8048501` calls `puts("Authenticated!")` and runs `system("/bin/sh")`
- `804850b` return 0
- `804850d - 8048514` calls `puts("Invalid Password!")`
- `8048519 - 804851f` return 1
# level01
```
objdump -M intel -d level01
objdump -s -j .data level01
```
## main
```
80484d0: 55 push ebp
80484d1: 89 e5 mov ebp,esp
80484d3: 57 push edi
80484d4: 53 push ebx
80484d5: 83 e4 f0 and esp,0xfffffff0
80484d8: 83 ec 60 sub esp,0x60
80484db: 8d 5c 24 1c lea ebx,[esp+0x1c]
80484df: b8 00 00 00 00 mov eax,0x0
80484e4: ba 10 00 00 00 mov edx,0x10
80484e9: 89 df mov edi,ebx
80484eb: 89 d1 mov ecx,edx
80484ed: f3 ab rep stos DWORD PTR es:[edi],eax
80484ef: c7 44 24 5c 00 00 00 mov DWORD PTR [esp+0x5c],0x0
```
- `80484d0 - 80484d5` Stack frame setup and stack alignment
- `80484d8 - 80484db` Allocates 96 bytes on the stack and loads a buffer at [esp + 0x1c] to ebx. Call this **child_input**
- `80484df - 80484ed` Repeatedly fill up the data pointed in `edi` (child_input) with the value in `eax`, which is 16, for `edx` times which is 10. The `es` is an explicit segmentation specifier for compatibility issues. Effectively, this does `memset(child_input, 0, 16);`
```
80484ef: c7 44 24 5c 00 00 00 mov DWORD PTR [esp+0x5c],0x0
80484f6: 00
80484f7: c7 04 24 b8 86 04 08 mov DWORD PTR [esp],0x80486b8
80484fe: e8 7d fe ff ff call 8048380 <puts@plt>
8048503: b8 df 86 04 08 mov eax,0x80486df
8048508: 89 04 24 mov DWORD PTR [esp],eax
804850b: e8 50 fe ff ff call 8048360 <printf@plt>
```
- `80484ef` Write 0 to a pointer at [esp + 0x5c], Call this **num**
- `80484f7 - 80484fe` Effectively call `puts("********* ADMIN LOGIN PROMPT *********")`
- `804850b` Effectively call `printf("Enter Username:")`
```
8048510: a1 20 a0 04 08 mov eax,ds:0x804a020
8048515: 89 44 24 08 mov DWORD PTR [esp+0x8],eax
8048519: c7 44 24 04 00 01 00 mov DWORD PTR [esp+0x4],0x100
8048520: 00
8048521: c7 04 24 40 a0 04 08 mov DWORD PTR [esp],0x804a040
8048528: e8 43 fe ff ff call 8048370 <fgets@plt>
804852d: e8 32 ff ff ff call 8048464 <verify_user_name>
```
- `8048510` Load a static global buffer into eax from `0x804a020`, call this **input_buf**
- `8048515 - 8048528` Effectively call `fgets(input_buf, 256, stdin)`
- `804852d` Call `verify_user_name` with the return value of fgets.
```
8048532: 89 44 24 5c mov DWORD PTR [esp+0x5c],eax
8048536: 83 7c 24 5c 00 cmp DWORD PTR [esp+0x5c],0x0
804853b: 74 13 je 8048550 <main+0x80>
804853d: c7 04 24 f0 86 04 08 mov DWORD PTR [esp],0x80486f0
8048544: e8 37 fe ff ff call 8048380 <puts@plt>
8048549: b8 01 00 00 00 mov eax,0x1
804854e: eb 5f jmp 80485af <main+0xdf>
```
- `8048532 - 804853b` Load the return value of `verify_user_name` and write it to **num**. Compare it with value 0. If the result is equal, jump to `<main+0x80>`.
- `804853d - 804854e` If not, call `puts("nope, incorrect username")` and return 1.
```
8048550: c7 04 24 0d 87 04 08 mov DWORD PTR [esp],0x804870d
8048557: e8 24 fe ff ff call 8048380 <puts@plt>
804855c: a1 20 a0 04 08 mov eax,ds:0x804a020
8048561: 89 44 24 08 mov DWORD PTR [esp+0x8],eax
8048565: c7 44 24 04 64 00 00 mov DWORD PTR [esp+0x4],0x64
804856c: 00
804856d: 8d 44 24 1c lea eax,[esp+0x1c]
8048571: 89 04 24 mov DWORD PTR [esp],eax
8048574: e8 f7 fd ff ff call 8048370 <fgets@plt>
8048579: 8d 44 24 1c lea eax,[esp+0x1c]
804857d: 89 04 24 mov DWORD PTR [esp],eax
8048580: e8 1e ff ff ff call 80484a3 <verify_user_pass>
```
- `8048550 - 8048557` Effectively call `puts("Enter Password:")`
- `804855c - 8048574` Effectively call `fgets(child_input, 100, stdin)`
- `8048579 - 8048580` Effectively call `verify_user_pass` with the return value of fgets earlier
```
8048585: 89 44 24 5c mov DWORD PTR [esp+0x5c],eax
8048589: 83 7c 24 5c 00 cmp DWORD PTR [esp+0x5c],0x0
804858e: 74 07 je 8048597 <main+0xc7>
8048590: 83 7c 24 5c 00 cmp DWORD PTR [esp+0x5c],0x0
8048595: 74 13 je 80485aa <main+0xda>
8048597: c7 04 24 1e 87 04 08 mov DWORD PTR [esp],0x804871e
804859e: e8 dd fd ff ff call 8048380 <puts@plt>
80485a3: b8 01 00 00 00 mov eax,0x1
80485a8: eb 05 jmp 80485af <main+0xdf>
80485aa: b8 00 00 00 00 mov eax,0x0
80485af: 8d 65 f8 lea esp,[ebp-0x8]
80485b2: 5b pop ebx
80485b3: 5f pop edi
80485b4: 5d pop ebp
80485b5: c3 ret
```
- `8048585 - 80485a8` Essentially the same operations earlier after we verify username, we compare the return value to 0, `puts("nope, incorrect password")` if its not and return 1
- `80485aa - 80485b5` return 0
## verify_user_name
```
8048464: 55 push ebp
8048465: 89 e5 mov ebp,esp
8048467: 57 push edi
8048468: 56 push esi
8048469: 83 ec 10 sub esp,0x10
804846c: c7 04 24 90 86 04 08 mov DWORD PTR [esp],0x8048690
8048473: e8 08 ff ff ff call 8048380 <puts@plt>
8048478: ba 40 a0 04 08 mov edx,0x804a040
804847d: b8 a8 86 04 08 mov eax,0x80486a8
8048482: b9 07 00 00 00 mov ecx,0x7
8048487: 89 d6 mov esi,edx
8048489: 89 c7 mov edi,eax
804848b: f3 a6 repz cmps BYTE PTR ds:[esi],BYTE PTR es:[edi]
804848d: 0f 97 c2 seta dl
8048490: 0f 92 c0 setb al
8048493: 89 d1 mov ecx,edx
8048495: 28 c1 sub cl,al
8048497: 89 c8 mov eax,ecx
8048499: 0f be c0 movsx eax,al
804849c: 83 c4 10 add esp,0x10
804849f: 5e pop esi
80484a0: 5f pop edi
80484a1: 5d pop ebp
80484a2: c3 ret
```
- `8048464 - 8048469` Sets up stack frame and allocates 16 bytes in stack
- `804846c - 8048473` Effectively call `puts("verifying username....")`
- `8048478 - 804848b` Sets up **input_buf** in `esi` and `"dat_wil"(from data section)` in `edi` and compare them.
- `804848d - 8048490` Records the differences in `dl` or `al`. If the comparisons are equal, both of them should be 0
- `8048493 - 8048499` Perform arithmethic on the differences to get the actual return value, since `al` or `dl` does not reflect the full registers - there might have other things unintentionally
- `804849f - 80484a2` Return the difference earlier.
## verify_user_pass
```
80484a3: 55 push ebp
80484a4: 89 e5 mov ebp,esp
80484a6: 57 push edi
80484a7: 56 push esi
80484a8: 8b 45 08 mov eax,DWORD PTR [ebp+0x8]
80484ab: 89 c2 mov edx,eax
80484ad: b8 b0 86 04 08 mov eax,0x80486b0
80484b2: b9 05 00 00 00 mov ecx,0x5
80484b7: 89 d6 mov esi,edx
80484b9: 89 c7 mov edi,eax
80484bb: f3 a6 repz cmps BYTE PTR ds:[esi],BYTE PTR es:[edi]
80484bd: 0f 97 c2 seta dl
80484c0: 0f 92 c0 setb al
80484c3: 89 d1 mov ecx,edx
80484c5: 28 c1 sub cl,al
80484c7: 89 c8 mov eax,ecx
80484c9: 0f be c0 movsx eax,al
80484cc: 5e pop esi
80484cd: 5f pop edi
80484ce: 5d pop ebp
80484cf: c3 ret
```
- `80484a3 - 80484a8` Set up stack frame and load the first argument into `eax`
- `80484ab - 80484cf` Compare it with the string "admin" from data segment, the rest is the same with `verify_user_name`
# level02
```
objdump -M intel -d level02
objdump -s -j .data level02
```
## main
```
400814: 55 push rbp
400815: 48 89 e5 mov rbp,rsp
400818: 48 81 ec 20 01 00 00 sub rsp,0x120
40081f: 89 bd ec fe ff ff mov DWORD PTR [rbp-0x114],edi
400825: 48 89 b5 e0 fe ff ff mov QWORD PTR [rbp-0x120],rsi
40082c: 48 8d 55 90 lea rdx,[rbp-0x70]
400830: b8 00 00 00 00 mov eax,0x0
400835: b9 0c 00 00 00 mov ecx,0xc
40083a: 48 89 d7 mov rdi,rdx
40083d: f3 48 ab rep stos QWORD PTR es:[rdi],rax
````
- `400814 - 400815` preparing stack frame addresses
- `400818 - 400825` allocates 288 bytes for the stack, loads the value of `edi` into `[rbp-0x114]` (call this **init_edi**), Load `rsi` into `[rbp-0x120]` (**init_rsi**)
- `40082c - 40083d` Loads `[rbp-0x70]` into `rdx` (call this **username**) effectively call `memset(username, 0, 12)`
---
```
400840: 48 89 fa mov rdx,rdi
400843: 89 02 mov DWORD PTR [rdx],eax
400845: 48 83 c2 04 add rdx,0x4
400849: 48 8d 95 60 ff ff ff lea rdx,[rbp-0xa0]
400850: b8 00 00 00 00 mov eax,0x0
400855: b9 05 00 00 00 mov ecx,0x5
40085a: 48 89 d7 mov rdi,rdx
40085d: f3 48 ab rep stos QWORD PTR es:[rdi],rax
400860: 48 89 fa mov rdx,rdi
400863: 88 02 mov BYTE PTR [rdx],al
400865: 48 83 c2 01 add rdx,0x1
```
- `400840` Null terminates `username` and increments it by 4 (why?)
- `400849 - 40085d` Loads `[rbp-0xa0]` aka **pass_file_content** into rdx and effectively call `memset(pass_file_content, 0, 5)`
- `400860 - 400863` Null terminates `pass_file_content` and increments it by 1 (why?)
---
```
400869: 48 8d 95 f0 fe ff ff lea rdx,[rbp-0x110]
400870: b8 00 00 00 00 mov eax,0x0
400875: b9 0c 00 00 00 mov ecx,0xc
40087a: 48 89 d7 mov rdi,rdx
40087d: f3 48 ab rep stos QWORD PTR es:[rdi],rax
400880: 48 89 fa mov rdx,rdi
400883: 89 02 mov DWORD PTR [rdx],eax
400885: 48 83 c2 04 add rdx,0x4
```
- `400869 - 400883` Do the same thing as above for another variable `[rbp-0x110]` aka **pass** using `memset(pass, 0, 12)`, this time it increments 4 in the end.
---
```
400889: 48 c7 45 f8 00 00 00 mov QWORD PTR [rbp-0x8],0x0
400890: 00
400891: c7 45 f4 00 00 00 00 mov DWORD PTR [rbp-0xc],0x0
400898: ba b0 0b 40 00 mov edx,0x400bb0
40089d: b8 b2 0b 40 00 mov eax,0x400bb2
4008a2: 48 89 d6 mov rsi,rdx
4008a5: 48 89 c7 mov rdi,rax
4008a8: e8 53 fe ff ff call 400700 <fopen@plt>
4008ad: 48 89 45 f8 mov QWORD PTR [rbp-0x8],rax
4008b1: 48 83 7d f8 00 cmp QWORD PTR [rbp-0x8],0x0
4008b6: 75 2e jne 4008e6 <main+0xd2>
4008b8: 48 8b 05 91 09 20 00 mov rax,QWORD PTR [rip+0x200991] # 601250 <stderr@@GLIBC_2.2.5>
4008bf: 48 89 c2 mov rdx,rax
4008c2: b8 d0 0b 40 00 mov eax,0x400bd0
4008c7: 48 89 d1 mov rcx,rdx
4008ca: ba 24 00 00 00 mov edx,0x24
4008cf: be 01 00 00 00 mov esi,0x1
4008d4: 48 89 c7 mov rdi,rax
4008d7: e8 44 fe ff ff call 400720 <fwrite@plt>
4008dc: bf 01 00 00 00 mov edi,0x1
4008e1: e8 2a fe ff ff call 400710 <exit@plt>
```
- `400889 - 4008a8` Declares **open_passfile** at `[rbp-0x8]` and **read_pass_status** at `[rbp-0xc]` Prepares arguments to call `fopen("/home/users/level03/", "r")`
- `4008ad - 4008b1` Save the return value above in `[rbp-0x8]` aka **open_passfile** and compares it with 0. It its not equal, jump to `4008e6`
- `4008b8 - 4008e1` If it is 0, call `fwrite("ERROR: failed to open password file", 1, 24, stderr)` and `exit(1)`
---
```
4008e6: 48 8d 85 60 ff ff ff lea rax,[rbp-0xa0]
4008ed: 48 8b 55 f8 mov rdx,QWORD PTR [rbp-0x8]
4008f1: 48 89 d1 mov rcx,rdx
4008f4: ba 29 00 00 00 mov edx,0x29
4008f9: be 01 00 00 00 mov esi,0x1
4008fe: 48 89 c7 mov rdi,rax
400901: e8 8a fd ff ff call 400690 <fread@plt>
400906: 89 45 f4 mov DWORD PTR [rbp-0xc],eax
400909: 48 8d 85 60 ff ff ff lea rax,[rbp-0xa0]
400910: be f5 0b 40 00 mov esi,0x400bf5
400915: 48 89 c7 mov rdi,rax
400918: e8 b3 fd ff ff call 4006d0 <strcspn@plt>
40091d: c6 84 05 60 ff ff ff mov BYTE PTR [rbp+rax*1-0xa0],0x0
400924: 00
400925: 83 7d f4 29 cmp DWORD PTR [rbp-0xc],0x29
400929: 74 52 je 40097d <main+0x169>
40092b: 48 8b 05 1e 09 20 00 mov rax,QWORD PTR [rip+0x20091e] # 601250 <stderr@@GLIBC_2.2.5>
400932: 48 89 c2 mov rdx,rax
400935: b8 f8 0b 40 00 mov eax,0x400bf8
40093a: 48 89 d1 mov rcx,rdx
40093d: ba 24 00 00 00 mov edx,0x24
400942: be 01 00 00 00 mov esi,0x1
400947: 48 89 c7 mov rdi,rax
40094a: e8 d1 fd ff ff call 400720 <fwrite@plt>
40094f: 48 8b 05 fa 08 20 00 mov rax,QWORD PTR [rip+0x2008fa] # 601250 <stderr@@GLIBC_2.2.5>
400956: 48 89 c2 mov rdx,rax
400959: b8 f8 0b 40 00 mov eax,0x400bf8
40095e: 48 89 d1 mov rcx,rdx
400961: ba 24 00 00 00 mov edx,0x24
400966: be 01 00 00 00 mov esi,0x1
40096b: 48 89 c7 mov rdi,rax
40096e: e8 ad fd ff ff call 400720 <fwrite@plt>
400973: bf 01 00 00 00 mov edi,0x1
400978: e8 93 fd ff ff call 400710 <exit@plt>
```
- `4008e6 - 400901` Calls `fread(pass_file_content, 1, 29, open_passfile)` and stores the result in **read_pass_status**
- `400909 - 400918` Prepares arguments and calls `strcspn(pass_file_content, "\n")` which returns the number of bytes of **pass_file_content** which are not in the "\n".
- `40091d` pass_file_content[<ret_above>] = 0
- `400925 - 400978` Compare **read_pass_status** with `41`. If the are equal, jump to `40097d`. If they are not, `frwite("ERROR: failed to read password file", 1, 24, stderr)` twice and call `exit(1)`
---
```
40097d: 48 8b 45 f8 mov rax,QWORD PTR [rbp-0x8]
400981: 48 89 c7 mov rdi,rax
400984: e8 17 fd ff ff call 4006a0 <fclose@plt>
400989: bf 20 0c 40 00 mov edi,0x400c20
40098e: e8 ed fc ff ff call 400680 <puts@plt>
400993: bf 50 0c 40 00 mov edi,0x400c50
400998: e8 e3 fc ff ff call 400680 <puts@plt>
40099d: bf 80 0c 40 00 mov edi,0x400c80
4009a2: e8 d9 fc ff ff call 400680 <puts@plt>
4009a7: bf b0 0c 40 00 mov edi,0x400cb0
4009ac: e8 cf fc ff ff call 400680 <puts@plt>
4009b1: b8 d9 0c 40 00 mov eax,0x400cd9
4009b6: 48 89 c7 mov rdi,rax
4009b9: b8 00 00 00 00 mov eax,0x0
4009be: e8 fd fc ff ff call 4006c0 <printf@plt>
```
- `40097d - 400984` Closes the password file by calling `fclose(open_passfile)`
- `400989 - 4009be` Calls `puts()` for all the lines of the following output and calls `printf("--[ Username:")` at the end.
```
===== [ Secure Access System v1.0 ] =====
/***************************************\
| You must login to access this system. |
\**************************************/
```
---
```
4009c3: 48 8b 05 7e 08 20 00 mov rax,QWORD PTR [rip+0x20087e] # 601248 <__bss_start>
4009ca: 48 89 c2 mov rdx,rax
4009cd: 48 8d 45 90 lea rax,[rbp-0x70]
4009d1: be 64 00 00 00 mov esi,0x64
4009d6: 48 89 c7 mov rdi,rax
4009d9: e8 12 fd ff ff call 4006f0 <fgets@plt>
4009de: 48 8d 45 90 lea rax,[rbp-0x70]
4009e2: be f5 0b 40 00 mov esi,0x400bf5
4009e7: 48 89 c7 mov rdi,rax
4009ea: e8 e1 fc ff ff call 4006d0 <strcspn@plt>
4009ef: c6 44 05 90 00 mov BYTE PTR [rbp+rax*1-0x70],0x0
4009f4: b8 e8 0c 40 00 mov eax,0x400ce8
4009f9: 48 89 c7 mov rdi,rax
4009fc: b8 00 00 00 00 mov eax,0x0
400a01: e8 ba fc ff ff call 4006c0 <printf@plt>
```
- `4009c3 - 4009d9` Effectively calls `fgets(username, 100, stdin)`
- `4009de - 400a01` finds the index of newline string in **username**, and replaces the newline with nullbyte. Calls `printf(" --[ Password:")` after that
---
```
400a06: 48 8b 05 3b 08 20 00 mov rax,QWORD PTR [rip+0x20083b] # 601248 <__bss_start>
400a0d: 48 89 c2 mov rdx,rax
400a10: 48 8d 85 f0 fe ff ff lea rax,[rbp-0x110]
400a17: be 64 00 00 00 mov esi,0x64
400a1c: 48 89 c7 mov rdi,rax
400a1f: e8 cc fc ff ff call 4006f0 <fgets@plt>
400a24: 48 8d 85 f0 fe ff ff lea rax,[rbp-0x110]
400a2b: be f5 0b 40 00 mov esi,0x400bf5
400a30: 48 89 c7 mov rdi,rax
400a33: e8 98 fc ff ff call 4006d0 <strcspn@plt>
400a38: c6 84 05 f0 fe ff ff mov BYTE PTR [rbp+rax*1-0x110],0x0
400a3f: 00
```
- `400a06 - 400a3f` Essentially do the same with **pass** by calling `fgets(pass, 100, stdin)` and null terminates it
---
```
400a40: bf f8 0c 40 00 mov edi,0x400cf8
400a45: e8 36 fc ff ff call 400680 <puts@plt>
400a4a: 48 8d 8d f0 fe ff ff lea rcx,[rbp-0x110]
400a51: 48 8d 85 60 ff ff ff lea rax,[rbp-0xa0]
400a58: ba 29 00 00 00 mov edx,0x29
400a5d: 48 89 ce mov rsi,rcx
400a60: 48 89 c7 mov rdi,rax
400a63: e8 08 fc ff ff call 400670 <strncmp@plt>
400a68: 85 c0 test eax,eax
400a6a: 75 2a jne 400a96 <main+0x282>
400a6c: b8 22 0d 40 00 mov eax,0x400d22
400a71: 48 8d 55 90 lea rdx,[rbp-0x70]
400a75: 48 89 d6 mov rsi,rdx
400a78: 48 89 c7 mov rdi,rax
400a7b: b8 00 00 00 00 mov eax,0x0
400a80: e8 3b fc ff ff call 4006c0 <printf@plt>
400a85: bf 32 0d 40 00 mov edi,0x400d32
400a8a: e8 21 fc ff ff call 4006b0 <system@plt>
400a8f: b8 00 00 00 00 mov eax,0x0
400a94: c9 leave
400a95: c3 ret
400a96: 48 8d 45 90 lea rax,[rbp-0x70]
400a9a: 48 89 c7 mov rdi,rax
400a9d: b8 00 00 00 00 mov eax,0x0
400aa2: e8 19 fc ff ff call 4006c0 <printf@plt>
400aa7: bf 3a 0d 40 00 mov edi,0x400d3a
400aac: e8 cf fb ff ff call 400680 <puts@plt>
400ab1: bf 01 00 00 00 mov edi,0x1
400ab6: e8 55 fc ff ff call 400710 <exit@plt>
```
- `400a40 - 400a45` Calls `puts("*****************************************")`
- `400a4a - 400a68` Calls `strncmp(pass_file_content, pass, 41)` and test if the result is 0
- `400a6a` If its not equal, jump to `400a96`
- `400a6c - 400a95` call `printf("Greetings, %s!", username)` and `system("/bin/sh")`, and returns 0
- `400a96 - 400ab6` call `printf(username)` and `puts("does not have access!")` and `exit(1)`
# level03
```
objdump -M intel -d level03
objdump -s -j .data level03
```
## main
```
804885a: 55 push ebp
804885b: 89 e5 mov ebp,esp
804885d: 83 e4 f0 and esp,0xfffffff0
8048860: 83 ec 20 sub esp,0x20
8048863: 50 push eax
8048864: 31 c0 xor eax,eax
8048866: 74 03 je 804886b <main+0x11>
8048868: 83 c4 04 add esp,0x4
804886b: 58 pop eax
804886c: c7 04 24 00 00 00 00 mov DWORD PTR [esp],0x0
8048873: e8 38 fc ff ff call 80484b0 <time@plt>
8048878: 89 04 24 mov DWORD PTR [esp],eax
804887b: e8 80 fc ff ff call 8048500 <srand@plt>
8048880: c7 04 24 48 8a 04 08 mov DWORD PTR [esp],0x8048a48
8048887: e8 44 fc ff ff call 80484d0 <puts@plt>
804888c: c7 04 24 6c 8a 04 08 mov DWORD PTR [esp],0x8048a6c
8048893: e8 38 fc ff ff call 80484d0 <puts@plt>
8048898: c7 04 24 48 8a 04 08 mov DWORD PTR [esp],0x8048a48
804889f: e8 2c fc ff ff call 80484d0 <puts@plt>
80488a4: b8 7b 8a 04 08 mov eax,0x8048a7b
80488a9: 89 04 24 mov DWORD PTR [esp],eax
80488ac: e8 cf fb ff ff call 8048480 <printf@plt>
80488b1: b8 85 8a 04 08 mov eax,0x8048a85
80488b6: 8d 54 24 1c lea edx,[esp+0x1c]
80488ba: 89 54 24 04 mov DWORD PTR [esp+0x4],edx
80488be: 89 04 24 mov DWORD PTR [esp],eax
80488c1: e8 6a fc ff ff call 8048530 <__isoc99_scanf@plt>
80488c6: 8b 44 24 1c mov eax,DWORD PTR [esp+0x1c]
80488ca: c7 44 24 04 0d d0 37 mov DWORD PTR [esp+0x4],0x1337d00d
80488d1: 13
80488d2: 89 04 24 mov DWORD PTR [esp],eax
80488d5: e8 6d fe ff ff call 8048747 <test>
80488da: b8 00 00 00 00 mov eax,0x0
80488df: c9 leave
80488e0: c3 ret
```
- `804885a - 8048860` Stack setup, alignment and allocating 32 bytes for the stack
- `8048863 - 804886b` I dont know why they would do this but looks like it is just clearing out eax and making sure the stack is ok?
- `804886c - 8048873` Call `srand(time(0))`
- `8048880 - 804889f` For each line below, call `puts()` on it
```
***********************************
* level03 **
***********************************
```
- `80488a4 - 80488ac` Call `printf("Password:")`
- `80488ac - 80488c1` Loads `[esp + 0x1c]` aka **pwinput** to `eax`. Calls `scanf("%d", &pwinput)`
- `80488c6 - 80488e0` Calls `test(pwinput, 0x1337d00d)` and returns 0
## test
```
8048747: 55 push ebp
8048748: 89 e5 mov ebp,esp
804874a: 83 ec 28 sub esp,0x28
804874d: 8b 45 08 mov eax,DWORD PTR [ebp+0x8]
8048750: 8b 55 0c mov edx,DWORD PTR [ebp+0xc]
8048753: 89 d1 mov ecx,edx
8048755: 29 c1 sub ecx,eax
8048757: 89 c8 mov eax,ecx
8048759: 89 45 f4 mov DWORD PTR [ebp-0xc],eax
804875c: 83 7d f4 15 cmp DWORD PTR [ebp-0xc],0x15
8048760: 0f 87 e4 00 00 00 ja 804884a <test+0x103>
8048766: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
8048769: c1 e0 02 shl eax,0x2
804876c: 05 f0 89 04 08 add eax,0x80489f0
8048771: 8b 00 mov eax,DWORD PTR [eax]
8048773: ff e0 jmp eax
8048775: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
8048778: 89 04 24 mov DWORD PTR [esp],eax
804877b: e8 e0 fe ff ff call 8048660 <decrypt>
8048780: e9 d3 00 00 00 jmp 8048858 <test+0x111>
8048785: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
8048788: 89 04 24 mov DWORD PTR [esp],eax
804878b: e8 d0 fe ff ff call 8048660 <decrypt>
8048790: e9 c3 00 00 00 jmp 8048858 <test+0x111>
8048795: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
8048798: 89 04 24 mov DWORD PTR [esp],eax
804879b: e8 c0 fe ff ff call 8048660 <decrypt>
80487a0: e9 b3 00 00 00 jmp 8048858 <test+0x111>
80487a5: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
80487a8: 89 04 24 mov DWORD PTR [esp],eax
80487ab: e8 b0 fe ff ff call 8048660 <decrypt>
80487b0: e9 a3 00 00 00 jmp 8048858 <test+0x111>
80487b5: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
80487b8: 89 04 24 mov DWORD PTR [esp],eax
80487bb: e8 a0 fe ff ff call 8048660 <decrypt>
80487c0: e9 93 00 00 00 jmp 8048858 <test+0x111>
80487c5: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
80487c8: 89 04 24 mov DWORD PTR [esp],eax
80487cb: e8 90 fe ff ff call 8048660 <decrypt>
80487d0: e9 83 00 00 00 jmp 8048858 <test+0x111>
80487d5: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
80487d8: 89 04 24 mov DWORD PTR [esp],eax
80487db: e8 80 fe ff ff call 8048660 <decrypt>
80487e0: eb 76 jmp 8048858 <test+0x111>
80487e2: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
80487e5: 89 04 24 mov DWORD PTR [esp],eax
80487e8: e8 73 fe ff ff call 8048660 <decrypt>
80487ed: eb 69 jmp 8048858 <test+0x111>
80487ef: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
80487f2: 89 04 24 mov DWORD PTR [esp],eax
80487f5: e8 66 fe ff ff call 8048660 <decrypt>
80487fa: eb 5c jmp 8048858 <test+0x111>
80487fc: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
80487ff: 89 04 24 mov DWORD PTR [esp],eax
8048802: e8 59 fe ff ff call 8048660 <decrypt>
8048807: eb 4f jmp 8048858 <test+0x111>
8048809: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
804880c: 89 04 24 mov DWORD PTR [esp],eax
804880f: e8 4c fe ff ff call 8048660 <decrypt>
8048814: eb 42 jmp 8048858 <test+0x111>
8048816: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
8048819: 89 04 24 mov DWORD PTR [esp],eax
804881c: e8 3f fe ff ff call 8048660 <decrypt>
8048821: eb 35 jmp 8048858 <test+0x111>
8048823: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
8048826: 89 04 24 mov DWORD PTR [esp],eax
8048829: e8 32 fe ff ff call 8048660 <decrypt>
804882e: eb 28 jmp 8048858 <test+0x111>
8048830: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
8048833: 89 04 24 mov DWORD PTR [esp],eax
8048836: e8 25 fe ff ff call 8048660 <decrypt>
804883b: eb 1b jmp 8048858 <test+0x111>
804883d: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
8048840: 89 04 24 mov DWORD PTR [esp],eax
8048843: e8 18 fe ff ff call 8048660 <decrypt>
8048848: eb 0e jmp 8048858 <test+0x111>
804884a: e8 d1 fc ff ff call 8048520 <rand@plt>
804884f: 89 04 24 mov DWORD PTR [esp],eax
8048852: e8 09 fe ff ff call 8048660 <decrypt>
8048857: 90 nop
8048858: c9 leave
8048859: c3 ret
```
- `8048747 - 8048750` Set up stack frame and load **pwinput** at `[ebp+0x8]` to `eax` and **init_addr**`[ebp+0xc]` which is now equal to `0x1337d00d` to `edx`
- `8048753 - 8048759` **init_addr** -= **pwinput**
- `804875c - 8048760` comapre **init_addr** with `21`. If its more than, jump to `804884a`.
- `8048766 - 8048780` load **init_addr** in some temp variable and shift left by 2, which means multiply by 4 and add `0x80489f0` to that value. The temp variable is the derefrenced and jumped to.
- `804877b - 8048858` Continiously call `decrypt(init_addr)` and return
## decrypt
```
8048660: 55 push ebp
8048661: 89 e5 mov ebp,esp
8048663: 57 push edi
8048664: 56 push esi
8048665: 83 ec 40 sub esp,0x40
8048668: 65 a1 14 00 00 00 mov eax,gs:0x14
804866e: 89 45 f4 mov DWORD PTR [ebp-0xc],eax
8048671: 31 c0 xor eax,eax
8048673: c7 45 e3 51 7d 7c 75 mov DWORD PTR [ebp-0x1d],0x757c7d51
804867a: c7 45 e7 60 73 66 67 mov DWORD PTR [ebp-0x19],0x67667360
8048681: c7 45 eb 7e 73 66 7b mov DWORD PTR [ebp-0x15],0x7b66737e
8048688: c7 45 ef 7d 7c 61 33 mov DWORD PTR [ebp-0x11],0x33617c7d
804868f: c6 45 f3 00 mov BYTE PTR [ebp-0xd],0x0
8048693: 50 push eax
8048694: 31 c0 xor eax,eax
8048696: 74 03 je 804869b <decrypt+0x3b>
8048698: 83 c4 04 add esp,0x4
804869b: 58 pop eax
804869c: 8d 45 e3 lea eax,[ebp-0x1d]
804869f: c7 45 d4 ff ff ff ff mov DWORD PTR [ebp-0x2c],0xffffffff
80486a6: 89 c2 mov edx,eax
80486a8: b8 00 00 00 00 mov eax,0x0
80486ad: 8b 4d d4 mov ecx,DWORD PTR [ebp-0x2c]
80486b0: 89 d7 mov edi,edx
80486b2: f2 ae repnz scas al,BYTE PTR es:[edi]
80486b4: 89 c8 mov eax,ecx
80486b6: f7 d0 not eax
80486b8: 83 e8 01 sub eax,0x1
80486bb: 89 45 dc mov DWORD PTR [ebp-0x24],eax
80486be: c7 45 d8 00 00 00 00 mov DWORD PTR [ebp-0x28],0x0
80486c5: eb 1e jmp 80486e5 <decrypt+0x85>
80486c7: 8d 45 e3 lea eax,[ebp-0x1d]
80486ca: 03 45 d8 add eax,DWORD PTR [ebp-0x28]
80486cd: 0f b6 00 movzx eax,BYTE PTR [eax]
80486d0: 89 c2 mov edx,eax
80486d2: 8b 45 08 mov eax,DWORD PTR [ebp+0x8]
80486d5: 31 d0 xor eax,edx
80486d7: 89 c2 mov edx,eax
80486d9: 8d 45 e3 lea eax,[ebp-0x1d]
80486dc: 03 45 d8 add eax,DWORD PTR [ebp-0x28]
80486df: 88 10 mov BYTE PTR [eax],dl
80486e1: 83 45 d8 01 add DWORD PTR [ebp-0x28],0x1
80486e5: 8b 45 d8 mov eax,DWORD PTR [ebp-0x28]
80486e8: 3b 45 dc cmp eax,DWORD PTR [ebp-0x24]
80486eb: 72 da jb 80486c7 <decrypt+0x67>
80486ed: 8d 45 e3 lea eax,[ebp-0x1d]
80486f0: 89 c2 mov edx,eax
80486f2: b8 c3 89 04 08 mov eax,0x80489c3
80486f7: b9 11 00 00 00 mov ecx,0x11
80486fc: 89 d6 mov esi,edx
80486fe: 89 c7 mov edi,eax
8048700: f3 a6 repz cmps BYTE PTR ds:[esi],BYTE PTR es:[edi]
8048702: 0f 97 c2 seta dl
8048705: 0f 92 c0 setb al
8048708: 89 d1 mov ecx,edx
804870a: 28 c1 sub cl,al
804870c: 89 c8 mov eax,ecx
804870e: 0f be c0 movsx eax,al
8048711: 85 c0 test eax,eax
8048713: 75 0e jne 8048723 <decrypt+0xc3>
8048715: c7 04 24 d4 89 04 08 mov DWORD PTR [esp],0x80489d4
804871c: e8 bf fd ff ff call 80484e0 <system@plt>
8048721: eb 0c jmp 804872f <decrypt+0xcf>
8048723: c7 04 24 dc 89 04 08 mov DWORD PTR [esp],0x80489dc
804872a: e8 a1 fd ff ff call 80484d0 <puts@plt>
804872f: 8b 75 f4 mov esi,DWORD PTR [ebp-0xc]
8048732: 65 33 35 14 00 00 00 xor esi,DWORD PTR gs:0x14
8048739: 74 05 je 8048740 <decrypt+0xe0>
804873b: e8 80 fd ff ff call 80484c0 <__stack_chk_fail@plt>
8048740: 83 c4 40 add esp,0x40
8048743: 5e pop esi
8048744: 5f pop edi
8048745: 5d pop ebp
8048746: c3 ret
```
- `8048660 - 8048671` Prepare the stack and allocate 64 bytes for the stack. Load `20` into `[ebp-0xc]` aka **canary** and clears `eax`.
- `8048673 - 804863f` declates **cipher1** in `[ebp-0x1d]` with `0x757c7d51`, **cipher2** in `[ebp-0x19]` with `0x67667360`,**cipher3** in `[ebp-0x15]` with `0x7b66737e`,**cipher4** in `[ebp-0x11]` with `0x33617c7d`, **cipher5** in `[ebp-0xd]` with `0`.
- `8048693 - 804869b` I have no idea why they want to pop `eax` like that, so cant provide any context here yet..... (im guessing stack canary?)
- `804869c - 80486c5` **cipher1** has been loaded into `eax` and `0xffffffff` has been written to `[ebp-0x2c]` aka **clear_mask**.
- `80486a6 - 80486b2` evaluate string length of **cipher1**
- `80486b4 - 80486b8` store the value at eax and flip the polarity, since the result of the strlen was negative (direction flag), and then subtract 1
- `80486bb - 80486c5`Move the length into `[ebp-0x24]` aka **cipherlen** and zero into `[ebp-0x28]` aka **count**, jump to `80486e5`, which seems to be a loop checker
- `80486c7 - 80486e1` Load **cipher1**s address into `eax` and add the value of **count**. Derefrence the resultant address and write that result to `edx`. Load argument 1 (**init_addr**) into `eax` and xor it with `edx`, or our **cipher1addr + count**. -> **xor_res**. **cipher1[count] = xor_res**. `count += 1`
- `80486e5 - 80486eb` if **count** < **cipherlen** jump to `80486c7`
- `8048700 - 8048740` Comapres **cipher1** with the string `Congratulations!` using `strncmp(cipher1, "Congratulations!", 17)`. if its the same, `system("/bin/sh")`, else `puts("Invalid Password")` and return while checking for stack overflow.
# level04
```
objdump -M intel -d level04
objdump -s -j .data level04
```
## main
```
80486c8: 55 push ebp
80486c9: 89 e5 mov ebp,esp
80486cb: 57 push edi
80486cc: 53 push ebx
80486cd: 83 e4 f0 and esp,0xfffffff0
80486d0: 81 ec b0 00 00 00 sub esp,0xb0
80486d6: e8 75 fe ff ff call 8048550 <fork@plt>
80486db: 89 84 24 ac 00 00 00 mov DWORD PTR [esp+0xac],eax
80486e2: 8d 5c 24 20 lea ebx,[esp+0x20]
80486e6: b8 00 00 00 00 mov eax,0x0
80486eb: ba 20 00 00 00 mov edx,0x20
80486f0: 89 df mov edi,ebx
80486f2: 89 d1 mov ecx,edx
80486f4: f3 ab rep stos DWORD PTR es:[edi],eax
80486f6: c7 84 24 a8 00 00 00 mov DWORD PTR [esp+0xa8],0x0
80486fd: 00 00 00 00
8048701: c7 44 24 1c 00 00 00 mov DWORD PTR [esp+0x1c],0x0
8048708: 00
8048709: 83 bc 24 ac 00 00 00 cmp DWORD PTR [esp+0xac],0x0
8048710: 00
8048711: 75 56 jne 8048769 <main+0xa1>
8048713: c7 44 24 04 01 00 00 mov DWORD PTR [esp+0x4],0x1
804871a: 00
804871b: c7 04 24 01 00 00 00 mov DWORD PTR [esp],0x1
8048722: e8 19 fe ff ff call 8048540 <prctl@plt>
8048727: c7 44 24 0c 00 00 00 mov DWORD PTR [esp+0xc],0x0
804872e: 00
804872f: c7 44 24 08 00 00 00 mov DWORD PTR [esp+0x8],0x0
8048736: 00
8048737: c7 44 24 04 00 00 00 mov DWORD PTR [esp+0x4],0x0
804873e: 00
804873f: c7 04 24 00 00 00 00 mov DWORD PTR [esp],0x0
8048746: e8 25 fe ff ff call 8048570 <ptrace@plt>
804874b: c7 04 24 03 89 04 08 mov DWORD PTR [esp],0x8048903
8048752: e8 a9 fd ff ff call 8048500 <puts@plt>
8048757: 8d 44 24 20 lea eax,[esp+0x20]
804875b: 89 04 24 mov DWORD PTR [esp],eax
804875e: e8 4d fd ff ff call 80484b0 <gets@plt>
8048763: e9 b2 00 00 00 jmp 804881a <main+0x152>
8048768: 90 nop
8048769: 8d 44 24 1c lea eax,[esp+0x1c]
804876d: 89 04 24 mov DWORD PTR [esp],eax
8048770: e8 7b fd ff ff call 80484f0 <wait@plt>
8048775: 8b 44 24 1c mov eax,DWORD PTR [esp+0x1c]
8048779: 89 84 24 a0 00 00 00 mov DWORD PTR [esp+0xa0],eax
8048780: 8b 84 24 a0 00 00 00 mov eax,DWORD PTR [esp+0xa0]
8048787: 83 e0 7f and eax,0x7f
804878a: 85 c0 test eax,eax
804878c: 74 1e je 80487ac <main+0xe4>
804878e: 8b 44 24 1c mov eax,DWORD PTR [esp+0x1c]
8048792: 89 84 24 a4 00 00 00 mov DWORD PTR [esp+0xa4],eax
8048799: 8b 84 24 a4 00 00 00 mov eax,DWORD PTR [esp+0xa4]
80487a0: 83 e0 7f and eax,0x7f
80487a3: 83 c0 01 add eax,0x1
80487a6: d0 f8 sar al,1
80487a8: 84 c0 test al,al
80487aa: 7e 0e jle 80487ba <main+0xf2>
80487ac: c7 04 24 1d 89 04 08 mov DWORD PTR [esp],0x804891d
80487b3: e8 48 fd ff ff call 8048500 <puts@plt>
80487b8: eb 60 jmp 804881a <main+0x152>
80487ba: c7 44 24 0c 00 00 00 mov DWORD PTR [esp+0xc],0x0
80487c1: 00
80487c2: c7 44 24 08 2c 00 00 mov DWORD PTR [esp+0x8],0x2c
80487c9: 00
80487ca: 8b 84 24 ac 00 00 00 mov eax,DWORD PTR [esp+0xac]
80487d1: 89 44 24 04 mov DWORD PTR [esp+0x4],eax
80487d5: c7 04 24 03 00 00 00 mov DWORD PTR [esp],0x3
80487dc: e8 8f fd ff ff call 8048570 <ptrace@plt>
80487e1: 89 84 24 a8 00 00 00 mov DWORD PTR [esp+0xa8],eax
80487e8: 83 bc 24 a8 00 00 00 cmp DWORD PTR [esp+0xa8],0xb
80487ef: 0b
80487f0: 0f 85 72 ff ff ff jne 8048768 <main+0xa0>
80487f6: c7 04 24 31 89 04 08 mov DWORD PTR [esp],0x8048931
80487fd: e8 fe fc ff ff call 8048500 <puts@plt>
8048802: c7 44 24 04 09 00 00 mov DWORD PTR [esp+0x4],0x9
8048809: 00
804880a: 8b 84 24 ac 00 00 00 mov eax,DWORD PTR [esp+0xac]
8048811: 89 04 24 mov DWORD PTR [esp],eax
8048814: e8 07 fd ff ff call 8048520 <kill@plt>
8048819: 90 nop
804881a: b8 00 00 00 00 mov eax,0x0
804881f: 8d 65 f8 lea esp,[ebp-0x8]
8048822: 5b pop ebx
8048823: 5f pop edi
8048824: 5d pop ebp
8048825: c3 ret
8048826: 90 nop
```
- `80486c8 - 80486d6` Sets up stack, does stack alignment and allocates 176 bytes on the stack
- `80486d6 - 80486f4` Calls `fork()` and stores the return value on `[esp+0xac]` aka **pid**. Loads a buffer at `[esp+0x20]` aka **child_input** and call `memset(child_input, 0, 32)`
- `80486f6 - 8048711` Write 0 to `[esp+0xa8]` aka **ptrace_res** and `[esp+0x1c]` aka **wait_status**. Check if `pid == 0`. If not, jump to `8048769`
- `8048713 - 80487aa` This is the child fork. Call `prctl(1, 1)` [prctl man](https://linux.die.net/man/2/prctl), which according to [the header](https://github.com/torvalds/linux/blob/master/include/uapi/linux/prctl.h), is `prctl(PR_SET_PDEATHSIG, SIGHUP)`. This will make the child receive a SIGHUP signal if the parent dies. Call `ptrace(0, 0, 0, 0)`, which can be translated to `ptrace(PTRACE_TRACEME, 0, 0, 0)`. What it does is that it allows the parent to inspect the childs program behaviour. `puts(".Give me some shellcode, k")` is called, a buffer is loaded at `[esp+0x20]` aka **child_input** and `gets(child_input)` is called. Once `gets` finished, the program returns.
- `8048769 - 8048824` Call `wait(&wait_status)`, write **wait_status** into a temp variable and `and 127` or according to the [header for wait](https://elixir.bootlin.com/linux/latest/source/tools/include/nolibc/types.h#L107) `WIFEXITED(wait_status)`. If its true, jump to `80487ac`. Else, check `WIFSIGNALED(wait_status)`. If its not true, jump to `80487ba`.
- `80487ac - 80487b8` Call `puts("child is exiting")` and return.
- `80487ba - 8048824` Call `ptrace(3, pid, 44, 0)` which corresponds to `ptrace(PTRACE_PEEKUSER, pid, 44, NULL);` and write the return value to `ptrace_res`. Compare it with `11`. If its not equal, return. Else, `puts("no exec() for you")` and `kill(pid, 9)` and return. Judging by the output, it seems like the ptrace is looking for an `exec()` call by the child before killing it.
# level05
```
objdump -M intel -d level05
objdump -s -j .data level05
```
## main
```
08048444 <main>:
8048444: 55 push ebp
8048445: 89 e5 mov ebp,esp
8048447: 57 push edi
8048448: 53 push ebx
8048449: 83 e4 f0 and esp,0xfffffff0
804844c: 81 ec 90 00 00 00 sub esp,0x90
8048452: c7 84 24 8c 00 00 00 mov DWORD PTR [esp+0x8c],0x0
8048459: 00 00 00 00
804845d: a1 f0 97 04 08 mov eax,ds:0x80497f0
8048462: 89 44 24 08 mov DWORD PTR [esp+0x8],eax
8048466: c7 44 24 04 64 00 00 mov DWORD PTR [esp+0x4],0x64
804846d: 00
804846e: 8d 44 24 28 lea eax,[esp+0x28]
8048472: 89 04 24 mov DWORD PTR [esp],eax
8048475: e8 d6 fe ff ff call 8048350 <fgets@plt>
804847a: c7 84 24 8c 00 00 00 mov DWORD PTR [esp+0x8c],0x0
8048481: 00 00 00 00
8048485: eb 4c jmp 80484d3 <main+0x8f>
8048487: 8d 44 24 28 lea eax,[esp+0x28]
804848b: 03 84 24 8c 00 00 00 add eax,DWORD PTR [esp+0x8c]
8048492: 0f b6 00 movzx eax,BYTE PTR [eax]
8048495: 3c 40 cmp al,0x40
8048497: 7e 32 jle 80484cb <main+0x87>
8048499: 8d 44 24 28 lea eax,[esp+0x28]
804849d: 03 84 24 8c 00 00 00 add eax,DWORD PTR [esp+0x8c]
80484a4: 0f b6 00 movzx eax,BYTE PTR [eax]
80484a7: 3c 5a cmp al,0x5a
80484a9: 7f 20 jg 80484cb <main+0x87>
80484ab: 8d 44 24 28 lea eax,[esp+0x28]
80484af: 03 84 24 8c 00 00 00 add eax,DWORD PTR [esp+0x8c]
80484b6: 0f b6 00 movzx eax,BYTE PTR [eax]
80484b9: 89 c2 mov edx,eax
80484bb: 83 f2 20 xor edx,0x20
80484be: 8d 44 24 28 lea eax,[esp+0x28]
80484c2: 03 84 24 8c 00 00 00 add eax,DWORD PTR [esp+0x8c]
80484c9: 88 10 mov BYTE PTR [eax],dl
80484cb: 83 84 24 8c 00 00 00 add DWORD PTR [esp+0x8c],0x1
80484d2: 01
80484d3: 8b 9c 24 8c 00 00 00 mov ebx,DWORD PTR [esp+0x8c]
80484da: 8d 44 24 28 lea eax,[esp+0x28]
80484de: c7 44 24 1c ff ff ff mov DWORD PTR [esp+0x1c],0xffffffff
80484e5: ff
80484e6: 89 c2 mov edx,eax
80484e8: b8 00 00 00 00 mov eax,0x0
80484ed: 8b 4c 24 1c mov ecx,DWORD PTR [esp+0x1c]
80484f1: 89 d7 mov edi,edx
80484f3: f2 ae repnz scas al,BYTE PTR es:[edi]
80484f5: 89 c8 mov eax,ecx
80484f7: f7 d0 not eax
80484f9: 83 e8 01 sub eax,0x1
80484fc: 39 c3 cmp ebx,eax
80484fe: 72 87 jb 8048487 <main+0x43>
8048500: 8d 44 24 28 lea eax,[esp+0x28]
8048504: 89 04 24 mov DWORD PTR [esp],eax
8048507: e8 34 fe ff ff call 8048340 <printf@plt>
804850c: c7 04 24 00 00 00 00 mov DWORD PTR [esp],0x0
8048513: e8 58 fe ff ff call 8048370 <exit@plt>
8048518: 90 nop
```
- `8048444 - 804844c` Prep stack and stack alignment, allocates 144 bytes for the stack.
- `8048452 - 80484a9` Write 0 to a variable called **count** at `[esp+0x8c]`. Load a buffer from `[esp+0x28]` aka **inputbuf**, call `fgets(inputbuf, 100, stdin)`. Write 0 to **count** again and then jump to `80484d3` (I dont know why its so abrupt, loop maybe?), load address **inputbuf** to a tmp variable and increment the address by **count**. Derefrence the inputbuf and compare it with `64` and `90`. If its less or equals than `64` or more than `90` (not capital alphabet), jump to `80484cb`.
- `80484ab - 8048513` Load address of **inputbuf** and increment by **count**. Derefrence the index at **inputbuf** and `xor 32` the element. `inputbuf[count] = xorred_res` and increment **count**. while `strlen(inputbuf)` is more than **count**, jump back to `8048487.` When the loop exits, `printf(inputbuf)` and `exit(0)`
# level06
```
objdump -M intel -d level06
objdump -s -j .data level06
```
## main
```
8048879: 55 push ebp
804887a: 89 e5 mov ebp,esp
804887c: 83 e4 f0 and esp,0xfffffff0
804887f: 83 ec 50 sub esp,0x50
8048882: 8b 45 0c mov eax,DWORD PTR [ebp+0xc]
8048885: 89 44 24 1c mov DWORD PTR [esp+0x1c],eax
8048889: 65 a1 14 00 00 00 mov eax,gs:0x14
804888f: 89 44 24 4c mov DWORD PTR [esp+0x4c],eax
8048893: 31 c0 xor eax,eax
8048895: 50 push eax
8048896: 31 c0 xor eax,eax
8048898: 74 03 je 804889d <main+0x24>
804889a: 83 c4 04 add esp,0x4
804889d: 58 pop eax
804889e: c7 04 24 d4 8a 04 08 mov DWORD PTR [esp],0x8048ad4
80488a5: e8 e6 fc ff ff call 8048590 <puts@plt>
80488aa: c7 04 24 f8 8a 04 08 mov DWORD PTR [esp],0x8048af8
80488b1: e8 da fc ff ff call 8048590 <puts@plt>
80488b6: c7 04 24 d4 8a 04 08 mov DWORD PTR [esp],0x8048ad4
80488bd: e8 ce fc ff ff call 8048590 <puts@plt>
80488c2: b8 08 8b 04 08 mov eax,0x8048b08
80488c7: 89 04 24 mov DWORD PTR [esp],eax
80488ca: e8 41 fc ff ff call 8048510 <printf@plt>
80488cf: a1 60 a0 04 08 mov eax,ds:0x804a060
80488d4: 89 44 24 08 mov DWORD PTR [esp+0x8],eax
80488d8: c7 44 24 04 20 00 00 mov DWORD PTR [esp+0x4],0x20
80488df: 00
80488e0: 8d 44 24 2c lea eax,[esp+0x2c]
80488e4: 89 04 24 mov DWORD PTR [esp],eax
80488e7: e8 64 fc ff ff call 8048550 <fgets@plt>
80488ec: c7 04 24 d4 8a 04 08 mov DWORD PTR [esp],0x8048ad4
80488f3: e8 98 fc ff ff call 8048590 <puts@plt>
80488f8: c7 04 24 1c 8b 04 08 mov DWORD PTR [esp],0x8048b1c
80488ff: e8 8c fc ff ff call 8048590 <puts@plt>
8048904: c7 04 24 d4 8a 04 08 mov DWORD PTR [esp],0x8048ad4
804890b: e8 80 fc ff ff call 8048590 <puts@plt>
8048910: b8 40 8b 04 08 mov eax,0x8048b40
8048915: 89 04 24 mov DWORD PTR [esp],eax
8048918: e8 f3 fb ff ff call 8048510 <printf@plt>
804891d: b8 60 8a 04 08 mov eax,0x8048a60
8048922: 8d 54 24 28 lea edx,[esp+0x28]
8048926: 89 54 24 04 mov DWORD PTR [esp+0x4],edx
804892a: 89 04 24 mov DWORD PTR [esp],eax
804892d: e8 ae fc ff ff call 80485e0 <__isoc99_scanf@plt>
8048932: 8b 44 24 28 mov eax,DWORD PTR [esp+0x28]
8048936: 89 44 24 04 mov DWORD PTR [esp+0x4],eax
804893a: 8d 44 24 2c lea eax,[esp+0x2c]
804893e: 89 04 24 mov DWORD PTR [esp],eax
8048941: e8 02 fe ff ff call 8048748 <auth>
8048946: 85 c0 test eax,eax
8048948: 75 1f jne 8048969 <main+0xf0>
804894a: c7 04 24 52 8b 04 08 mov DWORD PTR [esp],0x8048b52
8048951: e8 3a fc ff ff call 8048590 <puts@plt>
8048956: c7 04 24 61 8b 04 08 mov DWORD PTR [esp],0x8048b61
804895d: e8 3e fc ff ff call 80485a0 <system@plt>
8048962: b8 00 00 00 00 mov eax,0x0
8048967: eb 05 jmp 804896e <main+0xf5>
8048969: b8 01 00 00 00 mov eax,0x1
804896e: 8b 54 24 4c mov edx,DWORD PTR [esp+0x4c]
8048972: 65 33 15 14 00 00 00 xor edx,DWORD PTR gs:0x14
8048979: 74 05 je 8048980 <main+0x107>
804897b: e8 00 fc ff ff call 8048580 <__stack_chk_fail@plt>
8048980: c9 leave
8048981: c3 ret
8048982: 90 nop
```
- `8048879 - 804887f` Set up stack frame, stack alignment and allocates 80 bytes for the stack
- `8048882 - 8048898` Load argv into `[esp+0x1c]` aka **argv** and 20 into `[esp+0x4c]` aka **canary**. and save `canary ^ canary` in memory, aka **canary_xor**. `canary ^ canary` again, and if its true, jump to `804889d`
- `804889a - 80488ca` Idk why they want to shrink the stack by 4 and pop the result to eax, I assume its for stack canary. Call these in order :
```
puts("***********************************");
puts("* level06 *");
puts("***********************************");
printf("-> Enter Login:");
```
- `80488cf - 8048918` Load a buffer to `[esp+0x2c]` aka **logininput** and call `fgets(logininput, 32, stdin)` and calls these in order:
```
puts("***********************************");
puts("* NEW ACOUNT DETECTED *");
puts("***********************************");
printf("-> Enter Serial:");
```
- `804891d - 804897b` Load an unsigned int in `[esp+0x28]` aka **serial_input**. Call `scanf("%u", &serialinput);`. After that, call `auth(logininput, serialinput)`. If the return value is not equal zero, check the stack overflow and return. If it is, `system("/bin/sh")`
## auth
```
8048748: 55 push ebp
8048749: 89 e5 mov ebp,esp
804874b: 83 ec 28 sub esp,0x28
804874e: c7 44 24 04 63 8a 04 mov DWORD PTR [esp+0x4],0x8048a63
8048755: 08
8048756: 8b 45 08 mov eax,DWORD PTR [ebp+0x8]
8048759: 89 04 24 mov DWORD PTR [esp],eax
804875c: e8 bf fd ff ff call 8048520 <strcspn@plt>
8048761: 03 45 08 add eax,DWORD PTR [ebp+0x8]
8048764: c6 00 00 mov BYTE PTR [eax],0x0
8048767: c7 44 24 04 20 00 00 mov DWORD PTR [esp+0x4],0x20
804876e: 00
804876f: 8b 45 08 mov eax,DWORD PTR [ebp+0x8]
8048772: 89 04 24 mov DWORD PTR [esp],eax
8048775: e8 56 fe ff ff call 80485d0 <strnlen@plt>
804877a: 89 45 f4 mov DWORD PTR [ebp-0xc],eax
804877d: 50 push eax
804877e: 31 c0 xor eax,eax
8048780: 74 03 je 8048785 <auth+0x3d>
8048782: 83 c4 04 add esp,0x4
8048785: 58 pop eax
8048786: 83 7d f4 05 cmp DWORD PTR [ebp-0xc],0x5
804878a: 7f 0a jg 8048796 <auth+0x4e>
804878c: b8 01 00 00 00 mov eax,0x1
8048791: e9 e1 00 00 00 jmp 8048877 <auth+0x12f>
8048796: c7 44 24 0c 00 00 00 mov DWORD PTR [esp+0xc],0x0
804879d: 00
804879e: c7 44 24 08 01 00 00 mov DWORD PTR [esp+0x8],0x1
80487a5: 00
80487a6: c7 44 24 04 00 00 00 mov DWORD PTR [esp+0x4],0x0
80487ad: 00
80487ae: c7 04 24 00 00 00 00 mov DWORD PTR [esp],0x0
80487b5: e8 36 fe ff ff call 80485f0 <ptrace@plt>
80487ba: 83 f8 ff cmp eax,0xffffffff
80487bd: 75 2e jne 80487ed <auth+0xa5>
80487bf: c7 04 24 68 8a 04 08 mov DWORD PTR [esp],0x8048a68
80487c6: e8 c5 fd ff ff call 8048590 <puts@plt>
80487cb: c7 04 24 8c 8a 04 08 mov DWORD PTR [esp],0x8048a8c
80487d2: e8 b9 fd ff ff call 8048590 <puts@plt>
80487d7: c7 04 24 b0 8a 04 08 mov DWORD PTR [esp],0x8048ab0
80487de: e8 ad fd ff ff call 8048590 <puts@plt>
80487e3: b8 01 00 00 00 mov eax,0x1
80487e8: e9 8a 00 00 00 jmp 8048877 <auth+0x12f>
80487ed: 8b 45 08 mov eax,DWORD PTR [ebp+0x8]
80487f0: 83 c0 03 add eax,0x3
80487f3: 0f b6 00 movzx eax,BYTE PTR [eax]
80487f6: 0f be c0 movsx eax,al
80487f9: 35 37 13 00 00 xor eax,0x1337
80487fe: 05 ed ed 5e 00 add eax,0x5eeded
8048803: 89 45 f0 mov DWORD PTR [ebp-0x10],eax
8048806: c7 45 ec 00 00 00 00 mov DWORD PTR [ebp-0x14],0x0
804880d: eb 4c jmp 804885b <auth+0x113>
804880f: 8b 45 ec mov eax,DWORD PTR [ebp-0x14]
8048812: 03 45 08 add eax,DWORD PTR [ebp+0x8]
8048815: 0f b6 00 movzx eax,BYTE PTR [eax]
8048818: 3c 1f cmp al,0x1f
804881a: 7f 07 jg 8048823 <auth+0xdb>
804881c: b8 01 00 00 00 mov eax,0x1
8048821: eb 54 jmp 8048877 <auth+0x12f>
8048823: 8b 45 ec mov eax,DWORD PTR [ebp-0x14]
8048826: 03 45 08 add eax,DWORD PTR [ebp+0x8]
8048829: 0f b6 00 movzx eax,BYTE PTR [eax]
804882c: 0f be c0 movsx eax,al
804882f: 89 c1 mov ecx,eax
8048831: 33 4d f0 xor ecx,DWORD PTR [ebp-0x10]
8048834: ba 2b 3b 23 88 mov edx,0x88233b2b
8048839: 89 c8 mov eax,ecx
804883b: f7 e2 mul edx
804883d: 89 c8 mov eax,ecx
804883f: 29 d0 sub eax,edx
8048841: d1 e8 shr eax,1
8048843: 01 d0 add eax,edx
8048845: c1 e8 0a shr eax,0xa
8048848: 69 c0 39 05 00 00 imul eax,eax,0x539
804884e: 89 ca mov edx,ecx
8048850: 29 c2 sub edx,eax
8048852: 89 d0 mov eax,edx
8048854: 01 45 f0 add DWORD PTR [ebp-0x10],eax
8048857: 83 45 ec 01 add DWORD PTR [ebp-0x14],0x1
804885b: 8b 45 ec mov eax,DWORD PTR [ebp-0x14]
804885e: 3b 45 f4 cmp eax,DWORD PTR [ebp-0xc]
8048861: 7c ac jl 804880f <auth+0xc7>
8048863: 8b 45 0c mov eax,DWORD PTR [ebp+0xc]
8048866: 3b 45 f0 cmp eax,DWORD PTR [ebp-0x10]
8048869: 74 07 je 8048872 <auth+0x12a>
804886b: b8 01 00 00 00 mov eax,0x1
8048870: eb 05 jmp 8048877 <auth+0x12f>
8048872: b8 00 00 00 00 mov eax,0x0
8048877: c9 leave
8048878: c3 ret
8048748: 55 push ebp
8048749: 89 e5 mov ebp,esp
804874b: 83 ec 28 sub esp,0x28
804874e: c7 44 24 04 63 8a 04 mov DWORD PTR [esp+0x4],0x8048a63
8048755: 08
8048756: 8b 45 08 mov eax,DWORD PTR [ebp+0x8]
8048759: 89 04 24 mov DWORD PTR [esp],eax
804875c: e8 bf fd ff ff call 8048520 <strcspn@plt>
8048761: 03 45 08 add eax,DWORD PTR [ebp+0x8]
8048764: c6 00 00 mov BYTE PTR [eax],0x0
8048767: c7 44 24 04 20 00 00 mov DWORD PTR [esp+0x4],0x20
804876e: 00
804876f: 8b 45 08 mov eax,DWORD PTR [ebp+0x8]
8048772: 89 04 24 mov DWORD PTR [esp],eax
8048775: e8 56 fe ff ff call 80485d0 <strnlen@plt>
804877a: 89 45 f4 mov DWORD PTR [ebp-0xc],eax
804877d: 50 push eax
804877e: 31 c0 xor eax,eax
8048780: 74 03 je 8048785 <auth+0x3d>
8048782: 83 c4 04 add esp,0x4
8048785: 58 pop eax
8048786: 83 7d f4 05 cmp DWORD PTR [ebp-0xc],0x5
804878a: 7f 0a jg 8048796 <auth+0x4e>
804878c: b8 01 00 00 00 mov eax,0x1
8048791: e9 e1 00 00 00 jmp 8048877 <auth+0x12f>
8048796: c7 44 24 0c 00 00 00 mov DWORD PTR [esp+0xc],0x0
804879d: 00
804879e: c7 44 24 08 01 00 00 mov DWORD PTR [esp+0x8],0x1
80487a5: 00
80487a6: c7 44 24 04 00 00 00 mov DWORD PTR [esp+0x4],0x0
80487ad: 00
80487ae: c7 04 24 00 00 00 00 mov DWORD PTR [esp],0x0
80487b5: e8 36 fe ff ff call 80485f0 <ptrace@plt>
80487ba: 83 f8 ff cmp eax,0xffffffff
80487bd: 75 2e jne 80487ed <auth+0xa5>
80487bf: c7 04 24 68 8a 04 08 mov DWORD PTR [esp],0x8048a68
80487c6: e8 c5 fd ff ff call 8048590 <puts@plt>
80487cb: c7 04 24 8c 8a 04 08 mov DWORD PTR [esp],0x8048a8c
80487d2: e8 b9 fd ff ff call 8048590 <puts@plt>
80487d7: c7 04 24 b0 8a 04 08 mov DWORD PTR [esp],0x8048ab0
80487de: e8 ad fd ff ff call 8048590 <puts@plt>
80487e3: b8 01 00 00 00 mov eax,0x1
80487e8: e9 8a 00 00 00 jmp 8048877 <auth+0x12f>
80487ed: 8b 45 08 mov eax,DWORD PTR [ebp+0x8]
80487f0: 83 c0 03 add eax,0x3
80487f3: 0f b6 00 movzx eax,BYTE PTR [eax]
80487f6: 0f be c0 movsx eax,al
80487f9: 35 37 13 00 00 xor eax,0x1337
80487fe: 05 ed ed 5e 00 add eax,0x5eeded
8048803: 89 45 f0 mov DWORD PTR [ebp-0x10],eax
8048806: c7 45 ec 00 00 00 00 mov DWORD PTR [ebp-0x14],0x0
804880d: eb 4c jmp 804885b <auth+0x113>
804880f: 8b 45 ec mov eax,DWORD PTR [ebp-0x14]
8048812: 03 45 08 add eax,DWORD PTR [ebp+0x8]
8048815: 0f b6 00 movzx eax,BYTE PTR [eax]
8048818: 3c 1f cmp al,0x1f
804881a: 7f 07 jg 8048823 <auth+0xdb>
804881c: b8 01 00 00 00 mov eax,0x1
8048821: eb 54 jmp 8048877 <auth+0x12f>
8048823: 8b 45 ec mov eax,DWORD PTR [ebp-0x14]
8048826: 03 45 08 add eax,DWORD PTR [ebp+0x8]
8048829: 0f b6 00 movzx eax,BYTE PTR [eax]
804882c: 0f be c0 movsx eax,al
804882f: 89 c1 mov ecx,eax
8048831: 33 4d f0 xor ecx,DWORD PTR [ebp-0x10]
8048834: ba 2b 3b 23 88 mov edx,0x88233b2b
8048839: 89 c8 mov eax,ecx
804883b: f7 e2 mul edx
804883d: 89 c8 mov eax,ecx
804883f: 29 d0 sub eax,edx
8048841: d1 e8 shr eax,1
8048843: 01 d0 add eax,edx
8048845: c1 e8 0a shr eax,0xa
8048848: 69 c0 39 05 00 00 imul eax,eax,0x539
804884e: 89 ca mov edx,ecx
8048850: 29 c2 sub edx,eax
8048852: 89 d0 mov eax,edx
8048854: 01 45 f0 add DWORD PTR [ebp-0x10],eax
8048857: 83 45 ec 01 add DWORD PTR [ebp-0x14],0x1
804885b: 8b 45 ec mov eax,DWORD PTR [ebp-0x14]
804885e: 3b 45 f4 cmp eax,DWORD PTR [ebp-0xc]
8048861: 7c ac jl 804880f <auth+0xc7>
8048863: 8b 45 0c mov eax,DWORD PTR [ebp+0xc]
8048866: 3b 45 f0 cmp eax,DWORD PTR [ebp-0x10]
8048869: 74 07 je 8048872 <auth+0x12a>
804886b: b8 01 00 00 00 mov eax,0x1
8048870: eb 05 jmp 8048877 <auth+0x12f>
8048872: b8 00 00 00 00 mov eax,0x0
8048877: c9 leave
8048878: c3 ret
```
- `8048748 - 804875c` Set up stack and allocate 40 bytes for stack, load **logininput** to `[epb+0x8]` and call `strcspn(logininput, "\n")`
- `8048761 - 804877a` Replace the character "\n" with a nullbyte for **logininput**. Call `strnlen(logininput, 32)`, save the result in a variable at `[ebp-0xc]` aka **loginlen**
- `804877d - 80487b5` Do some weird canary shit until `8048785`, where it checks if **loginlen** is greater than 5. If it is, jump to `8048796`. If not, junp to `8048877` which returns. Calls `ptrace(0, 0, 1, 0)`, can be translated to `ptrace(PTRACE_TRACEME, 0, 1, 0)` which means allow parent to trace me.
- `80487bd - 80487e8` If the return value of the ptrace is -1, run the following in order:
```
puts("\033[32m.---------------------------.");
puts("\033[31m| !! TAMPERING DETECTED !! |");
puts("\033[32m'---------------------------'");
return 1;
```
- `80487ed - 8048818` Store **logininput[3]** in a temp variable and XOR it with `0x1337 (4919)` and add `0x5eeded (6221293)`. The result is stored in `[ebp-0x10]` aka **enc_logininput** and 0 is stored in `[ebp-0x14]` aka **count**. Jump to `804885b` (loop check). Derefrence **logininput[count]** and compares it with 31. If is less or equal than, return 1.
- `8048823 - 8048861` **logininput[count]** is loaded into `ecx` and it is XOR'd against **enc_logininput** to `eax`. `0x88233b2b` which is loaded into `edx`, and we are multiplying `0x88233b2b * **logininput[count]**` and shifting the result by 1 to the right. It add back **logininput[count]** and shifts right by 10. It then multiplies 1337 and stores the value in `eax`. After that, **enc_logininput -= logininput[count]** and move **enc_logininput** to `eax`. **enc_logininput + logininput[count]** and increments **count**, compares count with login length.
- `8048863 - 8048877` Compare **serialinput** with the **enc_logininput** If its equal, return 0, else return 1
# level07
## main
```
8048723: 55 push ebp
8048724: 89 e5 mov ebp,esp
8048726: 57 push edi
8048727: 56 push esi
8048728: 53 push ebx
8048729: 83 e4 f0 and esp,
804872c: 81 ec d0 01 00 00 sub esp,0x1d0
```
This section sets up the stack frame and does stack alignment. Also allocates 464 bytes on the stack.
```
8048732: 8b 45 0c mov eax,DWORD PTR [ebp+0xc]
8048735: 89 44 24 1c mov DWORD PTR [esp+0x1c],eax
8048739: 8b 45 10 mov eax,DWORD PTR [ebp+0x10]
804873c: 89 44 24 18 mov DWORD PTR [esp+0x18],eax
8048740: 65 a1 14 00 00 00 mov eax,gs:0x14
8048746: 89 84 24 cc 01 00 00 mov DWORD PTR [esp+0x1cc],eax
804874d: 31 c0 xor eax,eax
```
This section takes in argv and writes it to `[esp+0x1c]` aka **argv**, also writes envp in `[esp+0x18]` aka **envp**, writes 20 in `[esp+0x1cc]` aka **num1** and sets up the canary mechanism
```
804874f: c7 84 24 b4 01 00 00 mov DWORD PTR [esp+0x1b4],0x0
8048756: 00 00 00 00
804875a: c7 84 24 b8 01 00 00 mov DWORD PTR [esp+0x1b8],0x0
8048761: 00 00 00 00
8048765: c7 84 24 bc 01 00 00 mov DWORD PTR [esp+0x1bc],0x0
804876c: 00 00 00 00
8048770: c7 84 24 c0 01 00 00 mov DWORD PTR [esp+0x1c0],0x0
8048777: 00 00 00 00
804877b: c7 84 24 c4 01 00 00 mov DWORD PTR [esp+0x1c4],0x0
8048782: 00 00 00 00
8048786: c7 84 24 c8 01 00 00 mov DWORD PTR [esp+0x1c8],0x0
804878d: 00 00 00 00
8048791: 8d 5c 24 24 lea ebx,[esp+0x24]
8048795: b8 00 00 00 00 mov eax,0x0
804879a: ba 64 00 00 00 mov edx,0x64
804879f: 89 df mov edi,ebx
80487a1: 89 d1 mov ecx,edx
80487a3: f3 ab rep stos DWORD PTR es:[edi],eax
80487a5: eb 43 jmp 80487ea <main+0xc7>
```
Declares 6 variables on the stack, `[esp+0x1b4]` aka **op_ret**, `[esp+0x1b8]` aka **user_cmd**, `[esp+0x1bc]` aka **var3**, `[esp+0x1c0]` aka **var4**, `[esp+0x1c4]` aka **var5**, `[esp+0x1c8]` aka **var7**, all of them have value 0 inside them. **var3 to var7** may be part of the same array.
Load a buffer from `[esp+0x24]` aka **meat** and call `memset(meat, 0, 100)` and jump to `80487ea` (looks like a loop).
```
80487a7: 8b 44 24 1c mov eax,DWORD PTR [esp+0x1c]
80487ab: 8b 00 mov eax,DWORD PTR [eax]
80487ad: c7 44 24 14 ff ff ff mov DWORD PTR [esp+0x14],0xffffffff
80487b4: ff
80487b5: 89 c2 mov edx,eax
80487b7: b8 00 00 00 00 mov eax,0x0
80487bc: 8b 4c 24 14 mov ecx,DWORD PTR [esp+0x14]
80487c0: 89 d7 mov edi,edx
80487c2: f2 ae repnz scas al,BYTE PTR es:[edi]
80487c4: 89 c8 mov eax,ecx
80487c6: f7 d0 not eax
80487c8: 8d 50 ff lea edx,[eax-0x1]
80487cb: 8b 44 24 1c mov eax,DWORD PTR [esp+0x1c]
80487cf: 8b 00 mov eax,DWORD PTR [eax]
80487d1: 89 54 24 08 mov DWORD PTR [esp+0x8],edx
80487d5: c7 44 24 04 00 00 00 mov DWORD PTR [esp+0x4],0x0
80487dc: 00
80487dd: 89 04 24 mov DWORD PTR [esp],eax
80487e0: e8 0b fd ff ff call 80484f0 <memset@plt>
80487e5: 83 44 24 1c 04 add DWORD PTR [esp+0x1c],0x4
80487ea: 8b 44 24 1c mov eax,DWORD PTR [esp+0x1c]
80487ee: 8b 00 mov eax,DWORD PTR [eax]
80487f0: 85 c0 test eax,eax
80487f2: 75 b3 jne 80487a7 <main+0x84>
80487f4: eb 43 jmp 8048839 <main+0x116>
80487f6: 8b 44 24 18 mov eax,DWORD PTR [esp+0x18]
80487fa: 8b 00 mov eax,DWORD PTR [eax]
80487fc: c7 44 24 14 ff ff ff mov DWORD PTR [esp+0x14],0xffffffff
8048803: ff
8048804: 89 c2 mov edx,eax
8048806: b8 00 00 00 00 mov eax,0x0
804880b: 8b 4c 24 14 mov ecx,DWORD PTR [esp+0x14]
804880f: 89 d7 mov edi,edx
8048811: f2 ae repnz scas al,BYTE PTR es:[edi]
8048813: 89 c8 mov eax,ecx
8048815: f7 d0 not eax
8048817: 8d 50 ff lea edx,[eax-0x1]
804881a: 8b 44 24 18 mov eax,DWORD PTR [esp+0x18]
804881e: 8b 00 mov eax,DWORD PTR [eax]
8048820: 89 54 24 08 mov DWORD PTR [esp+0x8],edx
8048824: c7 44 24 04 00 00 00 mov DWORD PTR [esp+0x4],0x0
804882b: 00
804882c: 89 04 24 mov DWORD PTR [esp],eax
804882f: e8 bc fc ff ff call 80484f0 <memset@plt>
8048834: 83 44 24 18 04 add DWORD PTR [esp+0x18],0x4
8048839: 8b 44 24 18 mov eax,DWORD PTR [esp+0x18]
804883d: 8b 00 mov whi eax,DWORD PTR [eax]
804883f: 85 c0 test eax,eax
8048841: 75 b3 jne 80487f6 <main+0xd3>
```
Load argv from **argv** and calls strlen on it after defref `strlen(*argv)` and call `memset(*argv, 0, <strlen res>)`. Increment the address of **argv** by 4 (next argument) and compare it with 0. If its not equal, loop back to `80487a7`, essentially repeating this until argv is fully cleared.
Do the same thing for envp.
```
8048843: c7 04 24 38 8b 04 08 mov DWORD PTR [esp],0x8048b38
804884a: e8 71 fc ff ff call 80484c0 <puts@plt>
804884f: b8 4b 8d 04 08 mov eax,0x8048d4b
8048854: 89 04 24 mov DWORD PTR [esp],eax
8048857: e8 14 fc ff ff call 8048470 <printf@plt>
804885c: c7 84 24 b4 01 00 00 mov DWORD PTR [esp+0x1b4],0x1
8048863: 01 00 00 00
8048867: a1 40 a0 04 08 mov eax,ds:0x804a040
804886c: 89 44 24 08 mov DWORD PTR [esp+0x8],eax
8048870: c7 44 24 04 14 00 00 mov DWORD PTR [esp+0x4],0x14
8048877: 00
8048878: 8d 84 24 b8 01 00 00 lea eax,[esp+0x1b8]
804887f: 89 04 24 mov DWORD PTR [esp],eax
8048882: e8 19 fc ff ff call 80484a0 <fgets@plt>
8048887: 8d 84 24 b8 01 00 00 lea eax,[esp+0x1b8]
804888e: c7 44 24 14 ff ff ff mov DWORD PTR [esp+0x14],0xffffffff
8048895: ff
8048896: 89 c2 mov edx,eax
8048898: b8 00 00 00 00 mov eax,0x0
804889d: 8b 4c 24 14 mov ecx,DWORD PTR [esp+0x14]
80488a1: 89 d7 mov edi,edx
80488a3: f2 ae repnz scas al,BYTE PTR es:[edi]
80488a5: 89 c8 mov eax,ecx
80488a7: f7 d0 not eax
80488a9: 83 e8 01 sub eax,0x1
80488ac: 83 e8 01 sub eax,0x1
80488af: c6 84 04 b8 01 00 00 mov BYTE PTR [esp+eax*1+0x1b8],0x0
80488b6: 00
```
Call these in order :-
```
puts("----------------------------------------------------\n"\
" Welcome to wil's crappy number storage service! \n"\
"----------------------------------------------------\n"\
" Commands: \n"\
" store - store a number into the data storage \n"\
" read - read a number from the data storage \n"\
" quit - exit the program \n"\
"----------------------------------------------------\n"\
" wil has reserved some storage :> \n"\
"----------------------------------------------------\n"\
"\n");
printf("Input command: ");
fgets(user_cmd, 20, stdin);
op_ret = 1;
```
Once the fgets returns, find the newline character in the string and replace it with a nullbyte using .
```
80488b7: 8d 84 24 b8 01 00 00 lea eax,[esp+0x1b8]
80488be: 89 c2 mov edx,eax
80488c0: b8 5b 8d 04 08 mov eax,0x8048d5b
80488c5: b9 05 00 00 00 mov ecx,0x5
80488ca: 89 d6 mov esi,edx
80488cc: 89 c7 mov edi,eax
80488ce: f3 a6 repz cmps BYTE PTR ds:[esi],BYTE PTR es:[edi]
80488d0: 0f 97 c2 seta dl
80488d3: 0f 92 c0 setb al
80488d6: 89 d1 mov ecx,edx
80488d8: 28 c1 sub cl,al
80488da: 89 c8 mov eax,ecx
80488dc: 0f be c0 movsx eax,al
80488df: 85 c0 test eax,eax
80488e1: 75 15 jne 80488f8 <main+0x1d5>
80488e3: 8d 44 24 24 lea eax,[esp+0x24]
80488e7: 89 04 24 mov DWORD PTR [esp],eax
80488ea: e8 41 fd ff ff call 8048630 <store_number>
80488ef: 89 84 24 b4 01 00 00 mov DWORD PTR [esp+0x1b4],eax
80488f6: eb 6d jmp 8048965 <main+0x242>
```
Comapre **user_cmd** with "store" using `strncmp(user_cmd, "store", 5)`. If its not equal, jump to `80488f8`, which should check next command. If it is, call `store_number(meat)` and place the return value at **op_ret**, go back to the loop start by jumping to `8048965`
```
80488f8: 8d 84 24 b8 01 00 00 lea eax,[esp+0x1b8]
80488ff: 89 c2 mov edx,eax
8048901: b8 61 8d 04 08 mov eax,0x8048d61
8048906: b9 04 00 00 00 mov ecx,0x4
804890b: 89 d6 mov esi,edx
804890d: 89 c7 mov edi,eax
804890f: f3 a6 repz cmps BYTE PTR ds:[esi],BYTE PTR es:[edi]
8048911: 0f 97 c2 seta dl
8048914: 0f 92 c0 setb al
8048917: 89 d1 mov ecx,edx
8048919: 28 c1 sub cl,al
804891b: 89 c8 mov eax,ecx
804891d: 0f be c0 movsx eax,al
8048920: 85 c0 test eax,eax
8048922: 75 15 jne 8048939 <main+0x216>
8048924: 8d 44 24 24 lea eax,[esp+0x24]
8048928: 89 04 24 mov DWORD PTR [esp],eax
804892b: e8 a7 fd ff ff call 80486d7 <read_number>
8048930: 89 84 24 b4 01 00 00 mov DWORD PTR [esp+0x1b4],eax
8048937: eb 2c jmp 8048965 <main+0x242>
```
Do the same thing to `read`, `strncmp(user_cmd, "read", 4)` and call `read_number(meat)` , saving the output at **op_ret** and jumping to `8048965`
```
8048939: 8d 84 24 b8 01 00 00 lea eax,[esp+0x1b8]
8048940: 89 c2 mov edx,eax
8048942: b8 66 8d 04 08 mov eax,0x8048d66
8048947: b9 04 00 00 00 mov ecx,0x4
804894c: 89 d6 mov esi,edx
804894e: 89 c7 mov edi,eax
8048950: f3 a6 repz cmps BYTE PTR ds:[esi],BYTE PTR es:[edi]
8048952: 0f 97 c2 seta dl
8048955: 0f 92 c0 setb al
8048958: 89 d1 mov ecx,edx
804895a: 28 c1 sub cl,al
804895c: 89 c8 mov eax,ecx
804895e: 0f be c0 movsx eax,al
8048961: 85 c0 test eax,eax
8048963: 74 6a je 80489cf <main+0x2ac>
```
Do the same thing to `"quit"`, `strncmp(user_cmd, "quit", 4)` and jump to `80489cf`, which checks for canary and returns.
```
8048965: 83 bc 24 b4 01 00 00 cmp DWORD PTR [esp+0x1b4],0x0
804896c: 00
804896d: 74 1a je 8048989 <main+0x266>
804896f: b8 6b 8d 04 08 mov eax,0x8048d6b
8048974: 8d 94 24 b8 01 00 00 lea edx,[esp+0x1b8]
804897b: 89 54 24 04 mov DWORD PTR [esp+0x4],edx
804897f: 89 04 24 mov DWORD PTR [esp],eax
8048982: e8 e9 fa ff ff call 8048470 <printf@plt>
8048987: eb 18 jmp 80489a1 <main+0x27e>
8048989: b8 88 8d 04 08 mov eax,0x8048d88
804898e: 8d 94 24 b8 01 00 00 lea edx,[esp+0x1b8]
8048995: 89 54 24 04 mov DWORD PTR [esp+0x4],edx
8048999: 89 04 24 mov DWORD PTR [esp],eax
804899c: e8 cf fa ff ff call 8048470 <printf@plt>
80489a1: 8d 84 24 b8 01 00 00 lea eax,[esp+0x1b8]
80489a8: c7 00 00 00 00 00 mov DWORD PTR [eax],0x0
80489ae: c7 40 04 00 00 00 00 mov DWORD PTR [eax+0x4],0x0
80489b5: c7 40 08 00 00 00 00 mov DWORD PTR [eax+0x8],0x0
80489bc: c7 40 0c 00 00 00 00 mov DWORD PTR [eax+0xc],0x0
80489c3: c7 40 10 00 00 00 00 mov DWORD PTR [eax+0x10],0x0
80489ca: e9 80 fe ff ff jmp 804884f <main+0x12c>
80489cf: 90 nop
80489d0: b8 00 00 00 00 mov eax,0x0
80489d5: 8b b4 24 cc 01 00 00 mov esi,DWORD PTR [esp+0x1cc]
80489dc: 65 33 35 14 00 00 00 xor esi,DWORD PTR gs:0x14
80489e3: 74 05 je 80489ea <main+0x2c7>
80489e5: e8 c6 fa ff ff call 80484b0 <__stack_chk_fail@plt>
80489ea: 8d 65 f4 lea esp,[ebp-0xc]
80489ed: 5b pop ebx
80489ee: 5e pop esi
80489ef: 5f pop edi
80489f0: 5d pop ebp
80489f1: c3 ret
```
Check for empty **op_ret** If it is empty or 0, jump to `8048989` which calls
`printf(" Completed %s command successfully\n", user_cmd)`, clears all vars and goes back to loop. If the loop exits, check canary and return.
If **op_ret** is non zero, call `printf("Failed to do %s command\n", user_cmd)`
## read_number
```
080486d7 <read_number>:
80486d7: 55 push ebp
80486d8: 89 e5 mov ebp,esp
80486da: 83 ec 28 sub esp,0x28
80486dd: c7 45 f4 00 00 00 00 mov DWORD PTR [ebp-0xc],0x0
80486e4: b8 dd 8a 04 08 mov eax,0x8048add
80486e9: 89 04 24 mov DWORD PTR [esp],eax
80486ec: e8 7f fd ff ff call 8048470 <printf@plt>
80486f1: e8 f1 fe ff ff call 80485e7 <get_unum>
80486f6: 89 45 f4 mov DWORD PTR [ebp-0xc],eax
80486f9: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
80486fc: c1 e0 02 shl eax,0x2
80486ff: 03 45 08 add eax,DWORD PTR [ebp+0x8]
8048702: 8b 10 mov edx,DWORD PTR [eax]
8048704: b8 1b 8b 04 08 mov eax,0x8048b1b
8048709: 89 54 24 08 mov DWORD PTR [esp+0x8],edx
804870d: 8b 55 f4 mov edx,DWORD PTR [ebp-0xc]
8048710: 89 54 24 04 mov DWORD PTR [esp+0x4],edx
8048714: 89 04 24 mov DWORD PTR [esp],eax
8048717: e8 54 fd ff ff call 8048470 <printf@plt>
804871c: b8 00 00 00 00 mov eax,0x0
8048721: c9 leave
8048722: c3 ret
```
Sets up stack and allocates 40 bytes on the stack. Clears out `[ebp-0xc]` aka **num_input** and calls `printf("Index: ")` and then calls `get_unum()`, and stores the value in **num_input**. The number is then shifted left by 2 and added by the first argument in `[ebp+0x8]` aka **meat**. **meat** is then derefrenced and put to `edx` and calls `printf("Number at data[%u] is %u, ", num_input, meat)`. Returns 0
## store_number
```
8048630: 55 push ebp
8048631: 89 e5 mov ebp,esp
8048633: 83 ec 28 sub esp,0x28
8048636: c7 45 f0 00 00 00 00 mov DWORD PTR [ebp-0x10],0x0
804863d: c7 45 f4 00 00 00 00 mov DWORD PTR [ebp-0xc],0x0
8048644: b8 d3 8a 04 08 mov eax,0x8048ad3
8048649: 89 04 24 mov DWORD PTR [esp],eax
804864c: e8 1f fe ff ff call 8048470 <printf@plt>
8048651: e8 91 ff ff ff call 80485e7 <get_unum>
8048656: 89 45 f0 mov DWORD PTR [ebp-0x10],eax
8048659: b8 dd 8a 04 08 mov eax,0x8048add
804865e: 89 04 24 mov DWORD PTR [esp],eax
8048661: e8 0a fe ff ff call 8048470 <printf@plt>
8048666: e8 7c ff ff ff call 80485e7 <get_unum>
804866b: 89 45 f4 mov DWORD PTR [ebp-0xc],eax
804866e: 8b 4d f4 mov ecx,DWORD PTR [ebp-0xc]
8048671: ba ab aa aa aa mov edx,0xaaaaaaab
8048676: 89 c8 mov eax,ecx
8048678: f7 e2 mul edx
804867a: d1 ea shr edx,1
804867c: 89 d0 mov eax,edx
804867e: 01 c0 add eax,eax
8048680: 01 d0 add eax,edx
8048682: 89 ca mov edx,ecx
8048684: 29 c2 sub edx,eax
8048686: 85 d2 test edx,edx
8048688: 74 0d je 8048697 <store_number+0x67>
804868a: 8b 45 f0 mov eax,DWORD PTR [ebp-0x10]
804868d: c1 e8 18 shr eax,0x18
8048690: 3d b7 00 00 00 cmp eax,0xb7
8048695: 75 2b jne 80486c2 <store_number+0x92>
8048697: c7 04 24 e6 8a 04 08 mov DWORD PTR [esp],0x8048ae6
804869e: e8 1d fe ff ff call 80484c0 <puts@plt>
80486a3: c7 04 24 f8 8a 04 08 mov DWORD PTR [esp],0x8048af8
80486aa: e8 11 fe ff ff call 80484c0 <puts@plt>
80486af: c7 04 24 e6 8a 04 08 mov DWORD PTR [esp],0x8048ae6
80486b6: e8 05 fe ff ff call 80484c0 <puts@plt>
80486bb: b8 01 00 00 00 mov eax,0x1
80486c0: eb 13 jmp 80486d5 <store_number+0xa5>
80486c2: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
80486c5: c1 e0 02 shl eax,0x2
80486c8: 03 45 08 add eax,DWORD PTR [ebp+0x8]
80486cb: 8b 55 f0 mov edx,DWORD PTR [ebp-0x10]
80486ce: 89 10 mov DWORD PTR [eax],edx
80486d0: b8 00 00 00 00 mov eax,0x0
80486d5: c9 leave
80486d6: c3 ret
```
Sets up stack and allocates 40 bytes on the stack. Clears up `[ebp-0x10]` aka **num_input** and `[ebp-0xc]` aka **idx_input**. Call `printf("Number: ")` and then call `get_unum()`, which assigns the return value to **num_input** Do the same for **idx_input**, with the print being `printf("Index: ")`. The pseudocode for `8048671 - 8048686` is like so.
```
let idx_input = ...;
let temp1 = 0xaaaaaaab;
idx_input += temp1
temp1 >> 1
let temp2 = temp1
temp2 *= 2
temp2 += temp1
let temp3 = 0xaaaaaaab - temp2
temp3 == 0?
```
If the condition is true jump to `8048697` which calls
```
puts(" *** ERROR! ***");
puts(" This index is reserved for wil!");
puts(" *** ERROR! ***");
```
and return 1
The pseudocode for `804868a - 8048690` is like so
```
num_input >> 0x18 == 0xb7?
```
If its not true, jump to `80486c2` which does `meat[idx_input] = num_input;`
and return 0. jump to `8048697` if its not.
## get_unum
```
80485e7: 55 push ebp
80485e8: 89 e5 mov ebp,esp
80485ea: 83 ec 28 sub esp,0x28
80485ed: c7 45 f4 00 00 00 00 mov DWORD PTR [ebp-0xc],0x0
80485f4: a1 60 a0 04 08 mov eax,ds:0x804a060
80485f9: 89 04 24 mov DWORD PTR [esp],eax
80485fc: e8 7f fe ff ff call 8048480 <fflush@plt>
8048601: b8 d0 8a 04 08 mov eax,0x8048ad0
8048606: 8d 55 f4 lea edx,[ebp-0xc]
8048609: 89 54 24 04 mov DWORD PTR [esp+0x4],edx
804860d: 89 04 24 mov DWORD PTR [esp],eax
8048610: e8 eb fe ff ff call 8048500 <__isoc99_scanf@plt>
8048615: e8 aa ff ff ff call 80485c4 <clear_stdin>
804861a: 8b 45 f4 mov eax,DWORD PTR [ebp-0xc]
804861d: c9 leave
804861e: c3 ret
```
Setup stack and allocate 40 bytes for the stack, declare a variable at `[ebp-0xc]` aka **res**, call `fflush(stdout)` and then ` scanf("%u", &res)`. Call `clear_stdin()` and return **res**
## clear_stdin
```
080485c4 <clear_stdin>:
80485c4: 55 push ebp
80485c5: 89 e5 mov ebp,esp
80485c7: 83 ec 18 sub esp,0x18
80485ca: c6 45 f7 00 mov BYTE PTR [ebp-0x9],0x0
80485ce: eb 01 jmp 80485d1 <clear_stdin+0xd>
80485d0: 90 nop
80485d1: e8 ba fe ff ff call 8048490 <getchar@plt>
80485d6: 88 45 f7 mov BYTE PTR [ebp-0x9],al
80485d9: 80 7d f7 0a cmp BYTE PTR [ebp-0x9],0xa
80485dd: 74 06 je 80485e5 <clear_stdin+0x21>
80485df: 80 7d f7 ff cmp BYTE PTR [ebp-0x9],0xff
80485e3: 75 eb jne 80485d0 <clear_stdin+0xc>
80485e5: c9 leave
80485e6: c3 ret
```
Setup stack and allocate 24 bytes for the stack, declare a variable at `[ebp-0x9]` aka **curr**, jump to `80485d1` (loop start), calls `getchar()` and stores ret value at **curr**. Compare **curr** with '\n' and -1. Return of they are either equal. jump back to `80485d0` if they are not (infinite loop)