Reputation: 484
I am working on a project that takes a Lua string and converts it into a C string – not at all difficult, of course. However, I run into trouble when attempting to convert a binary representation of a function, i.e. one produced by a call to string.dump
, to a C string. I am having trouble reading the entire string.
While it is not the ultimate goal of the project, consider the following simple example where I print out the characters in a string one-by-one using a C function called chars
that I have registered for use in Lua:
static void chars(char* cp) {
char* pointer = cp;
while (*pointer) {
printf("%c\n", *pointer);
++pointer;
}
return;
}
static int lua_chars(lua_State* L) {
lua_len(L, 1);
size_t len = static_cast<size_t>(lua_tonumber(L, -1)) + 1;
lua_pop(L, 1);
if (len > 0) {
char* cp = static_cast<char*>(malloc(len));
strcat(cp, lua_tostring(L, 1));
chars(cp);
free(cp);
}
return 0;
}
Calling chars
from a Lua script would look like this:
chars("Hello World!")
and would print out the characters one by one with each followed by a newline.
Now to the actual issue. Consider this example where I declare a function in Lua, dump it with string.dump
, and then pass that string to the function chars
to print out its characters individually:
local function foo()
print("foo")
return
end
local s = assert(string.dump(foo))
chars(s)
The string s
in its entirety, not printed with my function chars
, looks something like this:
uaS?
xV(w@=stdin@A@$@&?&?printfoo_ENV
However, chars
only prints the first five bytes:
u
a
S
(Note there are supposed to be two lines of whitespace before the 'u'.)
I am almost certain that this is due to null characters within the string, which I think interferes with lua_tostring
's functionality. I have come across lua_Writer
for reading chunks, but I have no idea how to use/code it. How can I successfully convert the entire string on the Lua stack to a C string?
Upvotes: 2
Views: 1388
Reputation: 5847
I am almost certain that this is due to null characters within the string
Yes, it's exactly because Lua strings can contain zeroes.
which I think interferes with lua_tostring's functionality.
And this is false. lua_tostring()
works as intended. It's just strcat()
you're using will only copy the data up to the nearest zero byte.
If you need to copy the string, use memcpy
, passing it both the pointer to Lua string data and Lua string length (lua_len
, lua_rawlen
, etc).
But just for printing you don't even need to copy anything. Pass the len
variable as an argument to chars()
, and check that length instead of waiting for zero byte.
Upvotes: 2
Reputation: 199
The Problem isn't lua_tostring
but strcat
which copies until it finds an null characters. Same Problem with your chars
function.
That should work:
memcpy(cp, lua_tostring(L, 1), len);
chars(cp, len);
...
static void chars(char* cp, size_t len) {
for (size_t i = 0; i < len; ++i, ++cp) {
putchar(*cp);
}
}
Upvotes: 2