Проблема Lua при попытке запустить скрипт в отдельном состоянии lua

Я новичок во внедрении Lua, и мне удалось зайти так далеко в своем путешествии. Я сохраняю результат luaL_loadfile в глобальном масштабе, чтобы его можно было вызывать повторно. Моя текущая проблема заключается в том, что когда я пытаюсь запустить скрипт внутри скрипта в состоянии, отличном от текущего состояния скриптов, я получаю segfault.

struct State
{
    // deleted and defaulted ctors removed for brevity
    State(std::string name, uint32_t id) : 
        id(id), state(luaL_newstate()), name(std::move(name))
    {
        assert(this->state != nullptr && "state is nullptr");
        assert(this->name != "" && "Name is empty");

        luaL_openlibs(state);
        lua_settop(state, 0);
    }

    ~State()
    {
        lua_close(state);
    }

    uint32_t id;
    lua_State* state;
    std::string name;
};

struct Script
{
    // deleted and defaulted ctors removed for brevity
    Script(std::string name, uint32_t id, uint32_t stateId) :
        id(id), stateId(stateId), name(name) { }

    uint32_t id;
    uint32_t stateId;
    std::string name;
};

Вот как загружаются скрипты:

bool ScriptEngine::LoadScript(State& state, std::string filename)
{
    auto success(luaL_loadfile(state.state, filename.c_str()) == 0);
    lua_setglobal(state.state, filename.c_str());

    scripts.emplace_back(filename, nextScriptId, state.id);
    ++nextScriptId;

    return success;
}

Моя функция выполнения:

 int ScriptEngine::RunScript(Script& script)
 {
    auto state(GetState(script.stateId));
    assert(state != nullptr && "Script state is invalid");

    lua_getglobal(state->state, script.name.c_str());
    // Segfaults in the above line in index2adr called by lua_getfield 
    // if the state is not the same as the current state

    auto top(lua_gettop(state->state));
    if(lua_pcall(state->state, 0, LUA_MULTRET, 0))
    {
        std::cout << "unable to run script " << script.name << " " << 
            lua_tostring(state->state, -1) << std::endl;
        assert(0);
    }

    return top - lua_gettop(state->state);
}

Моя привязка, которая вызывает ScriptEngine::RunScript(Script&)

int RunScript(lua_State* state)
{
    auto script((Script*)lua_touserdata(state, -1));

    lua_pushliteral(state, "ScriptEngine"); 
    lua_gettable(state, LUA_REGISTRYINDEX);

    auto engine((ScriptEngine*)lua_touserdata(state, -1));

    return engine->RunScript(*script);
}

И мой тестовый скрипт:

local script = ScriptEngine.GetScript("config.txt")
print(script)

local rets = ScriptEngine.RunScript(script)
-- crash happens in the above line if the target script has a 
-- separate state than this script itself

print(rets)

person bsdunx    schedule 25.10.2014    source источник
comment
если вам это нужно не только для обучения, я бы порекомендовал LuaState@github   -  person Dmitry Ledentsov    schedule 28.10.2014
comment
См. это: stackoverflow.com/a/19388679/1142167   -  person Joel Cornett    schedule 26.09.2015
comment
Что вы можете сделать, так это сохранить фрагмент скрипта с помощью lua_dump, а затем загрузить фрагмент в отдельном состоянии lua с помощью luaL_loadbuffer   -  person Joel Cornett    schedule 26.09.2015