xref: /vim-8.2.3635/src/if_lua.c (revision 96f45c0b)
1 /* vi:set ts=8 sts=4 sw=4 noet:
2  *
3  * VIM - Vi IMproved	by Bram Moolenaar
4  *
5  * Lua interface by Luis Carvalho
6  *
7  * Do ":help uganda"  in Vim to read copying and usage conditions.
8  * Do ":help credits" in Vim to see a list of people who contributed.
9  * See README.txt for an overview of the Vim source code.
10  */
11 
12 #include "vim.h"
13 
14 #include <lua.h>
15 #include <lualib.h>
16 #include <lauxlib.h>
17 
18 /* Only do the following when the feature is enabled.  Needed for "make
19  * depend". */
20 #if defined(FEAT_LUA) || defined(PROTO)
21 
22 #define LUAVIM_CHUNKNAME "vim chunk"
23 #define LUAVIM_NAME "vim"
24 #define LUAVIM_EVALNAME "luaeval"
25 #define LUAVIM_EVALHEADER "local _A=select(1,...) return "
26 
27 typedef buf_T *luaV_Buffer;
28 typedef win_T *luaV_Window;
29 typedef dict_T *luaV_Dict;
30 typedef list_T *luaV_List;
31 typedef blob_T *luaV_Blob;
32 typedef struct {
33     char_u	*name;	// funcref
34     dict_T	*self;	// selfdict
35 } luaV_Funcref;
36 typedef void (*msgfunc_T)(char_u *);
37 
38 static const char LUAVIM_DICT[] = "dict";
39 static const char LUAVIM_LIST[] = "list";
40 static const char LUAVIM_BLOB[] = "blob";
41 static const char LUAVIM_FUNCREF[] = "funcref";
42 static const char LUAVIM_BUFFER[] = "buffer";
43 static const char LUAVIM_WINDOW[] = "window";
44 static const char LUAVIM_FREE[] = "luaV_free";
45 static const char LUAVIM_LUAEVAL[] = "luaV_luaeval";
46 static const char LUAVIM_SETREF[] = "luaV_setref";
47 
48 /* most functions are closures with a cache table as first upvalue;
49  * get/setudata manage references to vim userdata in cache table through
50  * object pointers (light userdata) */
51 #define luaV_getudata(L, v) \
52     lua_pushlightuserdata((L), (void *) (v)); \
53     lua_rawget((L), lua_upvalueindex(1))
54 #define luaV_setudata(L, v) \
55     lua_pushlightuserdata((L), (void *) (v)); \
56     lua_pushvalue((L), -2); \
57     lua_rawset((L), lua_upvalueindex(1))
58 #define luaV_getfield(L, s) \
59     lua_pushlightuserdata((L), (void *)(s)); \
60     lua_rawget((L), LUA_REGISTRYINDEX)
61 #define luaV_checksandbox(L) \
62     if (sandbox) luaL_error((L), "not allowed in sandbox")
63 #define luaV_msg(L) luaV_msgfunc((L), (msgfunc_T) msg)
64 #define luaV_emsg(L) luaV_msgfunc((L), (msgfunc_T) emsg)
65 #define luaV_checktypval(L, a, v, msg) \
66     do { \
67         if (luaV_totypval(L, a, v) == FAIL) \
68 	    luaL_error(L, msg ": cannot convert value"); \
69     } while (0)
70 
71 static luaV_List *luaV_pushlist(lua_State *L, list_T *lis);
72 static luaV_Dict *luaV_pushdict(lua_State *L, dict_T *dic);
73 static luaV_Blob *luaV_pushblob(lua_State *L, blob_T *blo);
74 static luaV_Funcref *luaV_pushfuncref(lua_State *L, char_u *name);
75 
76 #if LUA_VERSION_NUM <= 501
77 #define luaV_openlib(L, l, n) luaL_openlib(L, NULL, l, n)
78 #define luaL_typeerror luaL_typerror
79 #else
80 #define luaV_openlib luaL_setfuncs
81 #endif
82 
83 #ifdef DYNAMIC_LUA
84 
85 #ifndef MSWIN
86 # include <dlfcn.h>
87 # define HANDLE void*
88 # define load_dll(n) dlopen((n), RTLD_LAZY|RTLD_GLOBAL)
89 # define symbol_from_dll dlsym
90 # define close_dll dlclose
91 #else
92 # define load_dll vimLoadLib
93 # define symbol_from_dll GetProcAddress
94 # define close_dll FreeLibrary
95 #endif
96 
97 /* lauxlib */
98 #if LUA_VERSION_NUM <= 501
99 #define luaL_register dll_luaL_register
100 #define luaL_prepbuffer dll_luaL_prepbuffer
101 #define luaL_openlib dll_luaL_openlib
102 #define luaL_typerror dll_luaL_typerror
103 #define luaL_loadfile dll_luaL_loadfile
104 #define luaL_loadbuffer dll_luaL_loadbuffer
105 #else
106 #define luaL_prepbuffsize dll_luaL_prepbuffsize
107 #define luaL_setfuncs dll_luaL_setfuncs
108 #define luaL_loadfilex dll_luaL_loadfilex
109 #define luaL_loadbufferx dll_luaL_loadbufferx
110 #define luaL_argerror dll_luaL_argerror
111 #endif
112 #define luaL_checkany dll_luaL_checkany
113 #define luaL_checklstring dll_luaL_checklstring
114 #define luaL_checkinteger dll_luaL_checkinteger
115 #define luaL_optinteger dll_luaL_optinteger
116 #define luaL_checktype dll_luaL_checktype
117 #define luaL_error dll_luaL_error
118 #define luaL_newstate dll_luaL_newstate
119 #define luaL_buffinit dll_luaL_buffinit
120 #define luaL_addlstring dll_luaL_addlstring
121 #define luaL_pushresult dll_luaL_pushresult
122 /* lua */
123 #if LUA_VERSION_NUM <= 501
124 #define lua_tonumber dll_lua_tonumber
125 #define lua_tointeger dll_lua_tointeger
126 #define lua_call dll_lua_call
127 #define lua_pcall dll_lua_pcall
128 #else
129 #define lua_tonumberx dll_lua_tonumberx
130 #define lua_tointegerx dll_lua_tointegerx
131 #define lua_callk dll_lua_callk
132 #define lua_pcallk dll_lua_pcallk
133 #define lua_getglobal dll_lua_getglobal
134 #define lua_setglobal dll_lua_setglobal
135 #endif
136 #if LUA_VERSION_NUM <= 502
137 #define lua_replace dll_lua_replace
138 #define lua_remove dll_lua_remove
139 #endif
140 #if LUA_VERSION_NUM >= 503
141 #define lua_rotate dll_lua_rotate
142 #define lua_copy dll_lua_copy
143 #endif
144 #define lua_typename dll_lua_typename
145 #define lua_close dll_lua_close
146 #define lua_gettop dll_lua_gettop
147 #define lua_settop dll_lua_settop
148 #define lua_pushvalue dll_lua_pushvalue
149 #define lua_isnumber dll_lua_isnumber
150 #define lua_isstring dll_lua_isstring
151 #define lua_type dll_lua_type
152 #define lua_rawequal dll_lua_rawequal
153 #define lua_toboolean dll_lua_toboolean
154 #define lua_tolstring dll_lua_tolstring
155 #define lua_touserdata dll_lua_touserdata
156 #define lua_pushnil dll_lua_pushnil
157 #define lua_pushnumber dll_lua_pushnumber
158 #define lua_pushinteger dll_lua_pushinteger
159 #define lua_pushlstring dll_lua_pushlstring
160 #define lua_pushstring dll_lua_pushstring
161 #define lua_pushfstring dll_lua_pushfstring
162 #define lua_pushcclosure dll_lua_pushcclosure
163 #define lua_pushboolean dll_lua_pushboolean
164 #define lua_pushlightuserdata dll_lua_pushlightuserdata
165 #define lua_getfield dll_lua_getfield
166 #define lua_rawget dll_lua_rawget
167 #define lua_rawgeti dll_lua_rawgeti
168 #define lua_createtable dll_lua_createtable
169 #if LUA_VERSION_NUM >= 504
170  #define lua_newuserdatauv dll_lua_newuserdatauv
171 #else
172  #define lua_newuserdata dll_lua_newuserdata
173 #endif
174 #define lua_getmetatable dll_lua_getmetatable
175 #define lua_setfield dll_lua_setfield
176 #define lua_rawset dll_lua_rawset
177 #define lua_rawseti dll_lua_rawseti
178 #define lua_setmetatable dll_lua_setmetatable
179 #define lua_next dll_lua_next
180 /* libs */
181 #define luaopen_base dll_luaopen_base
182 #define luaopen_table dll_luaopen_table
183 #define luaopen_string dll_luaopen_string
184 #define luaopen_math dll_luaopen_math
185 #define luaopen_io dll_luaopen_io
186 #define luaopen_os dll_luaopen_os
187 #define luaopen_package dll_luaopen_package
188 #define luaopen_debug dll_luaopen_debug
189 #define luaL_openlibs dll_luaL_openlibs
190 
191 /* lauxlib */
192 #if LUA_VERSION_NUM <= 501
193 void (*dll_luaL_register) (lua_State *L, const char *libname, const luaL_Reg *l);
194 char *(*dll_luaL_prepbuffer) (luaL_Buffer *B);
195 void (*dll_luaL_openlib) (lua_State *L, const char *libname, const luaL_Reg *l, int nup);
196 int (*dll_luaL_typerror) (lua_State *L, int narg, const char *tname);
197 int (*dll_luaL_loadfile) (lua_State *L, const char *filename);
198 int (*dll_luaL_loadbuffer) (lua_State *L, const char *buff, size_t sz, const char *name);
199 #else
200 char *(*dll_luaL_prepbuffsize) (luaL_Buffer *B, size_t sz);
201 void (*dll_luaL_setfuncs) (lua_State *L, const luaL_Reg *l, int nup);
202 int (*dll_luaL_loadfilex) (lua_State *L, const char *filename, const char *mode);
203 int (*dll_luaL_loadbufferx) (lua_State *L, const char *buff, size_t sz, const char *name, const char *mode);
204 int (*dll_luaL_argerror) (lua_State *L, int numarg, const char *extramsg);
205 #endif
206 void (*dll_luaL_checkany) (lua_State *L, int narg);
207 const char *(*dll_luaL_checklstring) (lua_State *L, int numArg, size_t *l);
208 lua_Integer (*dll_luaL_checkinteger) (lua_State *L, int numArg);
209 lua_Integer (*dll_luaL_optinteger) (lua_State *L, int nArg, lua_Integer def);
210 void (*dll_luaL_checktype) (lua_State *L, int narg, int t);
211 int (*dll_luaL_error) (lua_State *L, const char *fmt, ...);
212 lua_State *(*dll_luaL_newstate) (void);
213 void (*dll_luaL_buffinit) (lua_State *L, luaL_Buffer *B);
214 void (*dll_luaL_addlstring) (luaL_Buffer *B, const char *s, size_t l);
215 void (*dll_luaL_pushresult) (luaL_Buffer *B);
216 /* lua */
217 #if LUA_VERSION_NUM <= 501
218 lua_Number (*dll_lua_tonumber) (lua_State *L, int idx);
219 lua_Integer (*dll_lua_tointeger) (lua_State *L, int idx);
220 void (*dll_lua_call) (lua_State *L, int nargs, int nresults);
221 int (*dll_lua_pcall) (lua_State *L, int nargs, int nresults, int errfunc);
222 #else
223 lua_Number (*dll_lua_tonumberx) (lua_State *L, int idx, int *isnum);
224 lua_Integer (*dll_lua_tointegerx) (lua_State *L, int idx, int *isnum);
225 void (*dll_lua_callk) (lua_State *L, int nargs, int nresults, int ctx,
226 	lua_CFunction k);
227 int (*dll_lua_pcallk) (lua_State *L, int nargs, int nresults, int errfunc,
228 	int ctx, lua_CFunction k);
229 void (*dll_lua_getglobal) (lua_State *L, const char *var);
230 void (*dll_lua_setglobal) (lua_State *L, const char *var);
231 #endif
232 #if LUA_VERSION_NUM <= 502
233 void (*dll_lua_replace) (lua_State *L, int idx);
234 void (*dll_lua_remove) (lua_State *L, int idx);
235 #endif
236 #if LUA_VERSION_NUM >= 503
237 void  (*dll_lua_rotate) (lua_State *L, int idx, int n);
238 void (*dll_lua_copy) (lua_State *L, int fromidx, int toidx);
239 #endif
240 const char *(*dll_lua_typename) (lua_State *L, int tp);
241 void       (*dll_lua_close) (lua_State *L);
242 int (*dll_lua_gettop) (lua_State *L);
243 void (*dll_lua_settop) (lua_State *L, int idx);
244 void (*dll_lua_pushvalue) (lua_State *L, int idx);
245 int (*dll_lua_isnumber) (lua_State *L, int idx);
246 int (*dll_lua_isstring) (lua_State *L, int idx);
247 int (*dll_lua_type) (lua_State *L, int idx);
248 int (*dll_lua_rawequal) (lua_State *L, int idx1, int idx2);
249 int (*dll_lua_toboolean) (lua_State *L, int idx);
250 const char *(*dll_lua_tolstring) (lua_State *L, int idx, size_t *len);
251 void *(*dll_lua_touserdata) (lua_State *L, int idx);
252 void (*dll_lua_pushnil) (lua_State *L);
253 void (*dll_lua_pushnumber) (lua_State *L, lua_Number n);
254 void (*dll_lua_pushinteger) (lua_State *L, lua_Integer n);
255 void (*dll_lua_pushlstring) (lua_State *L, const char *s, size_t l);
256 void (*dll_lua_pushstring) (lua_State *L, const char *s);
257 const char *(*dll_lua_pushfstring) (lua_State *L, const char *fmt, ...);
258 void (*dll_lua_pushcclosure) (lua_State *L, lua_CFunction fn, int n);
259 void (*dll_lua_pushboolean) (lua_State *L, int b);
260 void (*dll_lua_pushlightuserdata) (lua_State *L, void *p);
261 void (*dll_lua_getfield) (lua_State *L, int idx, const char *k);
262 #if LUA_VERSION_NUM <= 502
263 void (*dll_lua_rawget) (lua_State *L, int idx);
264 void (*dll_lua_rawgeti) (lua_State *L, int idx, int n);
265 #else
266 int (*dll_lua_rawget) (lua_State *L, int idx);
267 int (*dll_lua_rawgeti) (lua_State *L, int idx, lua_Integer n);
268 #endif
269 void (*dll_lua_createtable) (lua_State *L, int narr, int nrec);
270 #if LUA_VERSION_NUM >= 504
271 void *(*dll_lua_newuserdatauv) (lua_State *L, size_t sz, int nuvalue);
272 #else
273 void *(*dll_lua_newuserdata) (lua_State *L, size_t sz);
274 #endif
275 int (*dll_lua_getmetatable) (lua_State *L, int objindex);
276 void (*dll_lua_setfield) (lua_State *L, int idx, const char *k);
277 void (*dll_lua_rawset) (lua_State *L, int idx);
278 #if LUA_VERSION_NUM <= 502
279 void (*dll_lua_rawseti) (lua_State *L, int idx, int n);
280 #else
281 void (*dll_lua_rawseti) (lua_State *L, int idx, lua_Integer n);
282 #endif
283 int (*dll_lua_setmetatable) (lua_State *L, int objindex);
284 int (*dll_lua_next) (lua_State *L, int idx);
285 /* libs */
286 int (*dll_luaopen_base) (lua_State *L);
287 int (*dll_luaopen_table) (lua_State *L);
288 int (*dll_luaopen_string) (lua_State *L);
289 int (*dll_luaopen_math) (lua_State *L);
290 int (*dll_luaopen_io) (lua_State *L);
291 int (*dll_luaopen_os) (lua_State *L);
292 int (*dll_luaopen_package) (lua_State *L);
293 int (*dll_luaopen_debug) (lua_State *L);
294 void (*dll_luaL_openlibs) (lua_State *L);
295 
296 typedef void **luaV_function;
297 typedef struct {
298     const char *name;
299     luaV_function func;
300 } luaV_Reg;
301 
302 static const luaV_Reg luaV_dll[] = {
303     /* lauxlib */
304 #if LUA_VERSION_NUM <= 501
305     {"luaL_register", (luaV_function) &dll_luaL_register},
306     {"luaL_prepbuffer", (luaV_function) &dll_luaL_prepbuffer},
307     {"luaL_openlib", (luaV_function) &dll_luaL_openlib},
308     {"luaL_typerror", (luaV_function) &dll_luaL_typerror},
309     {"luaL_loadfile", (luaV_function) &dll_luaL_loadfile},
310     {"luaL_loadbuffer", (luaV_function) &dll_luaL_loadbuffer},
311 #else
312     {"luaL_prepbuffsize", (luaV_function) &dll_luaL_prepbuffsize},
313     {"luaL_setfuncs", (luaV_function) &dll_luaL_setfuncs},
314     {"luaL_loadfilex", (luaV_function) &dll_luaL_loadfilex},
315     {"luaL_loadbufferx", (luaV_function) &dll_luaL_loadbufferx},
316     {"luaL_argerror", (luaV_function) &dll_luaL_argerror},
317 #endif
318     {"luaL_checkany", (luaV_function) &dll_luaL_checkany},
319     {"luaL_checklstring", (luaV_function) &dll_luaL_checklstring},
320     {"luaL_checkinteger", (luaV_function) &dll_luaL_checkinteger},
321     {"luaL_optinteger", (luaV_function) &dll_luaL_optinteger},
322     {"luaL_checktype", (luaV_function) &dll_luaL_checktype},
323     {"luaL_error", (luaV_function) &dll_luaL_error},
324     {"luaL_newstate", (luaV_function) &dll_luaL_newstate},
325     {"luaL_buffinit", (luaV_function) &dll_luaL_buffinit},
326     {"luaL_addlstring", (luaV_function) &dll_luaL_addlstring},
327     {"luaL_pushresult", (luaV_function) &dll_luaL_pushresult},
328     /* lua */
329 #if LUA_VERSION_NUM <= 501
330     {"lua_tonumber", (luaV_function) &dll_lua_tonumber},
331     {"lua_tointeger", (luaV_function) &dll_lua_tointeger},
332     {"lua_call", (luaV_function) &dll_lua_call},
333     {"lua_pcall", (luaV_function) &dll_lua_pcall},
334 #else
335     {"lua_tonumberx", (luaV_function) &dll_lua_tonumberx},
336     {"lua_tointegerx", (luaV_function) &dll_lua_tointegerx},
337     {"lua_callk", (luaV_function) &dll_lua_callk},
338     {"lua_pcallk", (luaV_function) &dll_lua_pcallk},
339     {"lua_getglobal", (luaV_function) &dll_lua_getglobal},
340     {"lua_setglobal", (luaV_function) &dll_lua_setglobal},
341 #endif
342 #if LUA_VERSION_NUM <= 502
343     {"lua_replace", (luaV_function) &dll_lua_replace},
344     {"lua_remove", (luaV_function) &dll_lua_remove},
345 #endif
346 #if LUA_VERSION_NUM >= 503
347     {"lua_rotate", (luaV_function) &dll_lua_rotate},
348     {"lua_copy", (luaV_function) &dll_lua_copy},
349 #endif
350     {"lua_typename", (luaV_function) &dll_lua_typename},
351     {"lua_close", (luaV_function) &dll_lua_close},
352     {"lua_gettop", (luaV_function) &dll_lua_gettop},
353     {"lua_settop", (luaV_function) &dll_lua_settop},
354     {"lua_pushvalue", (luaV_function) &dll_lua_pushvalue},
355     {"lua_isnumber", (luaV_function) &dll_lua_isnumber},
356     {"lua_isstring", (luaV_function) &dll_lua_isstring},
357     {"lua_type", (luaV_function) &dll_lua_type},
358     {"lua_rawequal", (luaV_function) &dll_lua_rawequal},
359     {"lua_toboolean", (luaV_function) &dll_lua_toboolean},
360     {"lua_tolstring", (luaV_function) &dll_lua_tolstring},
361     {"lua_touserdata", (luaV_function) &dll_lua_touserdata},
362     {"lua_pushnil", (luaV_function) &dll_lua_pushnil},
363     {"lua_pushnumber", (luaV_function) &dll_lua_pushnumber},
364     {"lua_pushinteger", (luaV_function) &dll_lua_pushinteger},
365     {"lua_pushlstring", (luaV_function) &dll_lua_pushlstring},
366     {"lua_pushstring", (luaV_function) &dll_lua_pushstring},
367     {"lua_pushfstring", (luaV_function) &dll_lua_pushfstring},
368     {"lua_pushcclosure", (luaV_function) &dll_lua_pushcclosure},
369     {"lua_pushboolean", (luaV_function) &dll_lua_pushboolean},
370     {"lua_pushlightuserdata", (luaV_function) &dll_lua_pushlightuserdata},
371     {"lua_getfield", (luaV_function) &dll_lua_getfield},
372     {"lua_rawget", (luaV_function) &dll_lua_rawget},
373     {"lua_rawgeti", (luaV_function) &dll_lua_rawgeti},
374     {"lua_createtable", (luaV_function) &dll_lua_createtable},
375 #if LUA_VERSION_NUM >= 504
376     {"lua_newuserdatauv", (luaV_function) &dll_lua_newuserdatauv},
377 #else
378     {"lua_newuserdata", (luaV_function) &dll_lua_newuserdata},
379 #endif
380     {"lua_getmetatable", (luaV_function) &dll_lua_getmetatable},
381     {"lua_setfield", (luaV_function) &dll_lua_setfield},
382     {"lua_rawset", (luaV_function) &dll_lua_rawset},
383     {"lua_rawseti", (luaV_function) &dll_lua_rawseti},
384     {"lua_setmetatable", (luaV_function) &dll_lua_setmetatable},
385     {"lua_next", (luaV_function) &dll_lua_next},
386     /* libs */
387     {"luaopen_base", (luaV_function) &dll_luaopen_base},
388     {"luaopen_table", (luaV_function) &dll_luaopen_table},
389     {"luaopen_string", (luaV_function) &dll_luaopen_string},
390     {"luaopen_math", (luaV_function) &dll_luaopen_math},
391     {"luaopen_io", (luaV_function) &dll_luaopen_io},
392     {"luaopen_os", (luaV_function) &dll_luaopen_os},
393     {"luaopen_package", (luaV_function) &dll_luaopen_package},
394     {"luaopen_debug", (luaV_function) &dll_luaopen_debug},
395     {"luaL_openlibs", (luaV_function) &dll_luaL_openlibs},
396     {NULL, NULL}
397 };
398 
399 static HANDLE hinstLua = NULL;
400 
401     static void
402 end_dynamic_lua(void)
403 {
404     if (hinstLua)
405     {
406 	close_dll(hinstLua);
407 	hinstLua = 0;
408     }
409 }
410 
411     static int
412 lua_link_init(char *libname, int verbose)
413 {
414     const luaV_Reg *reg;
415     if (hinstLua) return OK;
416     hinstLua = load_dll(libname);
417     if (!hinstLua)
418     {
419 	if (verbose)
420 	    semsg(_(e_loadlib), libname);
421 	return FAIL;
422     }
423     for (reg = luaV_dll; reg->func; reg++)
424     {
425 	if ((*reg->func = symbol_from_dll(hinstLua, reg->name)) == NULL)
426 	{
427 	    close_dll(hinstLua);
428 	    hinstLua = 0;
429 	    if (verbose)
430 		semsg(_(e_loadfunc), reg->name);
431 	    return FAIL;
432 	}
433     }
434     return OK;
435 }
436 #endif /* DYNAMIC_LUA */
437 
438 #if defined(DYNAMIC_LUA) || defined(PROTO)
439     int
440 lua_enabled(int verbose)
441 {
442     return lua_link_init((char *)p_luadll, verbose) == OK;
443 }
444 #endif
445 
446 #if LUA_VERSION_NUM > 501
447     static int
448 luaL_typeerror(lua_State *L, int narg, const char *tname)
449 {
450     const char *msg = lua_pushfstring(L, "%s expected, got %s",
451 	    tname, luaL_typename(L, narg));
452     return luaL_argerror(L, narg, msg);
453 }
454 #endif
455 
456 
457 /* =======   Internal   ======= */
458 
459     static void
460 luaV_newmetatable(lua_State *L, const char *tname)
461 {
462     lua_newtable(L);
463     lua_pushlightuserdata(L, (void *) tname);
464     lua_pushvalue(L, -2);
465     lua_rawset(L, LUA_REGISTRYINDEX);
466 }
467 
468     static void *
469 luaV_toudata(lua_State *L, int ud, const char *tname)
470 {
471     void *p = lua_touserdata(L, ud);
472 
473     if (p != NULL) /* value is userdata? */
474     {
475 	if (lua_getmetatable(L, ud)) /* does it have a metatable? */
476 	{
477 	    luaV_getfield(L, tname); /* get metatable */
478 	    if (lua_rawequal(L, -1, -2)) /* MTs match? */
479 	    {
480 		lua_pop(L, 2); /* MTs */
481 		return p;
482 	    }
483 	}
484     }
485     return NULL;
486 }
487 
488     static void *
489 luaV_checkcache(lua_State *L, void *p)
490 {
491     luaV_getudata(L, p);
492     if (lua_isnil(L, -1)) luaL_error(L, "invalid object");
493     lua_pop(L, 1);
494     return p;
495 }
496 
497 #define luaV_unbox(L,luatyp,ud) (*((luatyp *) lua_touserdata((L),(ud))))
498 
499 #define luaV_checkvalid(L,luatyp,ud) \
500     luaV_checkcache((L), (void *) luaV_unbox((L),luatyp,(ud)))
501 
502     static void *
503 luaV_checkudata(lua_State *L, int ud, const char *tname)
504 {
505     void *p = luaV_toudata(L, ud, tname);
506     if (p == NULL) luaL_typeerror(L, ud, tname);
507     return p;
508 }
509 
510     static void
511 luaV_pushtypval(lua_State *L, typval_T *tv)
512 {
513     if (tv == NULL)
514     {
515 	lua_pushnil(L);
516 	return;
517     }
518     switch (tv->v_type)
519     {
520 	case VAR_STRING:
521 	    lua_pushstring(L, tv->vval.v_string == NULL
522 					    ? "" : (char *)tv->vval.v_string);
523 	    break;
524 	case VAR_NUMBER:
525 	    lua_pushinteger(L, (int) tv->vval.v_number);
526 	    break;
527 #ifdef FEAT_FLOAT
528 	case VAR_FLOAT:
529 	    lua_pushnumber(L, (lua_Number) tv->vval.v_float);
530 	    break;
531 #endif
532 	case VAR_LIST:
533 	    luaV_pushlist(L, tv->vval.v_list);
534 	    break;
535 	case VAR_DICT:
536 	    luaV_pushdict(L, tv->vval.v_dict);
537 	    break;
538 	case VAR_SPECIAL:
539 	    if (tv->vval.v_number <= VVAL_TRUE)
540 		lua_pushinteger(L, (int) tv->vval.v_number);
541 	    else
542 		lua_pushnil(L);
543 	    break;
544 	case VAR_FUNC:
545 	    luaV_pushfuncref(L, tv->vval.v_string);
546 	    break;
547 	case VAR_BLOB:
548 	    luaV_pushblob(L, tv->vval.v_blob);
549 	    break;
550 	default:
551 	    lua_pushnil(L);
552     }
553 }
554 
555 /*
556  * Converts lua value at 'pos' to typval 'tv'.
557  * Returns OK or FAIL.
558  */
559     static int
560 luaV_totypval(lua_State *L, int pos, typval_T *tv)
561 {
562     int status = OK;
563 
564     switch (lua_type(L, pos))
565     {
566 	case LUA_TBOOLEAN:
567 	    tv->v_type = VAR_SPECIAL;
568 	    tv->vval.v_number = (varnumber_T) lua_toboolean(L, pos);
569 	    break;
570 	case LUA_TNIL:
571 	    tv->v_type = VAR_SPECIAL;
572 	    tv->vval.v_number = VVAL_NULL;
573 	    break;
574 	case LUA_TSTRING:
575 	    tv->v_type = VAR_STRING;
576 	    tv->vval.v_string = vim_strsave((char_u *) lua_tostring(L, pos));
577 	    break;
578 	case LUA_TNUMBER:
579 #ifdef FEAT_FLOAT
580 	    tv->v_type = VAR_FLOAT;
581 	    tv->vval.v_float = (float_T) lua_tonumber(L, pos);
582 #else
583 	    tv->v_type = VAR_NUMBER;
584 	    tv->vval.v_number = (varnumber_T) lua_tointeger(L, pos);
585 #endif
586 	    break;
587 	case LUA_TUSERDATA:
588 	{
589 	    void *p = lua_touserdata(L, pos);
590 
591 	    if (lua_getmetatable(L, pos)) // has metatable?
592 	    {
593 		// check list
594 		luaV_getfield(L, LUAVIM_LIST);
595 		if (lua_rawequal(L, -1, -2))
596 		{
597 		    tv->v_type = VAR_LIST;
598 		    tv->vval.v_list = *((luaV_List *) p);
599 		    ++tv->vval.v_list->lv_refcount;
600 		    lua_pop(L, 2); // MTs
601 		    break;
602 		}
603 		// check dict
604 		luaV_getfield(L, LUAVIM_DICT);
605 		if (lua_rawequal(L, -1, -3))
606 		{
607 		    tv->v_type = VAR_DICT;
608 		    tv->vval.v_dict = *((luaV_Dict *) p);
609 		    ++tv->vval.v_dict->dv_refcount;
610 		    lua_pop(L, 3); // MTs
611 		    break;
612 		}
613 		// check blob
614 		luaV_getfield(L, LUAVIM_BLOB);
615 		if (lua_rawequal(L, -1, -4))
616 		{
617 		    tv->v_type = VAR_BLOB;
618 		    tv->vval.v_blob = *((luaV_Blob *) p);
619 		    ++tv->vval.v_blob->bv_refcount;
620 		    lua_pop(L, 4); // MTs
621 		    break;
622 		}
623 		// check funcref
624 		luaV_getfield(L, LUAVIM_FUNCREF);
625 		if (lua_rawequal(L, -1, -5))
626 		{
627 		    luaV_Funcref *f = (luaV_Funcref *) p;
628 		    func_ref(f->name);
629 		    tv->v_type = VAR_FUNC;
630 		    tv->vval.v_string = vim_strsave(f->name);
631 		    lua_pop(L, 5); // MTs
632 		    break;
633 		}
634 		lua_pop(L, 4); // MTs
635 	    }
636 	}
637 	// FALLTHROUGH
638 	default:
639 	    tv->v_type = VAR_NUMBER;
640 	    tv->vval.v_number = 0;
641 	    status = FAIL;
642     }
643     return status;
644 }
645 
646 /* similar to luaL_addlstring, but replaces \0 with \n if toline and
647  * \n with \0 otherwise */
648     static void
649 luaV_addlstring(luaL_Buffer *b, const char *s, size_t l, int toline)
650 {
651     while (l--)
652     {
653 	if (*s == '\0' && toline)
654 	    luaL_addchar(b, '\n');
655 	else if (*s == '\n' && !toline)
656 	    luaL_addchar(b, '\0');
657 	else
658 	    luaL_addchar(b, *s);
659 	s++;
660     }
661 }
662 
663     static void
664 luaV_pushline(lua_State *L, buf_T *buf, linenr_T n)
665 {
666     const char *s = (const char *) ml_get_buf(buf, n, FALSE);
667     luaL_Buffer b;
668     luaL_buffinit(L, &b);
669     luaV_addlstring(&b, s, strlen(s), 0);
670     luaL_pushresult(&b);
671 }
672 
673     static char_u *
674 luaV_toline(lua_State *L, int pos)
675 {
676     size_t l;
677     const char *s = lua_tolstring(L, pos, &l);
678 
679     luaL_Buffer b;
680     luaL_buffinit(L, &b);
681     luaV_addlstring(&b, s, l, 1);
682     luaL_pushresult(&b);
683     return (char_u *) lua_tostring(L, -1);
684 }
685 
686 /* pops a string s from the top of the stack and calls mf(t) for pieces t of
687  * s separated by newlines */
688     static void
689 luaV_msgfunc(lua_State *L, msgfunc_T mf)
690 {
691     luaL_Buffer b;
692     size_t l;
693     const char *p, *s = lua_tolstring(L, -1, &l);
694     luaL_buffinit(L, &b);
695     luaV_addlstring(&b, s, l, 0);
696     luaL_pushresult(&b);
697     /* break string */
698     p = s = lua_tolstring(L, -1, &l);
699     while (l--)
700     {
701 	if (*p++ == '\0') /* break? */
702 	{
703 	    mf((char_u *) s);
704 	    s = p;
705 	}
706     }
707     mf((char_u *) s);
708     lua_pop(L, 2); /* original and modified strings */
709 }
710 
711 #define luaV_newtype(typ,tname,luatyp,luatname) \
712 	static luatyp * \
713     luaV_new##tname(lua_State *L, typ *obj) \
714     { \
715 	luatyp *o = (luatyp *) lua_newuserdata(L, sizeof(luatyp)); \
716 	*o = obj; \
717 	luaV_setudata(L, obj); /* cache[obj] = udata */ \
718 	luaV_getfield(L, luatname); \
719 	lua_setmetatable(L, -2); \
720 	return o; \
721     }
722 
723 #define luaV_pushtype(typ,tname,luatyp) \
724 	static luatyp * \
725     luaV_push##tname(lua_State *L, typ *obj) \
726     { \
727 	luatyp *o = NULL; \
728 	if (obj == NULL) \
729 	    lua_pushnil(L); \
730 	else { \
731 	    luaV_getudata(L, obj); \
732 	    if (lua_isnil(L, -1)) /* not interned? */ \
733 	    { \
734 		lua_pop(L, 1); \
735 		o = luaV_new##tname(L, obj); \
736 	    } \
737 	    else \
738 		o = (luatyp *) lua_touserdata(L, -1); \
739 	} \
740 	return o; \
741     }
742 
743 #define luaV_type_tostring(tname,luatname) \
744 	static int \
745     luaV_##tname##_tostring(lua_State *L) \
746     { \
747 	lua_pushfstring(L, "%s: %p", luatname, lua_touserdata(L, 1)); \
748 	return 1; \
749     }
750 
751 /* =======   List type   ======= */
752 
753     static luaV_List *
754 luaV_newlist(lua_State *L, list_T *lis)
755 {
756     luaV_List *l = (luaV_List *) lua_newuserdata(L, sizeof(luaV_List));
757     *l = lis;
758     lis->lv_refcount++; /* reference in Lua */
759     luaV_setudata(L, lis); /* cache[lis] = udata */
760     luaV_getfield(L, LUAVIM_LIST);
761     lua_setmetatable(L, -2);
762     return l;
763 }
764 
765 luaV_pushtype(list_T, list, luaV_List)
766 luaV_type_tostring(list, LUAVIM_LIST)
767 
768     static int
769 luaV_list_len(lua_State *L)
770 {
771     list_T *l = luaV_unbox(L, luaV_List, 1);
772     lua_pushinteger(L, (int) list_len(l));
773     return 1;
774 }
775 
776     static int
777 luaV_list_iter(lua_State *L)
778 {
779     listitem_T *li = (listitem_T *) lua_touserdata(L, lua_upvalueindex(2));
780     if (li == NULL) return 0;
781     luaV_pushtypval(L, &li->li_tv);
782     lua_pushlightuserdata(L, (void *) li->li_next);
783     lua_replace(L, lua_upvalueindex(2));
784     return 1;
785 }
786 
787     static int
788 luaV_list_call(lua_State *L)
789 {
790     list_T *l = luaV_unbox(L, luaV_List, 1);
791     lua_pushvalue(L, lua_upvalueindex(1)); /* pass cache table along */
792     lua_pushlightuserdata(L, (void *) l->lv_first);
793     lua_pushcclosure(L, luaV_list_iter, 2);
794     return 1;
795 }
796 
797     static int
798 luaV_list_index(lua_State *L)
799 {
800     list_T *l = luaV_unbox(L, luaV_List, 1);
801     if (lua_isnumber(L, 2)) /* list item? */
802     {
803 	listitem_T *li = list_find(l, (long) luaL_checkinteger(L, 2));
804 	if (li == NULL)
805 	    lua_pushnil(L);
806 	else
807 	    luaV_pushtypval(L, &li->li_tv);
808     }
809     else if (lua_isstring(L, 2)) /* method? */
810     {
811 	const char *s = lua_tostring(L, 2);
812 	if (strncmp(s, "add", 3) == 0
813 		|| strncmp(s, "insert", 6) == 0)
814 	{
815 	    lua_getmetatable(L, 1);
816 	    lua_getfield(L, -1, s);
817 	}
818 	else
819 	    lua_pushnil(L);
820     }
821     else
822 	lua_pushnil(L);
823     return 1;
824 }
825 
826     static int
827 luaV_list_newindex(lua_State *L)
828 {
829     list_T *l = luaV_unbox(L, luaV_List, 1);
830     long n = (long) luaL_checkinteger(L, 2);
831     listitem_T *li;
832     if (l->lv_lock)
833 	luaL_error(L, "list is locked");
834     li = list_find(l, n);
835     if (li == NULL) return 0;
836     if (lua_isnil(L, 3)) /* remove? */
837     {
838 	vimlist_remove(l, li, li);
839 	clear_tv(&li->li_tv);
840 	vim_free(li);
841     }
842     else
843     {
844 	typval_T v;
845 	luaV_checktypval(L, 3, &v, "setting list item");
846 	clear_tv(&li->li_tv);
847 	copy_tv(&v, &li->li_tv);
848 	clear_tv(&v);
849     }
850     return 0;
851 }
852 
853     static int
854 luaV_list_add(lua_State *L)
855 {
856     luaV_List *lis = luaV_checkudata(L, 1, LUAVIM_LIST);
857     list_T *l = (list_T *) luaV_checkcache(L, (void *) *lis);
858     typval_T v;
859     if (l->lv_lock)
860 	luaL_error(L, "list is locked");
861     lua_settop(L, 2);
862     luaV_checktypval(L, 2, &v, "adding list item");
863     if (list_append_tv(l, &v) == FAIL)
864 	luaL_error(L, "failed to add item to list");
865     clear_tv(&v);
866     lua_settop(L, 1);
867     return 1;
868 }
869 
870     static int
871 luaV_list_insert(lua_State *L)
872 {
873     luaV_List *lis = luaV_checkudata(L, 1, LUAVIM_LIST);
874     list_T *l = (list_T *) luaV_checkcache(L, (void *) *lis);
875     long pos = (long) luaL_optinteger(L, 3, 0);
876     listitem_T *li = NULL;
877     typval_T v;
878     if (l->lv_lock)
879 	luaL_error(L, "list is locked");
880     if (pos < l->lv_len)
881     {
882 	li = list_find(l, pos);
883 	if (li == NULL)
884 	    luaL_error(L, "invalid position");
885     }
886     lua_settop(L, 2);
887     luaV_checktypval(L, 2, &v, "inserting list item");
888     if (list_insert_tv(l, &v, li) == FAIL)
889 	luaL_error(L, "failed to add item to list");
890     clear_tv(&v);
891     lua_settop(L, 1);
892     return 1;
893 }
894 
895 static const luaL_Reg luaV_List_mt[] = {
896     {"__tostring", luaV_list_tostring},
897     {"__len", luaV_list_len},
898     {"__call", luaV_list_call},
899     {"__index", luaV_list_index},
900     {"__newindex", luaV_list_newindex},
901     {"add", luaV_list_add},
902     {"insert", luaV_list_insert},
903     {NULL, NULL}
904 };
905 
906 
907 /* =======   Dict type   ======= */
908 
909     static luaV_Dict *
910 luaV_newdict(lua_State *L, dict_T *dic)
911 {
912     luaV_Dict *d = (luaV_Dict *) lua_newuserdata(L, sizeof(luaV_Dict));
913     *d = dic;
914     dic->dv_refcount++; /* reference in Lua */
915     luaV_setudata(L, dic); /* cache[dic] = udata */
916     luaV_getfield(L, LUAVIM_DICT);
917     lua_setmetatable(L, -2);
918     return d;
919 }
920 
921 luaV_pushtype(dict_T, dict, luaV_Dict)
922 luaV_type_tostring(dict, LUAVIM_DICT)
923 
924     static int
925 luaV_dict_len(lua_State *L)
926 {
927     dict_T *d = luaV_unbox(L, luaV_Dict, 1);
928     lua_pushinteger(L, (int) dict_len(d));
929     return 1;
930 }
931 
932     static int
933 luaV_dict_iter(lua_State *L UNUSED)
934 {
935 #ifdef FEAT_EVAL
936     hashitem_T *hi = (hashitem_T *) lua_touserdata(L, lua_upvalueindex(2));
937     int n = lua_tointeger(L, lua_upvalueindex(3));
938     dictitem_T *di;
939     if (n <= 0) return 0;
940     while (HASHITEM_EMPTY(hi)) hi++;
941     di = dict_lookup(hi);
942     lua_pushstring(L, (char *) hi->hi_key);
943     luaV_pushtypval(L, &di->di_tv);
944     lua_pushlightuserdata(L, (void *) (hi + 1));
945     lua_replace(L, lua_upvalueindex(2));
946     lua_pushinteger(L, n - 1);
947     lua_replace(L, lua_upvalueindex(3));
948     return 2;
949 #else
950     return 0;
951 #endif
952 }
953 
954     static int
955 luaV_dict_call(lua_State *L)
956 {
957     dict_T *d = luaV_unbox(L, luaV_Dict, 1);
958     hashtab_T *ht = &d->dv_hashtab;
959     lua_pushvalue(L, lua_upvalueindex(1)); /* pass cache table along */
960     lua_pushlightuserdata(L, (void *) ht->ht_array);
961     lua_pushinteger(L, ht->ht_used); /* # remaining items */
962     lua_pushcclosure(L, luaV_dict_iter, 3);
963     return 1;
964 }
965 
966     static int
967 luaV_dict_index(lua_State *L)
968 {
969     dict_T *d = luaV_unbox(L, luaV_Dict, 1);
970     char_u *key = (char_u *) luaL_checkstring(L, 2);
971     dictitem_T *di = dict_find(d, key, -1);
972 
973     if (di == NULL)
974 	lua_pushnil(L);
975     else
976     {
977 	luaV_pushtypval(L, &di->di_tv);
978 	if (di->di_tv.v_type == VAR_FUNC) /* funcref? */
979 	{
980 	    luaV_Funcref *f = (luaV_Funcref *) lua_touserdata(L, -1);
981 	    f->self = d; /* keep "self" reference */
982 	    d->dv_refcount++;
983 	}
984     }
985     return 1;
986 }
987 
988     static int
989 luaV_dict_newindex(lua_State *L)
990 {
991     dict_T *d = luaV_unbox(L, luaV_Dict, 1);
992     char_u *key = (char_u *) luaL_checkstring(L, 2);
993     dictitem_T *di;
994     typval_T v;
995 
996     if (d->dv_lock)
997 	luaL_error(L, "dict is locked");
998     if (key == NULL)
999 	return 0;
1000     if (*key == NUL)
1001 	luaL_error(L, "empty key");
1002     if (!lua_isnil(L, 3)) /* read value? */
1003     {
1004 	luaV_checktypval(L, 3, &v, "setting dict item");
1005 	if (d->dv_scope == VAR_DEF_SCOPE && v.v_type == VAR_FUNC)
1006 	    luaL_error(L, "cannot assign funcref to builtin scope");
1007     }
1008     di = dict_find(d, key, -1);
1009     if (di == NULL) /* non-existing key? */
1010     {
1011 	if (lua_isnil(L, 3))
1012 	    return 0;
1013 	di = dictitem_alloc(key);
1014 	if (di == NULL)
1015 	    return 0;
1016 	if (dict_add(d, di) == FAIL)
1017 	{
1018 	    vim_free(di);
1019 	    return 0;
1020 	}
1021     }
1022     else
1023 	clear_tv(&di->di_tv);
1024     if (lua_isnil(L, 3)) /* remove? */
1025     {
1026 	hashitem_T *hi = hash_find(&d->dv_hashtab, di->di_key);
1027 	hash_remove(&d->dv_hashtab, hi);
1028 	dictitem_free(di);
1029     }
1030     else
1031     {
1032 	copy_tv(&v, &di->di_tv);
1033 	clear_tv(&v);
1034     }
1035     return 0;
1036 }
1037 
1038 static const luaL_Reg luaV_Dict_mt[] = {
1039     {"__tostring", luaV_dict_tostring},
1040     {"__len", luaV_dict_len},
1041     {"__call", luaV_dict_call},
1042     {"__index", luaV_dict_index},
1043     {"__newindex", luaV_dict_newindex},
1044     {NULL, NULL}
1045 };
1046 
1047 
1048 /* =======   Blob type   ======= */
1049 
1050     static luaV_Blob *
1051 luaV_newblob(lua_State *L, blob_T *blo)
1052 {
1053     luaV_Blob *b = (luaV_Blob *) lua_newuserdata(L, sizeof(luaV_Blob));
1054     *b = blo;
1055     blo->bv_refcount++; /* reference in Lua */
1056     luaV_setudata(L, blo); /* cache[blo] = udata */
1057     luaV_getfield(L, LUAVIM_BLOB);
1058     lua_setmetatable(L, -2);
1059     return b;
1060 }
1061 
1062 luaV_pushtype(blob_T, blob, luaV_Blob)
1063 luaV_type_tostring(blob, LUAVIM_BLOB)
1064 
1065     static int
1066 luaV_blob_gc(lua_State *L)
1067 {
1068     blob_T *b = luaV_unbox(L, luaV_Blob, 1);
1069     blob_unref(b);
1070     return 0;
1071 }
1072 
1073     static int
1074 luaV_blob_len(lua_State *L)
1075 {
1076     blob_T *b = luaV_unbox(L, luaV_Blob, 1);
1077     lua_pushinteger(L, (int) blob_len(b));
1078     return 1;
1079 }
1080 
1081     static int
1082 luaV_blob_index(lua_State *L)
1083 {
1084     blob_T *b = luaV_unbox(L, luaV_Blob, 1);
1085     if (lua_isnumber(L, 2))
1086     {
1087 	int idx = luaL_checkinteger(L, 2);
1088 	if (idx < blob_len(b))
1089 	    lua_pushnumber(L, (lua_Number) blob_get(b, idx));
1090 	else
1091 	    lua_pushnil(L);
1092     }
1093     else if (lua_isstring(L, 2))
1094     {
1095 	const char *s = lua_tostring(L, 2);
1096 	if (strncmp(s, "add", 3) == 0)
1097 	{
1098 	    lua_getmetatable(L, 1);
1099 	    lua_getfield(L, -1, s);
1100 	}
1101 	else
1102 	    lua_pushnil(L);
1103     }
1104     else
1105 	lua_pushnil(L);
1106     return 1;
1107 }
1108 
1109     static int
1110 luaV_blob_newindex(lua_State *L)
1111 {
1112     blob_T *b = luaV_unbox(L, luaV_Blob, 1);
1113     if (b->bv_lock)
1114 	luaL_error(L, "blob is locked");
1115     if (lua_isnumber(L, 2))
1116     {
1117 	long len = blob_len(b);
1118 	int idx = luaL_checkinteger(L, 2);
1119 	int val = luaL_checkinteger(L, 3);
1120 	if (idx < len || (idx == len && ga_grow(&b->bv_ga, 1) == OK))
1121 	{
1122 	    blob_set(b, idx, (char_u) val);
1123 	    if (idx == len)
1124 		++b->bv_ga.ga_len;
1125 	}
1126 	else
1127 	    luaL_error(L, "index out of range");
1128     }
1129     return 0;
1130 }
1131 
1132     static int
1133 luaV_blob_add(lua_State *L)
1134 {
1135     luaV_Blob *blo = luaV_checkudata(L, 1, LUAVIM_BLOB);
1136     blob_T *b = (blob_T *) luaV_checkcache(L, (void *) *blo);
1137     if (b->bv_lock)
1138 	luaL_error(L, "blob is locked");
1139     lua_settop(L, 2);
1140     if (!lua_isstring(L, 2))
1141 	luaL_error(L, "string expected, got %s", luaL_typename(L, 2));
1142     else
1143     {
1144 	size_t i, l = 0;
1145 	const char *s = lua_tolstring(L, 2, &l);
1146 
1147 	if (ga_grow(&b->bv_ga, l) == OK)
1148 	    for (i = 0; i < l; ++i)
1149 		ga_append(&b->bv_ga, s[i]);
1150     }
1151     lua_settop(L, 1);
1152     return 1;
1153 }
1154 
1155 static const luaL_Reg luaV_Blob_mt[] = {
1156     {"__tostring", luaV_blob_tostring},
1157     {"__gc", luaV_blob_gc},
1158     {"__len", luaV_blob_len},
1159     {"__index", luaV_blob_index},
1160     {"__newindex", luaV_blob_newindex},
1161     {"add", luaV_blob_add},
1162     {NULL, NULL}
1163 };
1164 
1165 
1166 /* =======   Funcref type   ======= */
1167 
1168     static luaV_Funcref *
1169 luaV_newfuncref(lua_State *L, char_u *name)
1170 {
1171     luaV_Funcref *f = (luaV_Funcref *)lua_newuserdata(L, sizeof(luaV_Funcref));
1172 
1173     if (name != NULL)
1174     {
1175 	func_ref(name);
1176 	f->name = vim_strsave(name);
1177     }
1178     f->self = NULL;
1179     luaV_getfield(L, LUAVIM_FUNCREF);
1180     lua_setmetatable(L, -2);
1181     return f;
1182 }
1183 
1184     static luaV_Funcref *
1185 luaV_pushfuncref(lua_State *L, char_u *name)
1186 {
1187     return luaV_newfuncref(L, name);
1188 }
1189 
1190 
1191 luaV_type_tostring(funcref, LUAVIM_FUNCREF)
1192 
1193     static int
1194 luaV_funcref_gc(lua_State *L)
1195 {
1196     luaV_Funcref *f = (luaV_Funcref *) lua_touserdata(L, 1);
1197 
1198     func_unref(f->name);
1199     vim_free(f->name);
1200     // NOTE: Don't call "dict_unref(f->self)", because the dict of "f->self"
1201     // will be (or has been already) freed by Vim's garbage collection.
1202     return 0;
1203 }
1204 
1205 /* equivalent to string(funcref) */
1206     static int
1207 luaV_funcref_len(lua_State *L)
1208 {
1209     luaV_Funcref *f = (luaV_Funcref *) lua_touserdata(L, 1);
1210 
1211     lua_pushstring(L, (const char *) f->name);
1212     return 1;
1213 }
1214 
1215     static int
1216 luaV_funcref_call(lua_State *L)
1217 {
1218     luaV_Funcref *f = (luaV_Funcref *) lua_touserdata(L, 1);
1219     int i, n = lua_gettop(L) - 1; // #args
1220     int status = FAIL;
1221     typval_T args;
1222     typval_T rettv;
1223 
1224     args.v_type = VAR_LIST;
1225     args.vval.v_list = list_alloc();
1226     rettv.v_type = VAR_UNKNOWN; // as in clear_tv
1227     if (args.vval.v_list != NULL)
1228     {
1229 	typval_T v;
1230 
1231 	for (i = 0; i < n; i++)
1232 	{
1233 	    luaV_checktypval(L, i + 2, &v, "calling funcref");
1234 	    list_append_tv(args.vval.v_list, &v);
1235 	    clear_tv(&v);
1236 	}
1237 	status = func_call(f->name, &args, NULL, f->self, &rettv);
1238 	if (status == OK)
1239 	    luaV_pushtypval(L, &rettv);
1240 	clear_tv(&args);
1241 	clear_tv(&rettv);
1242     }
1243     if (status != OK)
1244 	luaL_error(L, "cannot call funcref");
1245     return 1;
1246 }
1247 
1248 static const luaL_Reg luaV_Funcref_mt[] = {
1249     {"__tostring", luaV_funcref_tostring},
1250     {"__gc", luaV_funcref_gc},
1251     {"__len", luaV_funcref_len},
1252     {"__call", luaV_funcref_call},
1253     {NULL, NULL}
1254 };
1255 
1256 
1257 /* =======   Buffer type   ======= */
1258 
1259 luaV_newtype(buf_T, buffer, luaV_Buffer, LUAVIM_BUFFER)
1260 luaV_pushtype(buf_T, buffer, luaV_Buffer)
1261 luaV_type_tostring(buffer, LUAVIM_BUFFER)
1262 
1263     static int
1264 luaV_buffer_len(lua_State *L)
1265 {
1266     buf_T *b = (buf_T *) luaV_checkvalid(L, luaV_Buffer, 1);
1267     lua_pushinteger(L, b->b_ml.ml_line_count);
1268     return 1;
1269 }
1270 
1271     static int
1272 luaV_buffer_call(lua_State *L)
1273 {
1274     buf_T *b = (buf_T *) luaV_checkvalid(L, luaV_Buffer, 1);
1275     lua_settop(L, 1);
1276     set_curbuf(b, DOBUF_SPLIT);
1277     return 1;
1278 }
1279 
1280     static int
1281 luaV_buffer_index(lua_State *L)
1282 {
1283     buf_T *b = (buf_T *) luaV_checkvalid(L, luaV_Buffer, 1);
1284     linenr_T n = (linenr_T) lua_tointeger(L, 2);
1285     if (n > 0 && n <= b->b_ml.ml_line_count)
1286 	luaV_pushline(L, b, n);
1287     else if (lua_isstring(L, 2))
1288     {
1289 	const char *s = lua_tostring(L, 2);
1290 	if (strncmp(s, "name", 4) == 0)
1291 	    lua_pushstring(L, (b->b_sfname == NULL)
1292 					? "" : (char *) b->b_sfname);
1293 	else if (strncmp(s, "fname", 5) == 0)
1294 	    lua_pushstring(L, (b->b_ffname == NULL)
1295 					? "" : (char *) b->b_ffname);
1296 	else if (strncmp(s, "number", 6) == 0)
1297 	    lua_pushinteger(L, b->b_fnum);
1298 	/* methods */
1299 	else if (strncmp(s,   "insert", 6) == 0
1300 		|| strncmp(s, "next", 4) == 0
1301 		|| strncmp(s, "previous", 8) == 0
1302 		|| strncmp(s, "isvalid", 7) == 0)
1303 	{
1304 	    lua_getmetatable(L, 1);
1305 	    lua_getfield(L, -1, s);
1306 	}
1307 	else
1308 	    lua_pushnil(L);
1309     }
1310     else
1311 	lua_pushnil(L);
1312     return 1;
1313 }
1314 
1315     static int
1316 luaV_buffer_newindex(lua_State *L)
1317 {
1318     buf_T *b = (buf_T *) luaV_checkvalid(L, luaV_Buffer, 1);
1319     linenr_T n = (linenr_T) luaL_checkinteger(L, 2);
1320 #ifdef HAVE_SANDBOX
1321     luaV_checksandbox(L);
1322 #endif
1323     if (n < 1 || n > b->b_ml.ml_line_count)
1324 	luaL_error(L, "invalid line number");
1325     if (lua_isnil(L, 3)) /* delete line */
1326     {
1327 	buf_T *buf = curbuf;
1328 	curbuf = b;
1329 	if (u_savedel(n, 1L) == FAIL)
1330 	{
1331 	    curbuf = buf;
1332 	    luaL_error(L, "cannot save undo information");
1333 	}
1334 	else if (ml_delete(n, FALSE) == FAIL)
1335 	{
1336 	    curbuf = buf;
1337 	    luaL_error(L, "cannot delete line");
1338 	}
1339 	else
1340 	{
1341 	    deleted_lines_mark(n, 1L);
1342 	    if (b == curwin->w_buffer) /* fix cursor in current window? */
1343 	    {
1344 		if (curwin->w_cursor.lnum >= n)
1345 		{
1346 		    if (curwin->w_cursor.lnum > n)
1347 		    {
1348 			curwin->w_cursor.lnum -= 1;
1349 			check_cursor_col();
1350 		    }
1351 		    else check_cursor();
1352 		    changed_cline_bef_curs();
1353 		}
1354 		invalidate_botline();
1355 	    }
1356 	}
1357 	curbuf = buf;
1358     }
1359     else if (lua_isstring(L, 3)) /* update line */
1360     {
1361 	buf_T *buf = curbuf;
1362 	curbuf = b;
1363 	if (u_savesub(n) == FAIL)
1364 	{
1365 	    curbuf = buf;
1366 	    luaL_error(L, "cannot save undo information");
1367 	}
1368 	else if (ml_replace(n, luaV_toline(L, 3), TRUE) == FAIL)
1369 	{
1370 	    curbuf = buf;
1371 	    luaL_error(L, "cannot replace line");
1372 	}
1373 	else changed_bytes(n, 0);
1374 	curbuf = buf;
1375 	if (b == curwin->w_buffer)
1376 	    check_cursor_col();
1377     }
1378     else
1379 	luaL_error(L, "wrong argument to change line");
1380     return 0;
1381 }
1382 
1383     static int
1384 luaV_buffer_insert(lua_State *L)
1385 {
1386     luaV_Buffer *lb = luaV_checkudata(L, 1, LUAVIM_BUFFER);
1387     buf_T *b = (buf_T *) luaV_checkcache(L, (void *) *lb);
1388     linenr_T last = b->b_ml.ml_line_count;
1389     linenr_T n = (linenr_T) luaL_optinteger(L, 3, last);
1390     buf_T *buf;
1391     luaL_checktype(L, 2, LUA_TSTRING);
1392 #ifdef HAVE_SANDBOX
1393     luaV_checksandbox(L);
1394 #endif
1395     /* fix insertion line */
1396     if (n < 0) n = 0;
1397     if (n > last) n = last;
1398     /* insert */
1399     buf = curbuf;
1400     curbuf = b;
1401     if (u_save(n, n + 1) == FAIL)
1402     {
1403 	curbuf = buf;
1404 	luaL_error(L, "cannot save undo information");
1405     }
1406     else if (ml_append(n, luaV_toline(L, 2), 0, FALSE) == FAIL)
1407     {
1408 	curbuf = buf;
1409 	luaL_error(L, "cannot insert line");
1410     }
1411     else
1412 	appended_lines_mark(n, 1L);
1413     curbuf = buf;
1414     update_screen(VALID);
1415     return 0;
1416 }
1417 
1418     static int
1419 luaV_buffer_next(lua_State *L)
1420 {
1421     luaV_Buffer *b = luaV_checkudata(L, 1, LUAVIM_BUFFER);
1422     buf_T *buf = (buf_T *) luaV_checkcache(L, (void *) *b);
1423     luaV_pushbuffer(L, buf->b_next);
1424     return 1;
1425 }
1426 
1427     static int
1428 luaV_buffer_previous(lua_State *L)
1429 {
1430     luaV_Buffer *b = luaV_checkudata(L, 1, LUAVIM_BUFFER);
1431     buf_T *buf = (buf_T *) luaV_checkcache(L, (void *) *b);
1432     luaV_pushbuffer(L, buf->b_prev);
1433     return 1;
1434 }
1435 
1436     static int
1437 luaV_buffer_isvalid(lua_State *L)
1438 {
1439     luaV_Buffer *b = luaV_checkudata(L, 1, LUAVIM_BUFFER);
1440     luaV_getudata(L, *b);
1441     lua_pushboolean(L, !lua_isnil(L, -1));
1442     return 1;
1443 }
1444 
1445 static const luaL_Reg luaV_Buffer_mt[] = {
1446     {"__tostring", luaV_buffer_tostring},
1447     {"__len", luaV_buffer_len},
1448     {"__call", luaV_buffer_call},
1449     {"__index", luaV_buffer_index},
1450     {"__newindex", luaV_buffer_newindex},
1451     {"insert", luaV_buffer_insert},
1452     {"next", luaV_buffer_next},
1453     {"previous", luaV_buffer_previous},
1454     {"isvalid", luaV_buffer_isvalid},
1455     {NULL, NULL}
1456 };
1457 
1458 
1459 /* =======   Window type   ======= */
1460 
1461 luaV_newtype(win_T, window, luaV_Window, LUAVIM_WINDOW)
1462 luaV_pushtype(win_T, window, luaV_Window)
1463 luaV_type_tostring(window, LUAVIM_WINDOW)
1464 
1465     static int
1466 luaV_window_call(lua_State *L)
1467 {
1468     win_T *w = (win_T *) luaV_checkvalid(L, luaV_Window, 1);
1469     lua_settop(L, 1);
1470     win_goto(w);
1471     return 1;
1472 }
1473 
1474     static int
1475 luaV_window_index(lua_State *L)
1476 {
1477     win_T *w = (win_T *) luaV_checkvalid(L, luaV_Window, 1);
1478     const char *s = luaL_checkstring(L, 2);
1479     if (strncmp(s, "buffer", 6) == 0)
1480 	luaV_pushbuffer(L, w->w_buffer);
1481     else if (strncmp(s, "line", 4) == 0)
1482 	lua_pushinteger(L, w->w_cursor.lnum);
1483     else if (strncmp(s, "col", 3) == 0)
1484 	lua_pushinteger(L, w->w_cursor.col + 1);
1485     else if (strncmp(s, "width", 5) == 0)
1486 	lua_pushinteger(L, w->w_width);
1487     else if (strncmp(s, "height", 6) == 0)
1488 	lua_pushinteger(L, w->w_height);
1489     /* methods */
1490     else if (strncmp(s,   "next", 4) == 0
1491 	    || strncmp(s, "previous", 8) == 0
1492 	    || strncmp(s, "isvalid", 7) == 0)
1493     {
1494 	lua_getmetatable(L, 1);
1495 	lua_getfield(L, -1, s);
1496     }
1497     else
1498 	lua_pushnil(L);
1499     return 1;
1500 }
1501 
1502     static int
1503 luaV_window_newindex(lua_State *L)
1504 {
1505     win_T *w = (win_T *) luaV_checkvalid(L, luaV_Window, 1);
1506     const char *s = luaL_checkstring(L, 2);
1507     int v = luaL_checkinteger(L, 3);
1508     if (strncmp(s, "line", 4) == 0)
1509     {
1510 #ifdef HAVE_SANDBOX
1511 	luaV_checksandbox(L);
1512 #endif
1513 	if (v < 1 || v > w->w_buffer->b_ml.ml_line_count)
1514 	    luaL_error(L, "line out of range");
1515 	w->w_cursor.lnum = v;
1516 	update_screen(VALID);
1517     }
1518     else if (strncmp(s, "col", 3) == 0)
1519     {
1520 #ifdef HAVE_SANDBOX
1521 	luaV_checksandbox(L);
1522 #endif
1523 	w->w_cursor.col = v - 1;
1524 	w->w_set_curswant = TRUE;
1525 	update_screen(VALID);
1526     }
1527     else if (strncmp(s, "width", 5) == 0)
1528     {
1529 	win_T *win = curwin;
1530 #ifdef FEAT_GUI
1531 	need_mouse_correct = TRUE;
1532 #endif
1533 	curwin = w;
1534 	win_setwidth(v);
1535 	curwin = win;
1536     }
1537     else if (strncmp(s, "height", 6) == 0)
1538     {
1539 	win_T *win = curwin;
1540 #ifdef FEAT_GUI
1541 	need_mouse_correct = TRUE;
1542 #endif
1543 	curwin = w;
1544 	win_setheight(v);
1545 	curwin = win;
1546     }
1547     else
1548 	luaL_error(L, "invalid window property: `%s'", s);
1549     return 0;
1550 }
1551 
1552     static int
1553 luaV_window_next(lua_State *L)
1554 {
1555     luaV_Window *w = luaV_checkudata(L, 1, LUAVIM_WINDOW);
1556     win_T *win = (win_T *) luaV_checkcache(L, (void *) *w);
1557     luaV_pushwindow(L, win->w_next);
1558     return 1;
1559 }
1560 
1561     static int
1562 luaV_window_previous(lua_State *L)
1563 {
1564     luaV_Window *w = luaV_checkudata(L, 1, LUAVIM_WINDOW);
1565     win_T *win = (win_T *) luaV_checkcache(L, (void *) *w);
1566     luaV_pushwindow(L, win->w_prev);
1567     return 1;
1568 }
1569 
1570     static int
1571 luaV_window_isvalid(lua_State *L)
1572 {
1573     luaV_Window *w = luaV_checkudata(L, 1, LUAVIM_WINDOW);
1574     luaV_getudata(L, *w);
1575     lua_pushboolean(L, !lua_isnil(L, -1));
1576     return 1;
1577 }
1578 
1579 static const luaL_Reg luaV_Window_mt[] = {
1580     {"__tostring", luaV_window_tostring},
1581     {"__call", luaV_window_call},
1582     {"__index", luaV_window_index},
1583     {"__newindex", luaV_window_newindex},
1584     {"next", luaV_window_next},
1585     {"previous", luaV_window_previous},
1586     {"isvalid", luaV_window_isvalid},
1587     {NULL, NULL}
1588 };
1589 
1590 
1591 /* =======   Vim module   ======= */
1592 
1593     static int
1594 luaV_print(lua_State *L)
1595 {
1596     int i, n = lua_gettop(L); /* nargs */
1597     const char *s;
1598     size_t l;
1599     luaL_Buffer b;
1600     luaL_buffinit(L, &b);
1601     lua_getglobal(L, "tostring");
1602     for (i = 1; i <= n; i++)
1603     {
1604 	lua_pushvalue(L, -1); /* tostring */
1605 	lua_pushvalue(L, i); /* arg */
1606 	lua_call(L, 1, 1);
1607 	s = lua_tolstring(L, -1, &l);
1608 	if (s == NULL)
1609 	    return luaL_error(L, "cannot convert to string");
1610 	if (i > 1) luaL_addchar(&b, ' '); /* use space instead of tab */
1611 	luaV_addlstring(&b, s, l, 0);
1612 	lua_pop(L, 1);
1613     }
1614     luaL_pushresult(&b);
1615     if (!got_int)
1616 	luaV_msg(L);
1617     return 0;
1618 }
1619 
1620     static int
1621 luaV_debug(lua_State *L)
1622 {
1623     lua_settop(L, 0);
1624     lua_getglobal(L, "vim");
1625     lua_getfield(L, -1, "eval");
1626     lua_remove(L, -2); /* vim.eval at position 1 */
1627     for (;;)
1628     {
1629 	const char *input;
1630 	size_t l;
1631 	lua_pushvalue(L, 1); /* vim.eval */
1632 	lua_pushliteral(L, "input('lua_debug> ')");
1633 	lua_call(L, 1, 1); /* return string */
1634 	input = lua_tolstring(L, -1, &l);
1635 	if (l == 0 || strcmp(input, "cont") == 0)
1636 	    return 0;
1637 	msg_putchar('\n'); /* avoid outputting on input line */
1638 	if (luaL_loadbuffer(L, input, l, "=(debug command)")
1639 		|| lua_pcall(L, 0, 0, 0))
1640 	    luaV_emsg(L);
1641 	lua_settop(L, 1); /* remove eventual returns, but keep vim.eval */
1642     }
1643 }
1644 
1645     static int
1646 luaV_command(lua_State *L)
1647 {
1648     do_cmdline_cmd((char_u *) luaL_checkstring(L, 1));
1649     update_screen(VALID);
1650     return 0;
1651 }
1652 
1653     static int
1654 luaV_eval(lua_State *L)
1655 {
1656     typval_T *tv = eval_expr((char_u *) luaL_checkstring(L, 1), NULL);
1657     if (tv == NULL) luaL_error(L, "invalid expression");
1658     luaV_pushtypval(L, tv);
1659     free_tv(tv);
1660     return 1;
1661 }
1662 
1663     static int
1664 luaV_beep(lua_State *L UNUSED)
1665 {
1666     vim_beep(BO_LANG);
1667     return 0;
1668 }
1669 
1670     static int
1671 luaV_line(lua_State *L)
1672 {
1673     luaV_pushline(L, curbuf, curwin->w_cursor.lnum);
1674     return 1;
1675 }
1676 
1677     static int
1678 luaV_list(lua_State *L)
1679 {
1680     list_T *l;
1681     int initarg = !lua_isnoneornil(L, 1);
1682 
1683     if (initarg && lua_type(L, 1) != LUA_TTABLE)
1684 	luaL_error(L, "table expected, got %s", luaL_typename(L, 1));
1685     l = list_alloc();
1686     if (l == NULL)
1687 	lua_pushnil(L);
1688     else
1689     {
1690 	luaV_newlist(L, l);
1691 	if (initarg) /* traverse table to init list */
1692 	{
1693 	    int notnil, i = 0;
1694 	    typval_T v;
1695 	    do
1696 	    {
1697 		lua_rawgeti(L, 1, ++i);
1698 		notnil = !lua_isnil(L, -1);
1699 		if (notnil)
1700 		{
1701 		    luaV_checktypval(L, -1, &v, "vim.list");
1702 		    list_append_tv(l, &v);
1703 		    clear_tv(&v);
1704 		}
1705 		lua_pop(L, 1); /* value */
1706 	    } while (notnil);
1707 	}
1708     }
1709     return 1;
1710 }
1711 
1712     static int
1713 luaV_dict(lua_State *L)
1714 {
1715     dict_T *d;
1716     int initarg = !lua_isnoneornil(L, 1);
1717 
1718     if (initarg && lua_type(L, 1) != LUA_TTABLE)
1719 	luaL_error(L, "table expected, got %s", luaL_typename(L, 1));
1720     d = dict_alloc();
1721     if (d == NULL)
1722 	lua_pushnil(L);
1723     else
1724     {
1725 	luaV_newdict(L, d);
1726 	if (initarg) /* traverse table to init dict */
1727 	{
1728 	    lua_pushnil(L);
1729 	    while (lua_next(L, 1))
1730 	    {
1731 		char_u *key;
1732 		dictitem_T *di;
1733 		typval_T v;
1734 
1735 		lua_pushvalue(L, -2); /* dup key in case it's a number */
1736 		key = (char_u *) lua_tostring(L, -1);
1737 		if (key == NULL)
1738 		{
1739 		    lua_pushnil(L);
1740 		    return 1;
1741 		}
1742 		if (*key == NUL)
1743 		    luaL_error(L, "table has empty key");
1744 		luaV_checktypval(L, -2, &v, "vim.dict"); /* value */
1745 		di = dictitem_alloc(key);
1746 		if (di == NULL || dict_add(d, di) == FAIL)
1747 		{
1748 		    vim_free(di);
1749 		    lua_pushnil(L);
1750 		    return 1;
1751 		}
1752 		copy_tv(&v, &di->di_tv);
1753 		clear_tv(&v);
1754 		lua_pop(L, 2); /* key copy and value */
1755 	    }
1756 	}
1757     }
1758     return 1;
1759 }
1760 
1761     static int
1762 luaV_blob(lua_State *L)
1763 {
1764     blob_T *b;
1765     int initarg = !lua_isnoneornil(L, 1);
1766 
1767     if (initarg && !lua_isstring(L, 1))
1768 	luaL_error(L, "string expected, got %s", luaL_typename(L, 1));
1769     b = blob_alloc();
1770     if (b == NULL)
1771 	lua_pushnil(L);
1772     else
1773     {
1774 	luaV_newblob(L, b);
1775 	if (initarg)
1776 	{
1777 	    size_t i, l = 0;
1778 	    const char *s = lua_tolstring(L, 1, &l);
1779 
1780 	    if (ga_grow(&b->bv_ga, l) == OK)
1781 		for (i = 0; i < l; ++i)
1782 		    ga_append(&b->bv_ga, s[i]);
1783 	}
1784     }
1785     return 1;
1786 }
1787 
1788     static int
1789 luaV_funcref(lua_State *L)
1790 {
1791     const char *name = luaL_checkstring(L, 1);
1792     /* note: not checking if function exists (needs function_exists) */
1793     if (name == NULL || *name == NUL || VIM_ISDIGIT(*name))
1794 	luaL_error(L, "invalid function name: %s", name);
1795     luaV_newfuncref(L, (char_u *) name);
1796     return 1;
1797 }
1798 
1799     static int
1800 luaV_buffer(lua_State *L)
1801 {
1802     buf_T *buf;
1803     if (lua_isstring(L, 1)) /* get by number or name? */
1804     {
1805 	if (lua_isnumber(L, 1)) /* by number? */
1806 	{
1807 	    int n = lua_tointeger(L, 1);
1808 	    FOR_ALL_BUFFERS(buf)
1809 		if (buf->b_fnum == n) break;
1810 	}
1811 	else // by name
1812 	{
1813 	    size_t l;
1814 	    const char *s = lua_tolstring(L, 1, &l);
1815 	    FOR_ALL_BUFFERS(buf)
1816 	    {
1817 		if (buf->b_ffname == NULL || buf->b_sfname == NULL)
1818 		{
1819 		    if (l == 0) break;
1820 		}
1821 		else if (strncmp(s, (char *)buf->b_ffname, l) == 0
1822 			|| strncmp(s, (char *)buf->b_sfname, l) == 0)
1823 		    break;
1824 	    }
1825 	}
1826     }
1827     else
1828 	buf = (lua_toboolean(L, 1)) ? firstbuf : curbuf; /* first buffer? */
1829     luaV_pushbuffer(L, buf);
1830     return 1;
1831 }
1832 
1833     static int
1834 luaV_window(lua_State *L)
1835 {
1836     win_T *win;
1837     if (lua_isnumber(L, 1)) /* get by number? */
1838     {
1839 	int n = lua_tointeger(L, 1);
1840 	for (win = firstwin; win != NULL; win = win->w_next, n--)
1841 	    if (n == 1) break;
1842     }
1843     else
1844 	win = (lua_toboolean(L, 1)) ? firstwin : curwin; /* first window? */
1845     luaV_pushwindow(L, win);
1846     return 1;
1847 }
1848 
1849     static int
1850 luaV_open(lua_State *L)
1851 {
1852     char_u *s = NULL;
1853 #ifdef HAVE_SANDBOX
1854     luaV_checksandbox(L);
1855 #endif
1856     if (lua_isstring(L, 1)) s = (char_u *) lua_tostring(L, 1);
1857     luaV_pushbuffer(L, buflist_new(s, NULL, 1L, BLN_LISTED));
1858     return 1;
1859 }
1860 
1861     static int
1862 luaV_type(lua_State *L)
1863 {
1864     luaL_checkany(L, 1);
1865     if (lua_type(L, 1) == LUA_TUSERDATA) /* check vim udata? */
1866     {
1867 	lua_settop(L, 1);
1868 	if (lua_getmetatable(L, 1))
1869 	{
1870 	    luaV_getfield(L, LUAVIM_LIST);
1871 	    if (lua_rawequal(L, -1, 2))
1872 	    {
1873 		lua_pushstring(L, "list");
1874 		return 1;
1875 	    }
1876 	    luaV_getfield(L, LUAVIM_DICT);
1877 	    if (lua_rawequal(L, -1, 2))
1878 	    {
1879 		lua_pushstring(L, "dict");
1880 		return 1;
1881 	    }
1882 	    luaV_getfield(L, LUAVIM_BLOB);
1883 	    if (lua_rawequal(L, -1, 2))
1884 	    {
1885 		lua_pushstring(L, "blob");
1886 		return 1;
1887 	    }
1888 	    luaV_getfield(L, LUAVIM_FUNCREF);
1889 	    if (lua_rawequal(L, -1, 2))
1890 	    {
1891 		lua_pushstring(L, "funcref");
1892 		return 1;
1893 	    }
1894 	    luaV_getfield(L, LUAVIM_BUFFER);
1895 	    if (lua_rawequal(L, -1, 2))
1896 	    {
1897 		lua_pushstring(L, "buffer");
1898 		return 1;
1899 	    }
1900 	    luaV_getfield(L, LUAVIM_WINDOW);
1901 	    if (lua_rawequal(L, -1, 2))
1902 	    {
1903 		lua_pushstring(L, "window");
1904 		return 1;
1905 	    }
1906 	}
1907     }
1908     lua_pushstring(L, luaL_typename(L, 1)); /* fallback */
1909     return 1;
1910 }
1911 
1912 static const luaL_Reg luaV_module[] = {
1913     {"command", luaV_command},
1914     {"eval", luaV_eval},
1915     {"beep", luaV_beep},
1916     {"line", luaV_line},
1917     {"list", luaV_list},
1918     {"dict", luaV_dict},
1919     {"blob", luaV_blob},
1920     {"funcref", luaV_funcref},
1921     {"buffer", luaV_buffer},
1922     {"window", luaV_window},
1923     {"open", luaV_open},
1924     {"type", luaV_type},
1925     {NULL, NULL}
1926 };
1927 
1928 /* for freeing list, dict, buffer and window objects; lightuserdata as arg */
1929     static int
1930 luaV_free(lua_State *L)
1931 {
1932     lua_pushnil(L);
1933     luaV_setudata(L, lua_touserdata(L, 1));
1934     return 0;
1935 }
1936 
1937     static int
1938 luaV_luaeval(lua_State *L)
1939 {
1940     luaL_Buffer b;
1941     size_t l;
1942     const char *str = lua_tolstring(L, 1, &l);
1943     typval_T *arg = (typval_T *) lua_touserdata(L, 2);
1944     typval_T *rettv = (typval_T *) lua_touserdata(L, 3);
1945     luaL_buffinit(L, &b);
1946     luaL_addlstring(&b, LUAVIM_EVALHEADER, sizeof(LUAVIM_EVALHEADER) - 1);
1947     luaL_addlstring(&b, str, l);
1948     luaL_pushresult(&b);
1949     str = lua_tolstring(L, -1, &l);
1950     if (luaL_loadbuffer(L, str, l, LUAVIM_EVALNAME)) /* compile error? */
1951     {
1952 	luaV_emsg(L);
1953 	return 0;
1954     }
1955     luaV_pushtypval(L, arg);
1956     if (lua_pcall(L, 1, 1, 0)) /* running error? */
1957     {
1958 	luaV_emsg(L);
1959 	return 0;
1960     }
1961     if (luaV_totypval(L, -1, rettv) == FAIL)
1962 	emsg("luaeval: cannot convert value");
1963     return 0;
1964 }
1965 
1966     static int
1967 luaV_setref(lua_State *L)
1968 {
1969     int copyID = lua_tointeger(L, 1);
1970     int abort = FALSE;
1971 
1972     luaV_getfield(L, LUAVIM_LIST);
1973     luaV_getfield(L, LUAVIM_DICT);
1974     luaV_getfield(L, LUAVIM_FUNCREF);
1975     lua_pushnil(L);
1976     // traverse cache table
1977     while (!abort && lua_next(L, lua_upvalueindex(1)) != 0)
1978     {
1979 	lua_getmetatable(L, -1);
1980 	if (lua_rawequal(L, -1, 2)) // list?
1981 	{
1982 	    list_T *l = (list_T *)lua_touserdata(L, 5); // key
1983 
1984 	    abort = set_ref_in_list(l, copyID);
1985 	}
1986 	else if (lua_rawequal(L, -1, 3)) // dict?
1987 	{
1988 	    dict_T *d = (dict_T *)lua_touserdata(L, 5); // key
1989 
1990 	    abort = set_ref_in_dict(d, copyID);
1991 	}
1992 	else if (lua_rawequal(L, -1, 4)) // funcref?
1993 	{
1994 	    luaV_Funcref *f = (luaV_Funcref *)lua_touserdata(L, 5); // key
1995 
1996 	    abort = set_ref_in_dict(f->self, copyID);
1997 	}
1998 	lua_pop(L, 2); // metatable and value
1999     }
2000     lua_pushinteger(L, abort);
2001     return 1;
2002 }
2003 
2004     static int
2005 luaopen_vim(lua_State *L)
2006 {
2007     /* set cache table */
2008     lua_newtable(L);
2009     lua_newtable(L);
2010     lua_pushstring(L, "v");
2011     lua_setfield(L, -2, "__mode");
2012     lua_setmetatable(L, -2); /* cache is weak-valued */
2013     /* print */
2014     lua_pushcfunction(L, luaV_print);
2015     lua_setglobal(L, "print");
2016     /* debug.debug */
2017     lua_getglobal(L, "debug");
2018     lua_pushcfunction(L, luaV_debug);
2019     lua_setfield(L, -2, "debug");
2020     lua_pop(L, 1);
2021     /* free */
2022     lua_pushlightuserdata(L, (void *) LUAVIM_FREE);
2023     lua_pushvalue(L, 1); /* cache table */
2024     lua_pushcclosure(L, luaV_free, 1);
2025     lua_rawset(L, LUA_REGISTRYINDEX);
2026     /* luaeval */
2027     lua_pushlightuserdata(L, (void *) LUAVIM_LUAEVAL);
2028     lua_pushvalue(L, 1); /* cache table */
2029     lua_pushcclosure(L, luaV_luaeval, 1);
2030     lua_rawset(L, LUA_REGISTRYINDEX);
2031     /* setref */
2032     lua_pushlightuserdata(L, (void *) LUAVIM_SETREF);
2033     lua_pushvalue(L, 1); /* cache table */
2034     lua_pushcclosure(L, luaV_setref, 1);
2035     lua_rawset(L, LUA_REGISTRYINDEX);
2036     /* register */
2037     luaV_newmetatable(L, LUAVIM_LIST);
2038     lua_pushvalue(L, 1);
2039     luaV_openlib(L, luaV_List_mt, 1);
2040     luaV_newmetatable(L, LUAVIM_DICT);
2041     lua_pushvalue(L, 1);
2042     luaV_openlib(L, luaV_Dict_mt, 1);
2043     luaV_newmetatable(L, LUAVIM_BLOB);
2044     lua_pushvalue(L, 1);
2045     luaV_openlib(L, luaV_Blob_mt, 1);
2046     luaV_newmetatable(L, LUAVIM_FUNCREF);
2047     lua_pushvalue(L, 1);
2048     luaV_openlib(L, luaV_Funcref_mt, 1);
2049     luaV_newmetatable(L, LUAVIM_BUFFER);
2050     lua_pushvalue(L, 1); /* cache table */
2051     luaV_openlib(L, luaV_Buffer_mt, 1);
2052     luaV_newmetatable(L, LUAVIM_WINDOW);
2053     lua_pushvalue(L, 1); /* cache table */
2054     luaV_openlib(L, luaV_Window_mt, 1);
2055     lua_newtable(L); /* vim table */
2056     lua_pushvalue(L, 1); /* cache table */
2057     luaV_openlib(L, luaV_module, 1);
2058     lua_setglobal(L, LUAVIM_NAME);
2059     return 0;
2060 }
2061 
2062     static lua_State *
2063 luaV_newstate(void)
2064 {
2065     lua_State *L = luaL_newstate();
2066     luaL_openlibs(L); /* core libs */
2067     lua_pushcfunction(L, luaopen_vim); /* vim */
2068     lua_call(L, 0, 0);
2069     return L;
2070 }
2071 
2072     static void
2073 luaV_setrange(lua_State *L, int line1, int line2)
2074 {
2075     lua_getglobal(L, LUAVIM_NAME);
2076     lua_pushinteger(L, line1);
2077     lua_setfield(L, -2, "firstline");
2078     lua_pushinteger(L, line2);
2079     lua_setfield(L, -2, "lastline");
2080     lua_pop(L, 1); /* vim table */
2081 }
2082 
2083 
2084 /* =======   Interface   ======= */
2085 
2086 static lua_State *L = NULL;
2087 
2088     static int
2089 lua_isopen(void)
2090 {
2091     return L != NULL;
2092 }
2093 
2094     static int
2095 lua_init(void)
2096 {
2097     if (!lua_isopen())
2098     {
2099 #ifdef DYNAMIC_LUA
2100 	if (!lua_enabled(TRUE))
2101 	{
2102 	    emsg(_("Lua library cannot be loaded."));
2103 	    return FAIL;
2104 	}
2105 #endif
2106 	L = luaV_newstate();
2107     }
2108     return OK;
2109 }
2110 
2111     void
2112 lua_end(void)
2113 {
2114     if (lua_isopen())
2115     {
2116 	lua_close(L);
2117 	L = NULL;
2118 #ifdef DYNAMIC_LUA
2119 	end_dynamic_lua();
2120 #endif
2121     }
2122 }
2123 
2124 /* ex commands */
2125     void
2126 ex_lua(exarg_T *eap)
2127 {
2128     char *script;
2129     if (lua_init() == FAIL) return;
2130     script = (char *) script_get(eap, eap->arg);
2131     if (!eap->skip)
2132     {
2133 	char *s = (script) ? script :  (char *) eap->arg;
2134 	luaV_setrange(L, eap->line1, eap->line2);
2135 	if (luaL_loadbuffer(L, s, strlen(s), LUAVIM_CHUNKNAME)
2136 		|| lua_pcall(L, 0, 0, 0))
2137 	    luaV_emsg(L);
2138     }
2139     if (script != NULL) vim_free(script);
2140 }
2141 
2142     void
2143 ex_luado(exarg_T *eap)
2144 {
2145     linenr_T l;
2146     const char *s = (const char *) eap->arg;
2147     luaL_Buffer b;
2148     size_t len;
2149     buf_T *was_curbuf = curbuf;
2150 
2151     if (lua_init() == FAIL) return;
2152     if (u_save(eap->line1 - 1, eap->line2 + 1) == FAIL)
2153     {
2154 	emsg(_("cannot save undo information"));
2155 	return;
2156     }
2157     luaV_setrange(L, eap->line1, eap->line2);
2158     luaL_buffinit(L, &b);
2159     luaL_addlstring(&b, "return function(line, linenr) ", 30); /* header */
2160     luaL_addlstring(&b, s, strlen(s));
2161     luaL_addlstring(&b, " end", 4); /* footer */
2162     luaL_pushresult(&b);
2163     s = lua_tolstring(L, -1, &len);
2164     if (luaL_loadbuffer(L, s, len, LUAVIM_CHUNKNAME))
2165     {
2166 	luaV_emsg(L);
2167 	lua_pop(L, 1); /* function body */
2168 	return;
2169     }
2170     lua_call(L, 0, 1);
2171     lua_replace(L, -2); /* function -> body */
2172     for (l = eap->line1; l <= eap->line2; l++)
2173     {
2174 	/* Check the line number, the command my have deleted lines. */
2175 	if (l > curbuf->b_ml.ml_line_count)
2176 	    break;
2177 
2178 	lua_pushvalue(L, -1); /* function */
2179 	luaV_pushline(L, curbuf, l); /* current line as arg */
2180 	lua_pushinteger(L, l); /* current line number as arg */
2181 	if (lua_pcall(L, 2, 1, 0))
2182 	{
2183 	    luaV_emsg(L);
2184 	    break;
2185 	}
2186 	/* Catch the command switching to another buffer. */
2187 	if (curbuf != was_curbuf)
2188 	    break;
2189 	if (lua_isstring(L, -1)) /* update line? */
2190 	{
2191 #ifdef HAVE_SANDBOX
2192 	    luaV_checksandbox(L);
2193 #endif
2194 	    ml_replace(l, luaV_toline(L, -1), TRUE);
2195 	    changed_bytes(l, 0);
2196 	    lua_pop(L, 1); /* result from luaV_toline */
2197 	}
2198 	lua_pop(L, 1); /* line */
2199     }
2200     lua_pop(L, 1); /* function */
2201     check_cursor();
2202     update_screen(NOT_VALID);
2203 }
2204 
2205     void
2206 ex_luafile(exarg_T *eap)
2207 {
2208     if (lua_init() == FAIL)
2209 	return;
2210     if (!eap->skip)
2211     {
2212 	luaV_setrange(L, eap->line1, eap->line2);
2213 	if (luaL_loadfile(L, (char *) eap->arg) || lua_pcall(L, 0, 0, 0))
2214 	    luaV_emsg(L);
2215     }
2216 }
2217 
2218 #define luaV_freetype(typ,tname) \
2219 	void \
2220     lua_##tname##_free(typ *o) \
2221     { \
2222 	if (!lua_isopen()) return; \
2223 	luaV_getfield(L, LUAVIM_FREE); \
2224 	lua_pushlightuserdata(L, (void *) o); \
2225 	lua_call(L, 1, 0); \
2226     }
2227 
2228 luaV_freetype(buf_T, buffer)
2229 luaV_freetype(win_T, window)
2230 
2231     void
2232 do_luaeval(char_u *str, typval_T *arg, typval_T *rettv)
2233 {
2234     lua_init();
2235     luaV_getfield(L, LUAVIM_LUAEVAL);
2236     lua_pushstring(L, (char *) str);
2237     lua_pushlightuserdata(L, (void *) arg);
2238     lua_pushlightuserdata(L, (void *) rettv);
2239     lua_call(L, 3, 0);
2240 }
2241 
2242     int
2243 set_ref_in_lua(int copyID)
2244 {
2245     int aborted = 0;
2246 
2247     if (lua_isopen())
2248     {
2249 	luaV_getfield(L, LUAVIM_SETREF);
2250 	/* call the function with 1 arg, getting 1 result back */
2251 	lua_pushinteger(L, copyID);
2252 	lua_call(L, 1, 1);
2253 	/* get the result */
2254 	aborted = lua_tointeger(L, -1);
2255 	/* pop result off the stack */
2256 	lua_pop(L, 1);
2257     }
2258     return aborted;
2259 }
2260 
2261 #endif
2262