菜鸟萌新如有错误还请大佬指正。一、simple_js查看页面源代码查看是否真的只是密码爆破。function dechiffre(pass_enc){ var pass 70,65,85,88,32,80,65,83,83,87,79,82,68,32,72,65,72,65; var tab pass_enc.split(,); var tab2 pass.split(,);var i,j,k,l0,m,n,o,p ;i 0;j tab.length; k j (l) (n0); n tab2.length; for(i (o0); i (k j n); i ){o tab[i-l];p String.fromCharCode((o tab2[i])); if(i 5)break;} for(i (o0); i (k j n); i ){ o tab[i-l]; if(i 5 i k-1) p String.fromCharCode((o tab2[i])); } p String.fromCharCode(tab2[17]); pass p;return pass; } String[fromCharCode](dechiffre(\x35\x35\x2c\x35\x36\x2c\x35\x34\x2c\x37\x39\x2c\x31\x31\x35\x2c\x36\x39\x2c\x31\x31\x34\x2c\x31\x31\x36\x2c\x31\x30\x37\x2c\x34\x39\x2c\x35\x30)); h window.prompt(Enter password); alert( dechiffre(h) );结果页面源代码中发现存在密码加密方式审计代码。发现我们无论输入怎样的密码都只会返回“FAUX PASSWORD HAHA”即“70,65,85,88,32,80,65,83,83,87,79,82,68,32,72,65,72,65”所对应的ascii码值那么最后的flag就应该在“\x35\x35\x2c\x35\x36\x2c\x35\x34\x2c\x37\x39\x2c\x31\x31\x35\x2c\x36\x39\x2c\x31\x31\x34\x2c\x31\x31\x36\x2c\x31\x30\x37\x2c\x34\x39\x2c\x35\x30”上十六进制转十进制字符拼接再对应ASCII码表。55,56,54,79,115,69,114,116,107,49,50 “786OsErtk12”所以flag就是Cyberpeace{786OsErtk12}。二、easytornado进入网站后是个目录对三个文件进行查看。观察url文件读取方式为filename和fileshash传参filename为访问文件绝对路径先尝试一下直接访问/fllllllllllllag。报错。filehash结合hints.txt文件得出filehash是cookie值连接MD5加密后的filename再进行MD5加密得出的结果那么该如何获取cookie结合第二个文件和题目来看Tornado的render()方法其实是其Web框架中用于渲染预定义模板文件的核心函数通常与RequestHandler配合使用。考虑通过模板注入来获取cookie。在Tornado中要渲染一个模板通常是在RequestHandler类中调用self.render()方法。Tornado为了方便开发者在渲染模板时会自动把一些“常用对象”注入到模板的命名空间Context中。查阅Tornado的官方源码模板中默认可以直接使用一个名为handler的变量指向的就是RequestHandler实例对象不仅如此通常还会有一个self变量和handler是等价的指向同一个对象。在报错页面尝试模板注入测试发现有响应百度了下ORZ是个网络梗那么模板注入点确认。尝试访问handler.settings。成功获取cookie那么接下来就是将/fllllllllllllag进行MD5加密然后拼接cookie再进行MD5加密进行访问获取flag。三、shrine进入主页面。import flask import os app flask.Flask(__name__) app.config[FLAG] os.environ.pop(FLAG) app.route(/) def index(): return open(__file__).read() app.route(/shrine/) def shrine(shrine): def safe_jinja(s): s s.replace((, ).replace(), ) blacklist [config, self] return .join([{{% set {}None%}}.format(c) for c in blacklist]) s return flask.render_template_string(safe_jinja(shrine)) if __name__ __main__: app.run(debugTrue)发现以上python代码发现FLAG存储在Flask应用的配置字典app.config中。/shrine/path:shrine路由接受用户传入的path参数将其传入safe_jinjia过滤后直接交给render_template_string渲染。审计过滤规则所有的“(”“)”都会被替换为空那么无法通过模板注入执行函数黑名单“config”、“self”会被提前置为None无法直接使用。在Python中__globals__是Python函数对象的内置属性返回函数所在模块的全局变量字典。Flask中current_app是Flask的应用上下文代理指向当前运行的Flask应用实例app是染过黑名单的核心对象。url_for(或get_flashed_messages)是Flask模板内置全局函数无需调用即可访问其__globals__属性获取函数所在上下文的全局字典变量。综合上面知识构造payload/shrine/{{url_for.__globals__[current_app].config}}/shrine/{{get_flashed_messages.__globals__[current_app].config}}获取flag。菜鸟萌新如有错误还请大佬指正。