*** empty log message ***

master
mark 20 years ago
parent d0e584b79f
commit 76a98495ba

@ -0,0 +1,31 @@
ex-20070109
API changes
* os.unsetenv is now folded into os.setenv
* os.rmdir is now folded into os.remove
* os.dir now elides . and .. entries from the listing
* lock and unlock now appear in the io table
* io.lock and io.unlock return the file object in case of success
POSIX implementation changes
* ENVIRON_DECL should be defined to expand to extern char **environ; on systems which neglect to declare environ when including <unistd.h>
* prepare for dirent metatable
* ex_pipe() refactored
Windows implementation changes
* os.remove must be overridden
* prepare for dirent metatable
* simplify directory iteration by adding POSIX-like abstraction
* ex_pipe() refactored

@ -1,10 +1,10 @@
-- Environment
os.setenv(name, value)
os.unsetenv(name)
os.getenv(name) -- get environment variable
os.setenv(name, value) -- set/unset environment variable
os.environ() -- returns a copy of the environment
-- Miscellaneous
os.sleep(seconds)
os.sleep(seconds) -- sleep for (floating) seconds
-- File system
os.chdir(pathname)

@ -1,13 +1,13 @@
CFLAGS = $(WARNINGS) $(DEFINES) $(INCLUDES)
DEFINES = $(DEBUG) -D_XOPEN_SOURCE=600 -DMISSING_POSIX_SPAWN -DMISSING_ENVIRON_DECL="extern char **environ"
DEFINES = $(DEBUG) -D_XOPEN_SOURCE=600 -DMISSING_POSIX_SPAWN -DENVIRON_DECL="extern char **environ;"
DEBUG= -D'debug(...)=fprintf(stderr,__VA_ARGS__)'
# -D_POSIX_SOURCE -D_XOPEN_SOURCE=600 -D_POSIX_C_SOURCE=200112L \
-U__STRICT_ANSI__ -D_GNU_SOURCE
INCLUDES = -I$(LUA)/include -I$(LUA)/src
WARNINGS = -W -Wall
#LUA = /home/mark/src/lang/lua/lua-5.1-rc2
#LUA = /home/mark/src/lang/lua/lua51
LUA = /home/medgar/src/lang/lua/lua-5.1.1
#LUA = /home/medgar/src/lang/lua/lua5_1_1/cygw15
LIBS = -L$(LUA)/src -llua5.1
ex-OBJS = ex.o spawn.o

@ -3,23 +3,21 @@
#include <ctype.h>
#include <errno.h>
#include <string.h>
#include <unistd.h> /* environ */
#include "lua.h"
#include "lualib.h"
#include "lauxlib.h"
#include <unistd.h>
ENVIRON_DECL
#include <dirent.h>
#include <fcntl.h>
#include <sys/stat.h>
#include "spawn.h"
#include "lua.h"
#include "lualib.h"
#include "lauxlib.h"
MISSING_ENVIRON_DECL;
#define absindex(L,i) ((i)>0?(i):lua_gettop(L)+(i)+1)
#include "spawn.h"
#define absindex(L,i) ((i)>0?(i):lua_gettop(L)+(i)+1)
/* -- nil error */
extern int push_error(lua_State *L)
@ -41,8 +39,8 @@ static int ex_getenv(lua_State *L)
return 1;
}
/* name value -- true/nil error *
* name -- true/nil error */
/* name value -- true/nil error
* name nil -- true/nil error */
static int ex_setenv(lua_State *L)
{
const char *nam = luaL_checkstring(L, 1);
@ -126,13 +124,23 @@ static FILE *check_file(lua_State *L, int idx, const char *argname)
return *pf;
}
static FILE **new_file(lua_State *L, int fd, const char *mode)
{
FILE **pf = lua_newuserdata(L, sizeof *pf);
*pf = 0;
luaL_getmetatable(L, LUA_FILEHANDLE);
lua_setmetatable(L, -2);
*pf = fdopen(fd, mode);
return pf;
}
#define new_dirent(L) lua_newtable(L)
/* pathname/file -- entry */
/* pathname/file [entry] -- entry */
static int ex_dirent(lua_State *L)
{
struct stat st;
int isdir;
switch (lua_type(L, 1)) {
default: return luaL_typerror(L, 1, "file or pathname");
case LUA_TSTRING: {
@ -146,19 +154,20 @@ static int ex_dirent(lua_State *L)
return push_error(L);
} break;
}
isdir = S_ISDIR(st.st_mode);
if (lua_type(L, 2) != LUA_TTABLE) {
lua_settop(L, 1);
new_dirent(L);
lua_replace(L, 2);
}
if (isdir)
else {
lua_settop(L, 2);
}
if (S_ISDIR(st.st_mode))
lua_pushliteral(L, "directory");
else
lua_pushliteral(L, "file");
lua_setfield(L, 2, "type");
lua_pushnumber(L, st.st_size);
lua_setfield(L, 2, "size");
lua_settop(L, 2);
return 1;
}
@ -202,8 +211,8 @@ static int diriter_close(lua_State *L)
static int isdotfile(const char *name)
{
return name[0] && (name[1] == 0
|| (name[1] == '.' && name[2] == 0));
return name[0] == '.' && (name[1] == '\0'
|| (name[1] == '.' && name[2] == '\0'));
}
/* pathname -- iter state nil */
@ -259,11 +268,11 @@ static int file_lock(lua_State *L, FILE *f, const char *mode, long offset, long
k.l_len = length;
if (-1 == fcntl(fileno(f), F_SETLK, &k))
return push_error(L);
lua_pushboolean(L, 1);
lua_settop(L, 1);
return 1;
}
/* file mode [offset [length]] -- true/nil error */
/* file mode [offset [length]] -- file/nil error */
static int ex_lock(lua_State *L)
{
FILE *f = check_file(L, 1, NULL);
@ -273,7 +282,7 @@ static int ex_lock(lua_State *L)
return file_lock(L, f, mode, offset, length);
}
/* file [offset [length]] -- true/nil error */
/* file [offset [length]] -- file/nil error */
static int ex_unlock(lua_State *L)
{
lua_pushliteral(L, "u");
@ -290,22 +299,12 @@ static int closeonexec(int d)
return fl;
}
static int new_file(lua_State *L, int fd, const char *mode)
{
FILE **pf = lua_newuserdata(L, sizeof *pf);
*pf = 0;
luaL_getmetatable(L, LUA_FILEHANDLE);
lua_setmetatable(L, -2);
*pf = fdopen(fd, mode);
return 1;
}
/* -- in out/nil error */
static int ex_pipe(lua_State *L)
{
int fd[2];
if (-1 == pipe(fd))
return 0;
return push_error(L);
closeonexec(fd[0]);
closeonexec(fd[1]);
new_file(L, fd[0], "r");
@ -322,8 +321,8 @@ static void get_redirect(lua_State *L, int idx, const char *stdname, struct spaw
lua_pop(L, 1);
}
/* filename [args-opts] -- true/nil error */
/* args-opts -- true/nil error */
/* filename [args-opts] -- proc/nil error */
/* args-opts -- proc/nil error */
static int ex_spawn(lua_State *L)
{
struct spawn_params *params;
@ -385,13 +384,13 @@ static int ex_spawn(lua_State *L)
}
lua_getfield(L, 2, "env"); /* cmd opts ... envtab */
switch (lua_type(L, -1)) {
default: return luaL_error(L, "bad env option (table expected, got %s)",
luaL_typename(L, -1));
case LUA_TNIL:
break;
case LUA_TTABLE:
spawn_param_env(params); /* cmd opts ... */
break;
default:
return luaL_error(L, "bad env option (table expected, got %s)", luaL_typename(L, -1));
}
get_redirect(L, 2, "stdin", params); /* cmd opts ... */
get_redirect(L, 2, "stdout", params); /* cmd opts ... */
@ -405,9 +404,7 @@ static int ex_spawn(lua_State *L)
/* copy the fields given in 'l' from one table to another; insert missing fields */
static void copy_fields(lua_State *L, const luaL_reg *l, int from, int to)
{
from = absindex(L, from);
to = absindex(L, to);
for (; l->name; l++) {
for (to = absindex(L, to); l->name; l++) {
lua_getfield(L, from, l->name);
if (lua_isnil(L, -1)) {
lua_pop(L, 1);
@ -467,6 +464,7 @@ int luaopen_ex(lua_State *L)
lua_getglobal(L, "io"); /* ex . io */
if (lua_isnil(L, -1)) return luaL_error(L, "io not loaded");
copy_fields(L, ex_iolib, 1, -1); /* ex . io */
copy_fields(L, ex_iofile_methods, 1, -1); /* ex . io */
lua_getfield(L, 1, "pipe"); /* ex . io ex_pipe */
lua_getfield(L, -2, "stderr"); /* ex . io ex_pipe io_stderr */
lua_getfenv(L, -1); /* ex . io ex_pipe io_stderr E */

@ -3,6 +3,7 @@
#include <errno.h>
#include <unistd.h>
ENVIRON_DECL
#include <limits.h>
#include <sys/types.h>
@ -12,7 +13,6 @@
#define OPEN_MAX sysconf(_SC_OPEN_MAX)
#endif
MISSING_ENVIRON_DECL;
int posix_spawn_file_actions_init(posix_spawn_file_actions_t *act)
{

@ -1,7 +1,5 @@
#include "lua.h"
#include "lauxlib.h"
#include <unistd.h>
ENVIRON_DECL
#include <sys/wait.h>
#if MISSING_POSIX_SPAWN
#include "posix_spawn.h"
@ -9,8 +7,10 @@
#include <spawn.h>
#endif
#include "lua.h"
#include "lauxlib.h"
#include "spawn.h"
MISSING_ENVIRON_DECL;
struct spawn_params {
lua_State *L;

@ -2,7 +2,7 @@
#define SPAWN_H
#include <stdio.h>
#include <lua.h>
#include "lua.h"
#define PROCESS_HANDLE "process"
struct process;

@ -8,8 +8,10 @@ WARNINGS = -W -Wall -Wno-missing-braces
LUA = /home/medgar/work/noom/lua/lua51
LUALIBS = -L$(LUA) -llua5.1
ex.dll-OBJS = ex.o spawn.o pusherror.o
ex.dll-OBJS = ex.o spawn.o pusherror.o dirent.o
ex.dll-LIBS = $(LUALIBS) $(EXTRALIBS)
ex.dll: $(ex.dll-OBJS)
$(CC) $(TARGET_ARCH) -shared -o $@ $(ex.dll-OBJS) $(ex.dll-LIBS)
clean:; rm ex.dll *.o
wdir.o: wdir.c wdir.h

@ -0,0 +1,68 @@
#include <windows.h>
#include <stdlib.h>
#include "dirent.h"
struct DIR_tag {
int first;
HANDLE hf;
WIN32_FIND_DATA fd;
};
static char *mkpattern(const char *name)
{
static const char suffix[] = "\\*";
size_t len = strlen(name);
char *pattern = malloc(len + sizeof suffix);
if (pattern)
strcpy(memcpy(pattern, name, len) + len, suffix);
return pattern;
}
DIR *
opendir(const char *name)
{
DIR *pi = malloc(sizeof *pi);
char *pattern = mkpattern(name);
if (!pi || !pattern
|| INVALID_HANDLE_VALUE == (pi->hf = FindFirstFile(pattern, &pi->fd))) {
free(pi);
pi = 0;
}
else {
pi->first = 1;
}
free(pattern);
return pi;
}
static int isdotfile(const char *name)
{
return name[0] == '.' && (name[1] == 0
|| (name[1] == '.' && name[2] == 0));
}
const WIN32_FIND_DATA *
readdir(DIR *pi)
{
switch (pi->first) do {
default:
if (!FindNextFile(pi->hf, &pi->fd)) {
FindClose(pi->hf);
pi->hf = INVALID_HANDLE_VALUE;
return 0;
}
case 1: pi->first = 0;
} while (isdotfile(pi->fd.cFileName));
return &pi->fd;
}
void
closedir(DIR *pi)
{
if (pi->hf != INVALID_HANDLE_VALUE)
{
FindClose(pi->hf);
pi->hf = INVALID_HANDLE_VALUE;
}
free(pi);
}

@ -0,0 +1,6 @@
#include <windows.h>
typedef struct DIR_tag DIR;
DIR *opendir(const char *name);
const WIN32_FIND_DATA *readdir(DIR *pi);
void closedir(DIR *pi);

@ -7,18 +7,19 @@
#include <io.h>
#include <fcntl.h>
#include <sys/locking.h>
#include "dirent.h"
#include "lua.h"
#include "lualib.h"
#include "lauxlib.h"
#include "spawn.h"
#include "pusherror.h"
#define absindex(L,i) ((i)>0?(i):lua_gettop(L)+(i)+1)
#include "spawn.h"
#define absindex(L,i) ((i)>0?(i):lua_gettop(L)+(i)+1)
#include "pusherror.h"
#define push_error(L) windows_pushlasterror(L)
#define file_handle(fp) (HANDLE)_get_osfhandle(fileno(fp))
/* name -- value/nil */
@ -32,7 +33,7 @@ static int ex_getenv(lua_State *L)
len = GetEnvironmentVariable(nam, val, sizeof val);
}
if (len == 0 && GetLastError() == ERROR_ENVVAR_NOT_FOUND)
return windows_pushlasterror(L);
return push_error(L);
lua_pushlstring(L, val, len);
if (val != sval) free(val);
return 1;
@ -45,7 +46,7 @@ static int ex_setenv(lua_State *L)
const char *nam = luaL_checkstring(L, 1);
const char *val = lua_tostring(L, 2);
if (!SetEnvironmentVariable(nam, val))
return windows_pushlasterror(L);
return push_error(L);
lua_pushboolean(L, 1);
return 1;
}
@ -55,7 +56,7 @@ static int ex_environ(lua_State *L)
{
const char *nam, *val, *end;
const char *envs = GetEnvironmentStrings();
if (!envs) return windows_pushlasterror(L);
if (!envs) return push_error(L);
lua_newtable(L);
for (nam = envs; *nam; nam = end + 1) {
end = strchr(val = strchr(nam, '=') + 1, '\0');
@ -81,7 +82,7 @@ static int ex_chdir(lua_State *L)
{
const char *pathname = luaL_checkstring(L, 1);
if (!SetCurrentDirectory(pathname))
return windows_pushlasterror(L);
return push_error(L);
lua_pushboolean(L, 1);
return 1;
}
@ -91,7 +92,7 @@ static int ex_mkdir(lua_State *L)
{
const char *pathname = luaL_checkstring(L, 1);
if (!CreateDirectory(pathname, 0))
return windows_pushlasterror(L);
return push_error(L);
lua_pushboolean(L, 1);
return 1;
}
@ -101,7 +102,7 @@ static int ex_currentdir(lua_State *L)
{
char pathname[MAX_PATH + 1];
size_t len = GetCurrentDirectory(sizeof pathname, pathname);
if (len == 0) return windows_pushlasterror(L);
if (len == 0) return push_error(L);
lua_pushlstring(L, pathname, len);
return 1;
}
@ -115,12 +116,13 @@ static int ex_remove(lua_State *L)
|| (attr & FILE_ATTRIBUTE_DIRECTORY
? !RemoveDirectory(pathname)
: !DeleteFile(pathname)))
return windows_pushlasterror(L);
return push_error(L);
lua_pushboolean(L, 1);
return 1;
}
FILE *check_file(lua_State *L, int idx, const char *argname)
static FILE *check_file(lua_State *L, int idx, const char *argname)
{
FILE **pf;
if (idx > 0) pf = luaL_checkudata(L, idx, LUA_FILEHANDLE);
@ -137,6 +139,19 @@ FILE *check_file(lua_State *L, int idx, const char *argname)
return *pf;
}
static FILE **new_file(lua_State *L, HANDLE h, int dmode, const char *mode)
{
FILE **pf = lua_newuserdata(L, sizeof *pf);
*pf = 0;
luaL_getmetatable(L, LUA_FILEHANDLE);
lua_setmetatable(L, -2);
*pf = _fdopen(_open_osfhandle((long)h, dmode), mode);
return pf;
}
#define file_handle(fp) (HANDLE)_get_osfhandle(fileno(fp))
static uint64_t get_file_size(const char *name)
{
HANDLE h = CreateFile(name, GENERIC_READ, FILE_SHARE_READ, 0, OPEN_EXISTING, 0, 0);
@ -169,7 +184,7 @@ static int ex_dirent(lua_State *L)
const char *name = lua_tostring(L, 1);
attr = GetFileAttributes(name);
if (attr == (DWORD)-1)
return windows_pushlasterror(L);
return push_error(L);
isdir = attr & FILE_ATTRIBUTE_DIRECTORY;
if (isdir)
size = 0;
@ -181,7 +196,7 @@ static int ex_dirent(lua_State *L)
uint64_t lsize;
BY_HANDLE_FILE_INFORMATION info;
if (!GetFileInformationByHandle(file_handle(f), &info))
return windows_pushlasterror(L);
return push_error(L);
attr = info.dwFileAttributes;
isdir = attr & FILE_ATTRIBUTE_DIRECTORY;
lsize = info.nFileSizeHigh; lsize <<= 32; lsize += info.nFileSizeLow;
@ -205,12 +220,7 @@ static int ex_dirent(lua_State *L)
return 1;
}
#define DIR_HANDLE "WIN32_FIND_DATA"
struct diriter {
HANDLE hf;
int first;
WIN32_FIND_DATA fd;
};
#define DIR_HANDLE "DIR*"
/* ...diriter... -- ...diriter... pathname */
static int diriter_getpathname(lua_State *L, int index)
@ -238,32 +248,18 @@ static int diriter_setpathname(lua_State *L, int index)
/* diriter -- diriter */
static int diriter_close(lua_State *L)
{
struct diriter *pi = lua_touserdata(L, 1);
if (pi->hf != INVALID_HANDLE_VALUE) {
FindClose(pi->hf);
pi->hf = INVALID_HANDLE_VALUE;
}
DIR **pd = lua_touserdata(L, 1);
closedir(*pd);
*pd = 0;
lua_pushnil(L);
diriter_setpathname(L, 1);
return 0;
}
static int isdotfile(const char *filename)
static int isdotfile(const char *name)
{
return filename[0] == '.' &&
(filename[1] == '\0' || (filename[1] == '.' && filename[2] == '\0'));
}
static int nextfile(struct diriter *pi)
{
if (!pi->first || isdotfile(pi->fd.cFileName))
do if (!FindNextFile(pi->hf, &pi->fd)) {
FindClose(pi->hf);
pi->hf = INVALID_HANDLE_VALUE;
return 0;
} while (isdotfile(pi->fd.cFileName));
pi->first = 0;
return 1;
return name[0] == '.' && (name[1] == '\0'
|| (name[1] == '.' && name[2] == '\0'));
}
/* pathname -- iter state nil */
@ -271,31 +267,29 @@ static int nextfile(struct diriter *pi)
static int ex_dir(lua_State *L)
{
const char *pathname;
struct diriter *pi;
DIR **pd;
const WIN32_FIND_DATA *d;
switch (lua_type(L, 1)) {
default: return luaL_typerror(L, 1, "pathname");
case LUA_TSTRING:
lua_pushvalue(L, 1); /* pathname ... pathname */
lua_pushliteral(L, "\\*"); /* pathname ... pathname "\\*" */
lua_concat(L, 2); /* pathname ... pattern */
pathname = lua_tostring(L, -1);
lua_pushcfunction(L, ex_dir); /* pathname ... pat iter */
pi = lua_newuserdata(L, sizeof *pi);/* pathname ... pat iter state */
pi->hf = FindFirstFile(pathname, &pi->fd);
if (pi->hf == INVALID_HANDLE_VALUE)
return windows_pushlasterror(L);
pi->first = 1;
luaL_getmetatable(L, DIR_HANDLE); /* pathname ... pat iter state M */
lua_setmetatable(L, -2); /* pathname ... pat iter state */
lua_pushvalue(L, 1); /* pathname ... pat iter state pathname */
diriter_setpathname(L, -2); /* pathname ... pat iter state */
pathname = lua_tostring(L, 1);
lua_pushcfunction(L, ex_dir); /* pathname ... iter */
pd = lua_newuserdata(L, sizeof *pd);/* pathname ... iter state */
*pd = opendir(pathname);
if (!*pd) return push_error(L);
luaL_getmetatable(L, DIR_HANDLE); /* pathname ... iter state M */
lua_setmetatable(L, -2); /* pathname ... iter state */
lua_pushvalue(L, 1); /* pathname ... iter state pathname */
diriter_setpathname(L, -2); /* pathname ... iter state */
return 2;
case LUA_TUSERDATA:
pi = luaL_checkudata(L, 1, DIR_HANDLE);
if (!nextfile(pi)) return 0;
pd = luaL_checkudata(L, 1, DIR_HANDLE);
do d = readdir(*pd);
while (d && isdotfile(d->cFileName));
if (!d) return push_error(L);
new_dirent(L); /* diriter ... entry */
diriter_getpathname(L, 1); /* diriter ... entry dirpath */
lua_pushstring(L, pi->fd.cFileName);/* diriter ... entry dirpath name */
lua_pushstring(L, d->cFileName); /* diriter ... entry dirpath name */
lua_pushvalue(L, -1); /* diriter ... entry dirpath name name */
lua_setfield(L, -4, "name"); /* diriter ... entry dirpath name */
lua_concat(L, 2); /* diriter ... entry fullpath */
@ -326,8 +320,7 @@ static int file_lock(lua_State *L, FILE *f, const char *mode, long offset, long
ret = flags ? LockFileEx(h, flags, 0, len.LowPart, len.HighPart, &ov)
: UnlockFileEx(h, 0, len.LowPart, len.HighPart, &ov);
if (!ret)
return windows_pushlasterror(L);
/* return the file */
return push_error(L);
lua_settop(L, 1);
return 1;
}
@ -351,33 +344,16 @@ static int ex_unlock(lua_State *L)
}
static int make_pipe(FILE **i, FILE **o)
/* -- in out/nil error */
static int ex_pipe(lua_State *L)
{
HANDLE ph[2];
if (0 == CreatePipe(ph+0, ph+1, 0, 0))
return 0;
if (!CreatePipe(ph + 0, ph + 1, 0, 0))
return push_error(L);
SetHandleInformation(ph[0], HANDLE_FLAG_INHERIT, 0);
SetHandleInformation(ph[1], HANDLE_FLAG_INHERIT, 0);
*i = _fdopen(_open_osfhandle((long)ph[0], _O_RDONLY), "r");
*o = _fdopen(_open_osfhandle((long)ph[1], _O_WRONLY), "w");
return 1;
}
#define new_file(L) lua_newuserdata(L, sizeof(FILE *))
/* -- in out/nil error */
static int ex_pipe(lua_State *L)
{
FILE *i, *o, **pf;
if (!make_pipe(&i, &o))
return windows_pushlasterror(L);
luaL_getmetatable(L, LUA_FILEHANDLE); /* M */
*(pf = new_file(L)) = i; /* M i */
lua_pushvalue(L, -2); /* M i M */
lua_setmetatable(L, -2); /* M i */
*(pf = new_file(L)) = o; /* M i o */
lua_pushvalue(L, -3); /* M i o M */
lua_setmetatable(L, -2); /* M i o */
new_file(L, ph[0], _O_RDONLY, "r");
new_file(L, ph[1], _O_WRONLY, "w");
return 2;
}
@ -386,7 +362,7 @@ static void get_redirect(lua_State *L, int idx, const char *stdname, struct spaw
{
lua_getfield(L, idx, stdname);
if (!lua_isnil(L, -1))
spawn_param_redirect(p, stdname, check_file(L, -1, stdname));
spawn_param_redirect(p, stdname, file_handle(check_file(L, -1, stdname)));
lua_pop(L, 1);
}
@ -456,6 +432,7 @@ static int ex_spawn(lua_State *L)
default: return luaL_error(L, "bad env option (table expected, got %s)",
luaL_typename(L, -1));
case LUA_TNIL:
break;
case LUA_TTABLE:
spawn_param_env(params); /* cmd opts ... */
break;
@ -468,11 +445,11 @@ static int ex_spawn(lua_State *L)
return spawn_param_execute(params); /* proc/nil error */
}
/* copy the fields given in 'l' from one table to another; insert missing fields */
static void copy_fields(lua_State *L, const luaL_reg *l, int from, int to)
{
to = absindex(L, to);
for (; l->name; l++) {
for (to = absindex(L, to); l->name; l++) {
lua_getfield(L, from, l->name);
if (lua_isnil(L, -1)) {
lua_pop(L, 1);
@ -533,6 +510,7 @@ int luaopen_ex(lua_State *L)
lua_getglobal(L, "io"); /* ex . io */
if (lua_isnil(L, -1)) return luaL_error(L, "io not loaded");
copy_fields(L, ex_iolib, 1, -1); /* ex . io */
copy_fields(L, ex_iofile_methods, 1, -1); /* ex . io */
lua_getfield(L, 1, "pipe"); /* ex . io ex_pipe */
lua_getfield(L, -2, "stderr"); /* ex . io ex_pipe io_stderr */
lua_getfenv(L, -1); /* ex . io ex_pipe io_stderr E */

@ -1,8 +1,8 @@
#ifndef pusherror_h
#define pusherror_h
#include <lua.h>
#include <windows.h>
#include "lua.h"
int windows_pusherror(lua_State *L, DWORD error, int nresults);
#define windows_pushlasterror(L) windows_pusherror(L, GetLastError(), -2)

@ -1,11 +1,10 @@
#include <stdlib.h>
#include <lua.h>
#include <lauxlib.h>
#include <windows.h>
#include <io.h>
#include "lua.h"
#include "lauxlib.h"
#include "spawn.h"
#include "pusherror.h"
@ -81,11 +80,6 @@ void spawn_param_env(struct spawn_params *p)
{
lua_State *L = p->L;
luaL_Buffer env;
if (lua_isnil(L, -1)) {
p->environment = 0;
lua_pop(L, 1);
return;
}
/* convert env table to zstring list */
/* {nam1=val1,nam2=val2} => "nam1=val1\0nam2=val2\0\0" */
luaL_buffinit(L, &env);
@ -108,9 +102,8 @@ void spawn_param_env(struct spawn_params *p)
p->environment = lua_tostring(L, -1);
}
void spawn_param_redirect(struct spawn_params *p, const char *stdname, FILE *f)
void spawn_param_redirect(struct spawn_params *p, const char *stdname, HANDLE h)
{
HANDLE h = file_handle(f);
SetHandleInformation(h, HANDLE_FLAG_INHERIT, HANDLE_FLAG_INHERIT);
if (!(p->si.dwFlags & STARTF_USESTDHANDLES)) {
p->si.hStdInput = GetStdHandle(STD_INPUT_HANDLE);

@ -1,8 +1,8 @@
#ifndef SPAWN_H
#define SPAWN_H
#include <lua.h>
#include <windows.h>
#include "lua.h"
#define PROCESS_HANDLE "process"
struct process;
@ -12,7 +12,7 @@ struct spawn_params *spawn_param_init(lua_State *L);
void spawn_param_filename(struct spawn_params *p, const char *filename);
void spawn_param_args(struct spawn_params *p);
void spawn_param_env(struct spawn_params *p);
void spawn_param_redirect(struct spawn_params *p, const char *stdname, FILE *f);
void spawn_param_redirect(struct spawn_params *p, const char *stdname, HANDLE h);
int spawn_param_execute(struct spawn_params *p);
int process_wait(lua_State *L);

Loading…
Cancel
Save