lua-users home
lua-l archive

[Date Prev][Date Next][Thread Prev][Thread Next] [Date Index] [Thread Index]


2014-08-12 17:11 GMT+02:00 Steven Degutis <sbdegutis@gmail.com>:
> This is my current understanding of how _G and _ENV work based on my
> reading of the manual and Pil^3 along with Roberto's response to my
> first email:
>
> When you create a new Lua state, its registry (i.e. the table at
> LUA_REGISTRYINDEX) contains a special table somewhere which is
> henceforth known as "the global environment".
>
> When you load a new chunk for Lua to execute, something essentially
> equivalent to the following pseudocode happens:
>
>     local _ENV = lua_gettable(L, LUA_REGISTRYINDEX, <global environment's key>)
>     _ENV._G = _ENV
>
> That is, _G is a "global" (i.e. a field on the key _ENV) referring to
> the initial value of _ENV, which is "the global environment".

I don't agree, but I may wrong.

I think it's like this:

1. When you create a new Lua state, you have an empty stack and two tables,
the registry and the global environment. The global environment is empty, no _G
yet, but it behaves like an upvalue called _ENV, so that all
references to global
variables get referred to it. The registry contains two items, [1]
being the current
running thread and [2] being a the global environment.

2. When you call luaL_openlibs, some stuff gets put in the registry.
Into the global
environment go all the standard library items, including _G
initialized to value [2]
from the registry.

3. The standalone Lua interpreter does both the above, so you never see
the intermediate state, but if you write your own host program, you can.

4. If you compile a function using `load` or `loadstring`, its _ENV is one of:
   a. An _ENV parameter.
   b. The _ENV specified in the `load`.
   c. An _ENV upvalue.

Note that _ENV is never global. You can assign anything you like to _ENV._ENV,
it will not be retrieved if you merely say _ENV.