# [Write-Up RootMe] Cracking - Part 1 ## :blue_book: Challenge List - [1. ELF x64 - Crackme automating](#ELF-x64---Crackme-automating) - [2. PE x86 - SEHVEH](#PE-x86---SEHVEH) ## :book: ELF x64 - Crackme automating ### :pencil: Đề bài ![image](https://hackmd.io/_uploads/rJb23RRa6.png) ### :massage: Tổng quan Nhận được một file bin thực thi trên linux với thông tin như sau ![image](https://hackmd.io/_uploads/BkDgTC06T.png) Kiểm tra sơ bộ ![image](https://hackmd.io/_uploads/r1Evp0ApT.png) Kiểm tra qua <span style="color:green">strings.exe</span> ![image](https://hackmd.io/_uploads/rk4wCCA6a.png) ![image](https://hackmd.io/_uploads/HJhwA0AT6.png) Bài thuộc dạng check password ### :knife: Phân tích 1. Mở file bằng <span style="color:blue">ida pro</span> 2. Phân tích hàm <span style="color:red">main</span> ![image](https://hackmd.io/_uploads/SJ-6VJk06.png) - Chương trình nhận input là đường dẫn 1 file - Hàm <span style="color:red">check</span> là hàm cấn quan tâm để phân tích quy trình xác thực mật khẩu của chương trình 3. Phân tích hàm <span style="color:red">check</span> ![image](https://hackmd.io/_uploads/rJ1a8JJRa.png) - Hàm có hơn 1000 node bắt đầu bằng đặt 2 giá trị tmp và kết thúc bằng gọi hàm <span style="color:red">badboy</span> nếu kết quả xác thực không đúng, <span style="color:red">ida pro</span> không thể tạo graph trên 1000 node nên ta buộc phải giải mã bằng tay - Phân tích node đầu ![image](https://hackmd.io/_uploads/H1NIO1kRp.png) - Phân tích node thứ 2 ![image](https://hackmd.io/_uploads/rkgJfQJRT.png) > Các node còn lại cũng sử dụng quy luật tương tự, cơ bản tại mỗi node sẽ tìm được một byte của file bằng cách xor **tmp2** và một giá trị **constant** - Công việc cần làm là viết một đoạn **IDA Python** để xử lý tất cả các node từ địa chỉ **0x0AD1** đến địa chỉ **0x03EC2B0** ```python! import idautils import ida_bytes import idc start_address = 0xad8 end_address = 0x03EC2B0 flag = [] def find_instruction(start_address, end_address): current_address = start_address tmp2 = 0 const = 0 while current_address < end_address: mnem = idc.print_insn_mnem(current_address) if mnem == 'mov': operand_type = idc.get_operand_type(current_address, 0) if operand_type == idc.o_displ: operand_value = idc.get_operand_value(current_address, 1) print(f"tmp2: {hex(operand_value)}") tmp2 = operand_value elif mnem == 'xor': operand_type = idc.get_operand_type(current_address, 0) if operand_type == idc.o_reg: operand_value = idc.get_operand_value(current_address, 1) print(f"const: {hex(operand_value)}") const = operand_value if tmp2 != 0 and const != 0: flag.append(tmp2 ^ const) current_address = idc.next_head(current_address) find_instruction(start_address, end_address) with open("out.txt","wb") as f: f.write(bytes(flag)) f.close() ``` - Giải mã và nhận được file sau ![image](https://hackmd.io/_uploads/ByM6gIJ06.png) Đây là một file thực thi của MSDOS ta tiến hành chạy thử bằng DOSBOX ![image](https://hackmd.io/_uploads/ryNoZLJCp.png) ## :book: PE x86 - SEHVEH ### :pencil: Đề bài ![image](https://hackmd.io/_uploads/B1UhndeCa.png) ### :massage: Tổng quan Bài yêu cầu tìm password nhập vào Gọi một số hàm đáng nghi liên quan đến xử lý ngoại lệ ![image](https://hackmd.io/_uploads/SJrKxFx06.png) Thông tin rõ ràng hơn từ 2 resource của challenge ![image](https://hackmd.io/_uploads/rJRI-YlRT.png) ### :knife: Phân tích Hàm start nơ bản như sau ![image](https://hackmd.io/_uploads/BJg3qXvA6.png) #### Phân tích hàm **check_paswd** - Hàm lấy địa chỉ của chuỗi nhập vào, kiểm tra độ dài của chuỗi xem có bằng 12 không, nếu không thì sẽ nhảy đến **loc_E414AD** và thoát hàm ![image](https://hackmd.io/_uploads/rkK4omDCT.png) - Load 4 bytes đầu của password vào thanh ghi eax sau đó xor với **0x5A643059** và so sánh với **0x3628552E** để tìm xác thực 4 byte đầu từ đó ta lấy được 4 byte đầu của password ![image](https://hackmd.io/_uploads/ryPy6Nv06.png) - Hàm đăng ký **off_E430A0 - 0x1000** để làm địa chỉ xử lý ngoại lệ và load tiếp 4 bytes tiếp theo của password vào eax, đưa **0x495F4265** vào ebx và tạo ngoại lệ để nhảy đến đoạn code xử lý sau đó xor giá trị trong eax với ebx và so sánh 4 bytes sau khi xử lý với **0x0FF2CF8E5** ![image](https://hackmd.io/_uploads/r1gZAVvCT.png) - Đoạn code xử lý ngoại lệ được đăng ký ![image](https://hackmd.io/_uploads/HkfF0VDC6.png) - Vậy là nó sẽ cộng 4 bytes input được load vào eax với **0x48335621** khi đã biết được quy luật ta có thể tìm ljai được mật khẩu - Tiếp theo nó đăng ký một **AddVectoredExceptionHandler** trong đó 2 vùng code được push vào stack như sau ![image](https://hackmd.io/_uploads/ry4zEHDRT.png) - Đầu tiên nó trừ 4 bytes cuối với **0x21486553** ![image](https://hackmd.io/_uploads/HJlH4HwCa.png) - Sau đó nó cộng kết quả với **0x48335621** ![image](https://hackmd.io/_uploads/BJkdEBDAT.png) - Cuối cùng nó xor kết quả với **0x74406653** và so sánh với **0x3C4C7440** ![image](https://hackmd.io/_uploads/Hk124SvRp.png) - Giải ngược lại ta có thể tìm được 4 bytes cuối của password :::spoiler password: weLl_d@nE!!! :::