View Full Version : Why is setmetatable omitted?
ThirdSign
April 21st, 2023, 11:25
Hello,
I'm wondering if the SmiteWorks team could elaborate on why setmetatable is excluded from the fantasy grounds sandbox. Specifically which security concerns they're addressing by doing so.
Other sandboxes don't appear to take the same precautions (ref: https://stackoverflow.com/a/61744388)
damned
April 21st, 2023, 14:51
I have no insight to the matter - but I am a little amused that the post you linked has a single upvote :ninja:
ThirdSign
April 21st, 2023, 14:53
I have no insight to the matter - but I am a little amused that the post you linked has a single upvote :ninja:
It's remarkably difficult to find anything online about setmetatable being a security vulnerability. I had to make do with what I could find.
LordEntrails
April 21st, 2023, 18:22
You might want to clarify why you would want access to this. i.e. giving a supportable use case might give SmiteWork more incentive to consider the change.
ThirdSign
April 21st, 2023, 18:41
Sure, no problem.
If you want to create a re-usable object in Lua, you write something like this:
function Account:new (o)
o = o or {} -- create object if user does not provide one
setmetatable(o, self)
self.__index = self
return o
end
When the user calls `Account:new()`, it sets the metatable for `o` to `Account`. Basically what this means is we've created a new table, and whenever the user calls something on it that doesn't exist, it goes up the chain to see if it exists on the metatable.
This lets us create instances of a table with isolated namespaces and inheritance.
The programming guide explains it well here: https://www.lua.org/pil/16.1.html
Right now, the way GFU works is you define functions in a file, and it slaps those into a table defined in `extension.xml`. It's kind of like having 1 instance of an object.
If we had setmetatable, we could operate the exact same way, except expose a `new` method (like above) that you could call in the exact same way, that returned its own instance. So instead of being constrained to a single table, you could create as many instances as you needed.
Just for completeness sake, it'd look something like this in FGU:
-- scripts/account.lua
local Class = {}
function new()
o = o or {} -- create object if user does not provide one
setmetatable(o, Class)
self.__index = Class
return o
end
function Class:setSomething(what)
self.something = what
end
function Class:saySomething()
Debug.chat(self.something)
end
-- someOtherScript.lua
function onInit()
local a = Example:new()
local b = Example:new()
a:setSomething("foobar")
b:setSomething("baz")
a:saySomething()
b:saySomething()
end
I was surprised it was disabled when I took a dive into extensions, and my search on the forums only brought up a 9 year old post that didn't provide any answers - just said it was disabled.
Moon Wizard
April 21st, 2023, 18:43
It has been disabled since before we took over the company as part of the initial sandbox for the application set up by the original developers. I've looked at the various limits applied to the sandbox and generally agree with the choices made so far.
The disabled functions in the sandbox are not required to build a ruleset in FG, as can be shown by what has been built to date. Many of those functions do have impact on security of the environment as well as potentially opening up attack vectors that we may not know about currently. Additionally, some of those functions open up a whole host of developer support issues as well. Given that the functions are not necessary to build rulesets and extensions, but more about different ways to structure and do things; I don't think it's worth the development time and risk to review and change that subsystem given the lengthy list of things we already want to get done with limited resources.
Regards,
JPG
Powered by vBulletin® Version 4.2.1 Copyright © 2026 vBulletin Solutions, Inc. All rights reserved.