PicoCTF - fermat-strings
Background
該函數返回 str1 開頭連續都不含字符串 str2 中字符的字符數。
這個函數返回一個int值轉換的整數。如果冇有有效的轉換可以執行,它返回零。
snprintf() 函數的返回值是輸出到 str 緩沖區中的字符數,不包括字符串結尾的空字符 \0。如果 snprintf() 輸出的字符數超過了 size 參數指定的緩沖區大小,則輸出的結果會被截斷,只有 size - 1 個字符被寫入緩沖區,最後一個字符為字符串結尾的空字符 \0。
需要注意的是,snprintf() 函數返回的字符數並不包括字符串結尾的空字符 \0,因此如果需要將輸出結果作為一個字符串使用,則需要在緩沖區的末尾添加一個空字符 \0。
Source code
1 | |
Recon
這一題太難了,可以參考的資料太少了,大部分都有一些缺失,而且重點是server那邊的版本和local端不一樣就會造成got hijack失敗,所以最後沒有做出來,但是流程還是可以記錄一下
- 先leak stack的資訊,例如
__libc_start_main的address,然後到1查詢,光這一點耗費蠻多心力,雖然說只要查看stack上相對的位置,就可以leak出對應的address,但有可能是因為我local端libc version是2.35,所以找不到對應位置上libc address在database上的資料,但在server端卻找得到,這可能是不同版本的鍋,所以之後要找這種libc version的問題,最好是在2.31的地方 - 得到libc的version後,就可以算offset,得出libc base address,然後就可以得出system在libc的確切位址,又由於這隻程式只會執行一次就結束,所以我們要讓他有loop的效果,作法就是got hijack,改掉pow的got位置為main function的address 註:為甚麼是改pow而不是atoi, snprintf之類的function的got?因為pow是比較後面被呼叫到的function,如果修改那些太早被呼叫到的function就馬上從main開始執行,這樣就沒辦法開shell了
- 接著我們可以再從第二次的input中開shell,這就是最後做不出來的地方,除了之前沒有寫過相關的題目不知道怎麼開以外,其他WP234也都會有其他的問題
Exploit
1 | |
Flag: picoCTF{f3rm4t_pwn1ng_s1nc3_th3_17th_c3ntury}