diff options
author | Daniel Silverstone <dsilvers@digital-scurf.org> | 2012-09-12 11:30:50 +0100 |
---|---|---|
committer | Daniel Silverstone <dsilvers@digital-scurf.org> | 2012-09-12 11:30:50 +0100 |
commit | 9015b9fd70e9d8a7215af131ebf950479c64a47c (patch) | |
tree | c5f05a0228d4729bf7ea4e9b44a73a646318e1dd | |
parent | 1bdbe528d4050d770e76b5a166e324ef6ce39d35 (diff) | |
download | luxio-9015b9fd70e9d8a7215af131ebf950479c64a47c.tar.gz |
Add prefork and preexec support to luxio.subprocess.spawn
-rw-r--r-- | luxio/subprocess.lua | 33 |
1 files changed, 32 insertions, 1 deletions
diff --git a/luxio/subprocess.lua b/luxio/subprocess.lua index 3da5993..617d20b 100644 --- a/luxio/subprocess.lua +++ b/luxio/subprocess.lua @@ -48,6 +48,13 @@ -- If you want to change directory before exec in the child, you can pass -- cwd="/some/path". -- +-- To run some code before forking, pass prefork=somefunction and to +-- run code before exec (in the child) pass preexec=somefunction. +-- +-- If the prefork function raises an error then the spawn will be stopped and +-- the error propagated. If the preexec function raises an error then the exec +-- will be stopped and the child will exit with status code 1. +-- -- spawn_simple has one additional tweak. If 'stdin' is provided as -- a string then it will automatically write that string to the stdin -- of the child (and close the FD afterwards) for you automatically. @@ -100,6 +107,7 @@ local stderr_fh = sio.stderr local setenv = l.setenv local unsetenv = l.unsetenv local _exit = l._exit +local _TRACEBACK = debug.traceback local F_SETFD = l.F_SETFD local F_GETFD = l.F_GETFD @@ -236,6 +244,21 @@ local function _spawn(t) -- Finally, let's fork + if proc.args.prefork then + local ok, msg = xpcall(proc.args.prefork, function(...) + for fd in pairs(parent_close) do + close(fd) + end + for fd in pairs(child_close) do + close(fd) + end + return _TRACEBACK(...) + end) + if not ok then + error(msg) + end + end + local pid, errno = fork() _assert(pid > -1, "Unable to fork()") @@ -305,7 +328,15 @@ local function _spawn(t) local cwd = tostring(proc.args.cwd) local ret, err = chdir(cwd) if ret ~= 0 then - stderr_fh:write("chdir(" .. cwd .. "): " .. err) + stderr_fh:write("chdir(" .. cwd .. "): " .. err .. "\n") + _exit(1) + end + end + + if proc.args.preexec then + local ok, msg = xpcall(proc.args.preexec, _TRACEBACK) + if not ok then + stderr_fh:write(msg .. "\n") _exit(1) end end |