This is a read-only snapshot of the ComputerCraft forums, taken in April 2020.
Lignum's profile picture

[CC1.74/MC1.7.10] os.queueEvent strips table args of their metatables

Started by Lignum, 25 September 2015 - 01:30 PM
Lignum #1
Posted 25 September 2015 - 03:30 PM
Description:
When an event is queued with tables as arguments, said tables will no longer have their metatable when they are retrieved from os.pullEvent.

Reproduction steps:
The bug can be reproduced with this code snippet:

local tbl = setmetatable({}, { __call = function() print("It works!") end })
tbl() --# Will print "It works!"

os.queueEvent("test", tbl)
local _, brokenTbl = os.pullEvent("test")
brokenTbl() --# attempt to call table
SquidDev #2
Posted 26 September 2015 - 10:17 AM
Pretty sure this is intended behaviour, though I couldn't say for sure.

This is because the queued table isn't the same table, but rather a copy of it. For instance:

local tbl = {}
os.queueEvent("foo", tbl)
local _, new = os.pullEvent("foo")

print(new, tbl, new == tbl)
Will print out two different tables and then false.

Functions also cannot be sent through any CC API (peripherals, os.queueEvent, etc…), due to how conversion works. A solution would be to generate a random id and queue that id instead of the table, and lookup the table based of the id when pulling from the queue.
Lignum #3
Posted 26 September 2015 - 10:36 AM
Pretty sure this is intended behaviour, though I couldn't say for sure.

This is because the queued table isn't the same table, but rather a copy of it. For instance:

Will print out two different tables and then false.

In which case the bug would be that the metatable doesn't get copied as well, or am I missing something?

A solution would be to generate a random id and queue that id instead of the table, and lookup the table based of the id when pulling from the queue.

Which is also what I ended up doing :P/>. Since my tables are cached objects, I allowed the receiving end to access the objects by their cache ID, which is a very ugly way to do it… but it works!
SquidDev #4
Posted 26 September 2015 - 10:39 AM
In which case the bug would be that the metatable doesn't get copied as well, or am I missing something?

The issue is that functions aren't copied either (they are just converted to nil), so a copied metatable would just be a table of nils. I'll agree that the event handling is kinda odd in CC (I'm trying to fix some bits in CCTweaks but that is a way off yet), but I think the the reasons for acting the way it does are valid.
dan200 #5
Posted 11 December 2015 - 03:17 PM
Not a bug. Event args can only contain Plain Old Data.