2 -- Copyright (C) 2008-2009 Matthew Wild
3 -- Copyright (C) 2008-2009 Waqas Hussain
5 -- This project is MIT/X11 licensed. Please see the
6 -- COPYING file in the source package for more information.
12 * POSIX support functions for Lua
15 #define MODULE_VERSION "0.3.0"
20 #include <sys/types.h>
32 /* Daemonization support */
34 static int lc_daemonize(lua_State *L)
41 lua_pushboolean(L, 0);
42 lua_pushstring(L, "already-daemonized");
46 /* Attempt initial fork */
47 if((pid = fork()) < 0)
50 lua_pushboolean(L, 0);
51 lua_pushstring(L, "fork-failed");
56 /* We are the parent process */
57 lua_pushboolean(L, 1);
58 lua_pushnumber(L, pid);
62 /* and we are the child process */
65 /* We failed to become session leader */
66 /* (we probably already were) */
67 lua_pushboolean(L, 0);
68 lua_pushstring(L, "setsid-failed");
72 /* Close stdin, stdout, stderr */
77 /* Final fork, use it wisely */
81 /* Show's over, let's continue */
82 lua_pushboolean(L, 1);
89 const char * const facility_strings[] = {
111 int facility_constants[] = {
136 The parameter ident in the call of openlog() is probably stored as-is.
137 Thus, if the string it points to is changed, syslog() may start
138 prepending the changed string, and if the string it points to ceases to
139 exist, the results are undefined. Most portable is to use a string
143 char* syslog_ident = NULL;
145 int lc_syslog_open(lua_State* L)
147 int facility = luaL_checkoption(L, 2, "daemon", facility_strings);
148 facility = facility_constants[facility];
150 luaL_checkstring(L, 1);
155 syslog_ident = strdup(lua_tostring(L, 1));
157 openlog(syslog_ident, LOG_PID, facility);
161 const char * const level_strings[] = {
169 int level_constants[] = {
177 int lc_syslog_log(lua_State* L)
179 int level = luaL_checkoption(L, 1, "notice", level_strings);
180 level = level_constants[level];
182 luaL_checkstring(L, 2);
184 syslog(level, "%s", lua_tostring(L, 2));
188 int lc_syslog_close(lua_State* L)
199 int lc_syslog_setmask(lua_State* L)
201 int level_idx = luaL_checkoption(L, 1, "notice", level_strings);
205 mask |= LOG_MASK(level_constants[level_idx]);
206 } while (++level_idx<=4);
214 int lc_getpid(lua_State* L)
216 lua_pushinteger(L, getpid());
220 /* UID/GID functions */
222 int lc_getuid(lua_State* L)
224 lua_pushinteger(L, getuid());
228 int lc_getgid(lua_State* L)
230 lua_pushinteger(L, getgid());
234 int lc_setuid(lua_State* L)
237 if(lua_gettop(L) < 1)
239 if(!lua_isnumber(L, 1) && lua_tostring(L, 1))
241 /* Passed UID is actually a string, so look up the UID */
243 p = getpwnam(lua_tostring(L, 1));
246 lua_pushboolean(L, 0);
247 lua_pushstring(L, "no-such-user");
254 uid = lua_tonumber(L, 1);
259 /* Ok, attempt setuid */
264 lua_pushboolean(L, 0);
268 lua_pushstring(L, "invalid-uid");
271 lua_pushstring(L, "permission-denied");
274 lua_pushstring(L, "unknown-error");
281 lua_pushboolean(L, 1);
286 /* Seems we couldn't find a valid UID to switch to */
287 lua_pushboolean(L, 0);
288 lua_pushstring(L, "invalid-uid");
292 /* Register functions */
294 int luaopen_util_pposix(lua_State *L)
298 lua_pushcfunction(L, lc_daemonize);
299 lua_setfield(L, -2, "daemonize");
301 lua_pushcfunction(L, lc_syslog_open);
302 lua_setfield(L, -2, "syslog_open");
304 lua_pushcfunction(L, lc_syslog_close);
305 lua_setfield(L, -2, "syslog_close");
307 lua_pushcfunction(L, lc_syslog_log);
308 lua_setfield(L, -2, "syslog_log");
310 lua_pushcfunction(L, lc_syslog_setmask);
311 lua_setfield(L, -2, "syslog_setminlevel");
313 lua_pushcfunction(L, lc_getpid);
314 lua_setfield(L, -2, "getpid");
316 lua_pushcfunction(L, lc_getuid);
317 lua_setfield(L, -2, "getuid");
319 lua_pushcfunction(L, lc_setuid);
320 lua_setfield(L, -2, "setuid");
322 lua_pushliteral(L, "pposix");
323 lua_setfield(L, -2, "_NAME");
325 lua_pushliteral(L, MODULE_VERSION);
326 lua_setfield(L, -2, "_VERSION");