论文阅读-Security Charm of WASM

Security Charm of WASM

slide

  1. WASM基础概念介绍
    • 功能
    • 线性内存模型
    • 函数表
  2. Emscripten介绍和安全问题
    • Emscripten介绍
    • 对WASM做的加固
    • 还有可能出现的安全问题
  3. WASM新的利用方式(emscripten.h)
    • buffer flow -> XSS
    • indirect function calls -> XSS & RCE
      • 更骚的姿势(syscall, 内联eval)
  4. 结论
    • To 开发团队
    • To 开发者
    • 未来方向
      • 逆向堆实现
      • 测信道姿势?
      • 条件竞争有无?

WASM基础

基本引入

1
2
3
4
5
6
7
8
9
10
11
12
13
14
;; simple.wasm
(module
// 声明import的函数i, 因此需要传入importObj
(func $i (import "imports" "i") (param i32))
// 声明export的函数e, 可在js中调用
(func (export "e")
i32.const 42
call $i))

var importObject = { imports: { i: arg => console.log(arg) } };
// 拿到wasm字节码后可以还原成一个module,然后module实例化为instance
fetch('simple.wasm').then(response => response.arrayBuffer())
.then(bytes => instantiate(bytes, importObject))
.then(instance => instance.exports.e());

函数指针

call_indirect实现了动态调用,类似函数指针,他根据索引从函数表中拿到函数实际地址进行执行。

Memory

在WebAssembly的内存模型中,内存表示为一个连续的无类型字节范围,称为线性内存。可以通过WebAssembly的.Memory方法或WebAssembly通过JavaScript分配此内存。分配的内存量由开发人员决定,最小内存单位为页面(64 KB)。内存也动态的,因此可以根据需要通过memory的.grow方法进行扩展。

js可以访问c++的内存。
https://www.cntofu.com/book/150/zh/ch2-c-js/ch2-03-mem-model.md

WebAssembly.Memory是一段字节数组(a large array of bytes),用于在WebAssembly和JavaScript之间共享内存。
http://www.itminus.com/blog/2018/01/19/WindWhisper/WASM/%E5%9F%BA%E6%9C%AC%E5%8E%9F%E7%90%86/WASM%E5%9F%BA%E6%9C%AC%E5%8E%9F%E7%90%863%E2%80%94%E2%80%94Memory/

在默认设置下,Emscripten堆一经初始化,容量就固定了,无法再扩容。而某些程序在运行时需要的内存容量在不同工况下可能有很大的波动。为了满足某些极端工况的需求而将TOTAL_MEMORY设置得非常高无疑是非常浪费的,为此,Emscripten提供了可在运行时扩大内存容量的模式,欲开启该模式,需要在编译时增加-s ALLOW_MEMORY_GROWTH=1参数。

Emscripten提供了两种内存分配器:
dlmalloc(默认), 由Doug Lea创建的内存分配器,其变种广泛使用于Linux等。
emmalloc, 专为Emscripten设计的内存分配器。

emmalloc的代码体积小于dlmalloc,但是如果程序中频繁申请大量的小片内存,使用dlmalloc性能较好。除非对于代码体积极度敏感的场合,否则使用默认的dlmalloc内存分配器无疑是更优的选择。

编译时设置MALLOC参数可以指定内存分配器,比如下列命令指定使用emmalloc:
emcc mem.cc -s MALLOC=”emmalloc” -o mem.js

为什么WASM比JS更快

https://juejin.im/entry/5bfb53a3f265da61715e02cd

WASM的漏洞利用

Buffer flow -> XSS

如下图,p1是一个js中硬编码的字符串,p2是从GET或POST请求传入的。因为p1是静态的,所以开发人员不需要执行任何过滤就可以直接输出到DOM。但是由于bof2存在缓冲区溢出,因此用户输入将溢出bof2并覆盖bof1,然后输出到DOM中从而造成XSS。
-w665

Indirect function calls -> XSS

想成功利用有两个条件:

  1. 覆盖函数指针
  2. 含有危险函数

-w658

payload溢出覆盖out函数指针为emscripten_run_script函数指针导致xss。

RCE

Server-side Remote Code Execution
和XSS一样,只是改下node的payload

Proudly powered by Hexo and Theme by Hacker
© 2021 LFY