【问题标题】:node.js vm and external methodsnode.js 虚拟机和外部方法
【发布时间】:2016-10-30 09:12:53
【问题描述】:

我在开发使用 vm 的应用时遇到了一些问题:

无限while (true) {}循环内的外部方法调用不会超时:

var context = {
    externalMethod: function(str) {console.log(str)}
};
vm.runInNewContext("while (true) {externalMethod('test')}", context, {}, 100);

上面的代码会无限运行,即使在 100 毫秒超时之后也是如此;

vm.runInNewContext("for (;;) {}", {}, {}, 100)

还有这个..即使没有运行外部方法,它也不会超时。

最后一个问题:在vm2 内部调用外部方法运行不受信任的代码有多安全:

var context = {
    method: (str) => {
        createMessage("id", str) // some external (non-sandbox) method that sends an authenticated POST request to a chat app...
    }
}

那么,是否可以使用该方法检索外部globalthis

【问题讨论】:

    标签: javascript node.js virtual-machine


    【解决方案1】:

    上面的代码会无限运行,即使在 100 毫秒超时之后也是如此

    timeout 应该是options 对象的属性,而不是单独的参数:

    vm.runInNewContext("while (true) {externalMethod('test')}", context, { timeout : 100 })
    

    还有最后一个问题:在vm2 内部调用外部方法运行不受信任的代码有多安全。

    我假设您的意思是 vm(内置 Node 模块)而不是 vm2。在这种情况下,当您在 VM 外部调用代码时,它可能会访问“外部”代码的全局变量、局部变量和 this

    const vm    = require('vm');
    let SECRET  = 'this is a secret';
    let context = {
      console, // to allow `console.log()` calls inside the sandboxed code
      externalMethod() {
        console.log('Secret outside:', SECRET)
      }
    };
    vm.runInNewContext(`
    console.log('Secret inside: ', typeof SECRET);
    externalMethod();
    `, context);
    

    您不能直接从“内部”代码访问SECRET,但外部方法可以访问它。因此,如果externalMethod 有可能运行不受信任的代码,那么它将是不安全的。

    【讨论】:

    • 很棒的答案,还有一个简单的问题:vm2(修改后的 vm 模块)通过去上下文化来防止非沙箱化的外部方法在沙箱中获取本地变量、全局变量或 this?
    • @Aurieh 你必须自己尝试一下,我自己实际上对vm2 没有任何经验:)
    猜你喜欢
    • 2021-01-15
    • 2011-02-12
    • 1970-01-01
    • 2012-08-04
    • 1970-01-01
    • 2019-01-05
    • 2014-12-17
    • 1970-01-01
    • 2013-10-23
    相关资源
    最近更新 更多