Python中的Sandbox Lua并使用调试钩子在沙箱中执行协同程序

时间:2014-08-28 07:20:47

标签: python debugging lua sandbox coroutine

我有一个python程序,用户应该能够在界面中编写自己的脚本。这里的语言应该是Lua。到目前为止,我有Lua沙箱,可以像这样一次执行用户代码:

lua_sandbox = lua.eval('''
function()   
  local function run(untrusted_code)
    local untrusted_function, message = load(untrusted_code, nil, 't', _ENV)
    if not untrusted_function then return nil, message end
    return xpcall(untrusted_function, errorHandler)
  end

-------------------- Defining Python functions and objects in Lua -------------------

  local function PythonFunctionInLua(arg)
    return python.eval('PythonFunction(' .. arg ..')')
  end

  PythonObjectInLua = python.eval('PythonObject')

-- Pass them to the local Lua sandbox
  _ENV = { print = print,
           PythonFunction = PythonFunctionInLua,
           PythonObject = PythonObjectInLua,
           coroutine = coroutine }

  assert(run [[''' + code + ''' ]])
end
''')

到目前为止,这么好。现在我想添加逐步执行代码的可能性。到目前为止我最好的想法是使用调试钩子,所以我尝试了这个:

... (from above until _ENV)
debug.sethook(scripterDebug, "l")
func = assert( run [[''' + code  + ''' ]] )
co = coroutine.create(func)
coroutine.resume(co)

出现问题:在用户再次点击处理下一行之前,我无法调用coroutine.yield暂停例程。从外面拨打电话,例如在scripterDebug钩子中,以及从内部调用它(将其插入code部分)导致attempt to yield across C-Call boundary t(我想我继续进出沙箱)在后一种情况下)。

我也尝试在run[[ ]]]中创建协同程序,这是一个令人屈服的作品,但我不能在外面调用coroutine.resume(co),因为`co'只在沙箱中知道。我必须从外部调用它,因为当用户点击继续时调用它,如果我将访问权限等等传递到沙箱中,整个事情就变得毫无用处。

有没有办法在沙盒中逐步执行此代码?

0 个答案:

没有答案