flask模板注入
概览
Flask是一个python的编写的轻量级Web应用框架,使用Jinja2作为渲染引擎。
当渲染的模板是用户可控的时候,就可能会造成模板注入(SSTI)
实例讲解
起一个简单的ssti网页
1 |
|
get传入s=ibukifalling,页面显示效果如下
但是此处利用jinja2的变量包裹标识符(双大括号)来构造的话
运算式被执行。如果输入的是js代码还可以造成xss
SSTI命令执行
先科普一下python的几个魔术方法
1 |
|
使用示例如下(前面的那个是两个单引号不是双引号,是一个啥都没有的字符串)
_class_ 魔术方法返回类型所属的对象,此处的字符串返回了str类
__mro__魔术方法返回str类的基类,再尝试用__subclasses__返回引用
可以看到通过不断通过对象的继承关系层层递进,到此处已经有这么多类,其中很可能有我们可以利用的类。
1 |
|
寻找重载过的init类(不含wrapper字样)
翻字典,眼尖的话应该已经看到eval了,接下来要干的事大家已经心知肚明了
可以看到成功执行了命令
得到最终的payload:
?s={{''.__class__.__mro__[1].__subclasses__()[80].__init__.__globals__['__builtins__']['eval']('__import__("os").popen("the command you want to exec").read()')}}
那此时实质上攻击者已经可以令服务器执行任意命令,攻陷服务器易如反掌
基本上就是这样一个思路,通过不断利用魔术方法在类中跳转,寻找可以利用的关键函数
总结与感想
SSTI的payload不是一成不变的,不过理解原理之后结合脚本还是很容易能找出相应的payload的
条条大路通罗马,同一道题也可能有多个payloads存在
感觉对python这类面向对象的语言有了更进一步的认知,写脚本的能力也略微提升了一丶丶
接下来还要继续努力