What is the second argument of lua_newstate(lua_Alloc f, void *ud) used for?

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
3 messages Options
Reply | Threaded
Open this post in threaded view
|

What is the second argument of lua_newstate(lua_Alloc f, void *ud) used for?

孙世龙 sunshilong
Hi, list

What is the second argument of lua_newstate(lua_Alloc f, void *ud) used for?

As per the manual of
Lua(https://www.lua.org/manual/5.3/manual.html#lua_Alloc), which says
that:
The second argument, ud, is an opaque pointer that Lua passes to the
allocator in every call.

The second argument is NULL when lua_newsate() is called by
luaL_newstate() which is invoked by main() function.
For your reference, here is the related code snippet:
LUALIB_API lua_State *luaL_newstate (void) {
  lua_State *L = lua_newstate(l_alloc, NULL);
  if (L) {
    int *warnstate;  /* space for warning state */
    lua_atpanic(L, &panic);
    warnstate = (int *)lua_newuserdatauv(L, sizeof(int), 0);
    luaL_ref(L, LUA_REGISTRYINDEX);  /* make sure it won't be collected */
    *warnstate = 0;  /* default is warnings off */
    lua_setwarnf(L, warnf, warnstate);
  }
  return L;
}


I am a little confused that when should I pass a valid pointer to
lua_newstate() as a second argument?
What is it used for?

I would be grateful to have some help with this question.
It would better if you can give me some simple examples.

Best regards
Sunshilong
v
Reply | Threaded
Open this post in threaded view
|

Re: What is the second argument of lua_newstate(lua_Alloc f, void *ud) used for?

v
It's not used (i.e. never dereferenced) for anything by Lua or its
default allocator. It is a user data pointer, a very common thing in C
APIs in general. It allows you to pass data to your custom allocator.
In practice, you can store anything that fits into pointer type there,
not just pointers (integers are most reasonable, but tiny struct might
work too).

In theory, this could be a use case: you have your custom allocator
that can allocate memory in few different manners (say, in faster and
smaller vs slower and bigger regions) and you want to have your
different Lua states use different options. Then you can write

allocOpts* opts = malloc(sizeof(allocOpts));
opts.region = ALLOC_SLOW;
lua_newstate(my_alloc, opts);

Bottom line is that this option is only usable by custom allocators,
default one ignores it completely.

On Tue, 2020-10-20 at 15:58 +0800, 孙世龙 sunshilong wrote:

> Hi, list
>
> What is the second argument of lua_newstate(lua_Alloc f, void *ud)
> used for?
>
> As per the manual of
> Lua(https://www.lua.org/manual/5.3/manual.html#lua_Alloc), which says
> that:
> The second argument, ud, is an opaque pointer that Lua passes to the
> allocator in every call.
>
> The second argument is NULL when lua_newsate() is called by
> luaL_newstate() which is invoked by main() function.
> For your reference, here is the related code snippet:
> LUALIB_API lua_State *luaL_newstate (void) {
>   lua_State *L = lua_newstate(l_alloc, NULL);
>   if (L) {
>     int *warnstate;  /* space for warning state */
>     lua_atpanic(L, &panic);
>     warnstate = (int *)lua_newuserdatauv(L, sizeof(int), 0);
>     luaL_ref(L, LUA_REGISTRYINDEX);  /* make sure it won't be
> collected */
>     *warnstate = 0;  /* default is warnings off */
>     lua_setwarnf(L, warnf, warnstate);
>   }
>   return L;
> }
>
>
> I am a little confused that when should I pass a valid pointer to
> lua_newstate() as a second argument?
> What is it used for?
>
> I would be grateful to have some help with this question.
> It would better if you can give me some simple examples.
>
> Best regards
> Sunshilong
Reply | Threaded
Open this post in threaded view
|

Re: What is the second argument of lua_newstate(lua_Alloc f, void *ud) used for?

Viacheslav Usov
On Tue, Oct 20, 2020 at 10:53 AM v <[hidden email]> wrote:

> It allows you to pass data to your custom allocator.

That is not its entire use.

> Bottom line is that this option is only usable by custom allocators,
> default one ignores it completely.

This can be used outside of the allocation context. This pointer can
be retrieved from any Lua state at any time (by C code). so this could
be used, for example, to associate a Lua state with some other
structure or value that fits in a pointer value. Specifically an
application that hosts multiple Lua states will probably want to have
some other data dedicated to a given state, so it might have something
like:

struct instance
{
    lua_State *L;
    /* other data */
};

It might be useful to instantiate L with the ud that is the address of
struct instance that contains L, so that there is a one-to-one
relationship between struct instance (and the other data) and
lua_State.

A very similar means is given by the extra space (or is it bytes?) in
a Lua state, so the implementor has some design choices.

Cheers,
V.