Lua 函数重定义,以及安全的运行时环境(沙盒)

您所在的位置:网站首页 LUA调用外部函数 Lua 函数重定义,以及安全的运行时环境(沙盒)

Lua 函数重定义,以及安全的运行时环境(沙盒)

2023-10-27 00:32| 来源: 网络整理| 查看: 265

  本文章借鉴《Lua程序设计(第四版)》。

一、函数重定义

  在Lua中,由于函数可以被保存在普通变量中,因此在Lua语言中可以轻松地重新定义函数,甚至是预定义函数。这种机制也正是Lua语言灵活的原因之一。通常,当重新定义一个函数的时候,我们需要在新的实现中调用原来的那个函数。例如,假设要冲i性能定义函数sin以使其参数以角度为单位而不是以弧度为单位。那么这个新函数就可以先对参数进行转换,然后调用原来的sin函数进行真正的计算。代码可能形如:

print(math.pi) --> 3.1415926535898 print(math.sin(30 * (math.pi / 180))) --> 0.5 local oldSin = math.sin math.sin = function(x) return oldSin(x * (math.pi / 180)) end print(math.sin(30)) --> 0.5

  另一种更清晰的完成重新定义的写法是:

print(math.sin(30 * (math.pi / 180))) --> 0.5 do local oldSin = math.sin local k = math.pi / 180 math.sin = function(x) return oldSin(x * k) end end print(math.sin(30)) --> 0.5

  上述代码使用了do代码段来限制局部变量oldSin的作用范围;根据可见性规则,局部变量oldSin只在这部分代码段中有效。因此,只有新版本的函数sin才能访问原来的sin函数,其他部分代码则访问不了。

二、沙盒

  将老版本的函数保存在一个私有的变量中,只用新版本的函数才能访问它,这样的技术创建一个安全的运行环境,即所谓的 “沙盒(sandbox)”。   我们可以使用同样的技巧来创建安全的运行时环境(secure environment),即所谓的沙盒。当执行一些诸如从远程服务器上下载到的未受信任代码(untrusted code)时,安全的运行时环境非常重要。例如,我们可以通过使用闭包(closure)重定义函数 io.open 来限制一个程序能够访问的文件:

do local oldOpen = io.open local access_OK = function(filename, mode) -- check access end io.open = function(filename,mode) if access_OK(filename, mode) then return oldOpen(filename, mode) else return nil, "access denied" end end end

  上述代码的巧妙之处在于,在经过重新定义后,一个程序只能通过新的受限版本来调用原来未受限版本的 io.open 函数。示例代码将原来不安全的版本保存为闭包的一个私有变量,该变量无法从外部访问。通过这一技巧,就可以在保证简洁性和灵活性的前提下在Lua语言本身上构建Lua沙盒。   相对于提供一套大而全(one-size-fits-all)的解决方案,Lua语言提供的是一套 “元机制(meta-mechanism)”,借助这种机制可以根据特定的安全需求来裁剪具体的运行时环境(真实的沙盒除了保护外部文件还有更多的功能)。



【本文地址】


今日新闻


推荐新闻


CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3