# NotOsint (Reverse) ## Challenge ![image](https://hackmd.io/_uploads/S15W3WAsR.png) - Thử thách cho ta file `ELF 64`. ## Bước 1: - Xem source code hàm `main` file bằng IDA. ``` __int64 __fastcall main(int a1, char **a2, char **a3) { int i; // [rsp+Ch] [rbp-134h] _DWORD v5[24]; // [rsp+10h] [rbp-130h] BYREF char s[200]; // [rsp+70h] [rbp-D0h] BYREF unsigned __int64 v7; // [rsp+138h] [rbp-8h] v7 = __readfsqword(0x28u); sleep(1u); puts("Alice: Hey Bob, I just found something cool"); sleep(1u); puts("Bob: Huh?"); sleep(1u); puts("Alice: PIS Club is inviting me to join. But I don't know what it is?"); sleep(1u); puts("Bob: Hmm!!! Let me see."); sleep(1u); printf("Bob: PIS stands for: "); sleep(1u); fgets(s1, 100, stdin); s1[strcspn(s1, "\n")] = 0; sub_12A9(s1); if ( !strcmp(s1, "PTITInformationSecurity") ) { puts("Alice: Oh. I found it. I will contact them."); sleep(1u); puts("PIS bot: How can I help you?"); sleep(1u); printf("PIS bot: Please enter the captcha code to verify you are human: "); sleep(1u); for ( i = 0; i <= 22; ++i ) __isoc99_scanf("%d", &v5[i]); if ( sub_1649(v5) ) { puts("The application for joining has been submitted. Please wait for the results from admin!!!"); sleep(1u); sub_16F8(&unk_4020, s); puts(s); } else { puts("Verification failed. Please try again later!!!"); sleep(1u); } } else { puts( "It seems that something is not right. Admin gives me information that its template is 'XXXX Xxxxxxxxxxx Xxxxxxxx'"); sleep(1u); puts("Let's check again!!!"); } return 0LL; } ``` ## Bước 2: ``` fgets(s1, 100, stdin); s1[strcspn(s1, "\n")] = 0; sub_12A9(s1); if ( !strcmp(s1, "PTITInformationSecurity") ) ``` - Tại đoạn này chương trình yêu cầu chúng ta nhập vào `s1` một chuỗi ký tự và so sánh chuỗi `s1` có giống với chuỗi ký tự `PTITInformationSecurity` hay không nếu khác chương trình sẽ thoát. ## Bước 3: ``` for ( i = 0; i <= 22; ++i ) __isoc99_scanf("%d", &v5[i]); if ( sub_1649(v5) ) { puts("The application for joining has been submitted. Please wait for the results from admin!!!"); sleep(1u); sub_16F8(&unk_4020, s); puts(s); } else { puts("Verification failed. Please try again later!!!"); sleep(1u); } } else { puts( "It seems that something is not right. Admin gives me information that its template is 'XXXX Xxxxxxxxxxx Xxxxxxxx'"); sleep(1u); puts("Let's check again!!!"); } ``` - Phân tích đoạn code này ta thấy chương trình sẽ kiểm tra 23 số nhập từ bàn phím tại hàm `sub_1649(v5)` nếu 23 số này phù hợp thì chương trình sẽ trả Flag cho chúng ta. ## Phương pháp: ### Cách 1: - Chúng ta sẽ sửa lại điều kiện tại hàm `sub_1649(v5)` `!=` sang `==`. ``` __int64 __fastcall sub_1649(__int64 a1) { int i; // [rsp+14h] [rbp-1Ch] char v3[9]; // [rsp+1Fh] [rbp-11h] BYREF unsigned __int64 v4; // [rsp+28h] [rbp-8h] v4 = __readfsqword(0x28u); for ( i = 0; i <= 22; ++i ) { sub_1387(*(4LL * i + a1), v3); sub_152F(v3); if ( sub_14CB(v3) != dword_4020[i] ) return 0LL; } return 1LL; } ``` ![image](https://hackmd.io/_uploads/BJ8bkG0o0.png) - Chọn vào hàm bool và chuyển sang ngôn ngữ Assembly. ![image](https://hackmd.io/_uploads/r19FkM0sC.png) - Chuyển `jz` sang `jnz` sau đó lưu lại. - ![image](https://hackmd.io/_uploads/S1f4Ez0oC.png) - Bây giờ điều kiện đã thành `==` ta có thể nhập bất kỳ 23 chữ số để ra flag. ### Cách 2: - Chúng ta vào hàm `sub_1649(v5)` . - ![image](https://hackmd.io/_uploads/SJYLrGCi0.png) ``` sub_1387(*(4LL * i + a1), v3); ``` - Vào hàm này để xem tác dụng của nó. ``` size_t __fastcall sub_1387(int a1, char *a2) { int v2; // eax size_t result; // rax char v5; // [rsp+1Fh] [rbp-11h] int v6; // [rsp+20h] [rbp-10h] int i; // [rsp+24h] [rbp-Ch] int j; // [rsp+28h] [rbp-8h] int v9; // [rsp+2Ch] [rbp-4h] v6 = 0; while ( a1 > 0 ) { v2 = v6++; a2[v2] = a1 % 2 + 48; a1 /= 2; } a2[v6] = 0; v9 = strlen(a2); for ( i = 0; i < v9 / 2; ++i ) { v5 = a2[i]; a2[i] = a2[v9 - i - 1]; a2[v9 - i - 1] = v5; } while ( 1 ) { result = strlen(a2); if ( result > 7 ) break; for ( j = strlen(a2); j >= 0; --j ) a2[j + 1] = a2[j]; *a2 = 48; } return result; } ``` - Hàm này có chức năng chuyển số nhập từ bàn sang hệ nhị phân, nếu chưa đủ 8bit thì đoạn mã sau sẽ bổ sung bit 0 để đủ 8 bit. ``` while ( 1 ) { result = strlen(a2); if ( result > 7 ) break; for ( j = strlen(a2); j >= 0; --j ) a2[j + 1] = a2[j]; *a2 = '0'; } return result; ``` - Tiếp tục xem source của hàm `sub_152F(v3)`. ``` __int64 __fastcall sub_152F(const char *a1) { __int64 result; // rax char v2; // [rsp+17h] [rbp-9h] int i; // [rsp+18h] [rbp-8h] int v4; // [rsp+1Ch] [rbp-4h] v4 = strlen(a1); for ( i = 0; ; ++i ) { result = (v4 / 2); if ( i >= result ) break; v2 = a1[i]; a1[i] = a1[v4 - i - 1]; a1[v4 - i - 1] = v2; } return result; } ``` - Hàm này có chức năng lật ngược bit của các số. - Trở lại hàm `if ( sub_14CB(v3) != dword_4020[i] ) return 0LL; } return 1LL;` - Vào hàm `sub_14CB(v3)`. ``` __int64 __fastcall sub_14CB(const char *a1) { unsigned int v2; // [rsp+10h] [rbp-10h] int v3; // [rsp+14h] [rbp-Ch] int i; // [rsp+18h] [rbp-8h] v2 = 0; v3 = 1; for ( i = strlen(a1) - 1; i >= 0; --i ) { if ( a1[i] == 49 ) v2 += v3; v3 *= 2; } return v2; } ``` - Hàm này có chức năng trả các giá trị nhị phân sau khi đổi về giá trị DEC. - Để chương trình trả về true. Thì ta phải nhập 23 số hệ DEC sao cho khi thực hiện các hàm trên bằng với giá trị cho trước trong hàm `dword_4020[i]`. - ![image](https://hackmd.io/_uploads/B18DtGCiR.png)