gpt4 book ai didi

c# - 取消主机 yield

转载 作者:太空宇宙 更新时间:2023-11-03 15:23:18 24 4
gpt4 key购买 nike

我有一个使用 Lua 脚本的网络应用程序。启动应用程序后,我创建一个全局 Lua 状态并加载所有包含各种函数的脚本文件,并为每个连接的客户端创建一个 Lua 线程,用于该连接。

// On start
var GL = luaL_newstate();
// register functions...
// load scripts...

// On connection
connection.State = lua_newthread(GL);

当使用脚本的请求进来时,我获取全局函数并调用它。

var NL = connection.State;

var result = lua_resume(NL, 0);
if (result != 0 && result != LUA_YIELD)
{
// error...
result = 0;
}

if (result == 0)
{
// function returned...
}

现在,有些脚本需要客户端对某些内容做出响应,因此我放弃了这些功能,等待它。当收到响应时,脚本将使用 lua_resume(NL, 1) 恢复。

// Lua
text("How are you?")
local response = select("Good", "Bad")

// Host
private int select(IntPtr L)
{
// send response request...
return lua_yield(L, 1);
}

// On response
lua_pushstring(NL, response);
var result = lua_resume(NL, 1);
// ...

我的问题是我需要能够取消那个 yield,并从 Lua 函数返回,而不需要在 Lua 函数中执行更多代码,也不需要向脚本添加额外的代码。换句话说,我基本上想让 Lua 线程抛出异常,回到开始,忘记它曾经执行过那个函数。

这可能吗?

有一件事我认为可能奏效,但没有奏效,那就是调用 lua_error。结果是 lua_error 调用中的 SEHException。我假设是因为脚本当前未运行,但正在生成。

最佳答案

虽然我没有找到一种方法来清除线程的空白(我认为这是不可能的),但我确实找到了解决 lua_newthread 工作原理的解决方案。

当线程被创建时,对它的引用被放在“全局”状态的堆栈中,并且直到它被从那里移除时才会被收集。清理线程所需要做的就是使用 lua_remove 将其从堆栈中删除。这需要您定期创建新线程,但这对我来说不是什么大问题。

我现在正在跟踪创建的线程及其在堆栈中的索引,因此当我出于任何原因(取消、错误等)完成它们时,我可以删除它们。所有其他索引都会更新,因为删除会移动之后的索引。

if (sessionOver)
{
lua_remove(GL, thread.StackIndex);

foreach (var t in threads)
{
if (t.StackIndex > thread.StackIndex)
t.StackIndex--;
}
}

关于c# - 取消主机 yield ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36388266/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com