在lua编程语言中,我知道你可以使用metamethod __metatable锁定userdata的metatable,这样任何人都无法使用getmetatable()函数查看userdata的metatable。但是,我仍然希望在锁定之后访问该元表。所以,我的问题是,在userdata的metatable被锁定之后,仍然可能(可能通过一些后门)仍然可以获得锁定的用户数据的元表,或者它是不可能的(如果是这样,那么对于什么原因)?
编辑#1: 我想要了解这一点的动机是因为我试图找到Roblox API的后门,以便我可以更有效地编写游戏脚本。
答案 0 :(得分:2)
这至少适用于lua 5.3
在lua中,您可以使用调试库方法debug.getmetatable
。无论__metatable
元方法如何,都应返回原始元表。
在C中,您可以将函数lua_getmetatable
用于相同的目的。
此外,你总是可以在某个地方创建一个变量来存储metatable,稍后可以通过该变量访问它。
此外,如果您使用了luaL_newmetatable
,那么您仍然可以在注册时使用您使用的元表名称找到metatable。
答案 1 :(得分:2)
您已声明您正在使用ROBLOX。当你考虑它时,他们已经将这些东西锁定为原因。为什么? 安全目的。允许脚本编写者访问此类内容危险并构成 严重威胁 。所以答案是否定的,一旦锁定,没有参考就没有办法回到metatable,因为如果有锁就没有意义。
ROBLOX还摆脱了调试库中的所有功能,但最近添加了debug.traceback
,因此debug.getmetatable
肯定无法解决问题。强>
但是,根据您的推理,是完成任务的其他方法。我会在这里讨论其中一些:
1)如果要设置实例的元表,请使用自己的表创建虚假实例,然后使用__index
和{{ 1}}控制对对象的属性和方法的访问
2)如果您想设置库的元表,我们采用与 1 相同的方法,创建一个假表并使用__newindex
索引旧表。
3)如果要设置全局环境的元表,请使用预先存在的元表设置一个新元素。请务必使用__index
,以便其他变量仍可使用!
至于阅读 metatables,没有你不能这样做。
除此之外,如果您锁定自己的表,如前所述, 是一种访问metatable的方法。只需存储参考即可。最好的方法是在__index
范围块中创建一个名为meta
的局部变量。
我希望这能回答你的问题,我试图专门针对ROBLOX,因为那是你的问题所在。