"Fossies" - the Fresh Open Source Software Archive

Member "imapfilter-2.8.2/src/system.c" (26 Dec 2023, 5700 Bytes) of package /linux/privat/imapfilter-2.8.2.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "system.c" see the Fossies "Dox" file reference documentation and the last Fossies "Diffs" side-by-side code changes report: 2.8.0_vs_2.8.1.

    1 #include <stdio.h>
    2 #include <stdlib.h>
    3 #include <unistd.h>
    4 #include <string.h>
    5 #include <errno.h>
    6 #include <fcntl.h>
    7 #include <sys/types.h>
    8 #include <termios.h>
    9 
   10 #include <lua.h>
   11 #include <lauxlib.h>
   12 #include <lualib.h>
   13 
   14 #include "imapfilter.h"
   15 
   16 
   17 static int ifsys_echo(lua_State *lua);
   18 static int ifsys_noecho(lua_State *lua);
   19 static int ifsys_popen(lua_State *lua);
   20 static int ifsys_pclose(lua_State *lua);
   21 static int ifsys_read(lua_State *lua);
   22 static int ifsys_write(lua_State *lua);
   23 static int ifsys_sleep(lua_State *lua);
   24 static int ifsys_daemon(lua_State *lua);
   25 
   26 /* Lua imapfilter library of system's functions. */
   27 static const luaL_Reg ifsyslib[] = {
   28     { "echo", ifsys_echo },
   29     { "noecho", ifsys_noecho },
   30     { "popen", ifsys_popen },
   31     { "pclose", ifsys_pclose },
   32     { "read", ifsys_read },
   33     { "write", ifsys_write },
   34     { "sleep", ifsys_sleep },
   35     { "daemon", ifsys_daemon },
   36     { NULL, NULL }
   37 };
   38 
   39 
   40 /*
   41  * Enable character echoing.
   42  */
   43 static int
   44 ifsys_echo(lua_State *lua)
   45 {
   46     struct termios t;
   47 
   48     if (lua_gettop(lua) != 0)
   49         luaL_error(lua, "wrong number of arguments");
   50 
   51     if (tcgetattr(fileno(stdin), &t)) {
   52         fprintf(stderr, "getting term attributs; %s\n",
   53             strerror(errno));
   54         return 1;
   55     }
   56 
   57     t.c_lflag |= (ECHO);
   58     t.c_lflag &= ~(ECHONL);
   59 
   60     if (tcsetattr(fileno(stdin), TCSAFLUSH, &t)) {
   61         fprintf(stderr, "setting term attributes; %s\n",
   62             strerror(errno));
   63         return 1;
   64     }
   65 
   66     return 0;
   67 }
   68 
   69 
   70 /*
   71  * Disable character echoing.
   72  */
   73 static int
   74 ifsys_noecho(lua_State *lua)
   75 {
   76     struct termios t;
   77 
   78     if (lua_gettop(lua) != 0)
   79         luaL_error(lua, "wrong number of arguments");
   80 
   81     if (tcgetattr(fileno(stdin), &t)) {
   82         fprintf(stderr, "getting term attributs; %s\n",
   83             strerror(errno));
   84         return 1;
   85     }
   86 
   87     t.c_lflag &= ~(ECHO);
   88     t.c_lflag |= (ECHONL);
   89 
   90     if (tcsetattr(fileno(stdin), TCSAFLUSH, &t)) {
   91         fprintf(stderr, "setting term attributes; %s\n",
   92             strerror(errno));
   93         return 1;
   94     }
   95 
   96     return 0;
   97 }
   98 
   99 
  100 /*
  101  * Lua implementation of the POSIX popen() function.
  102  */
  103 static int
  104 ifsys_popen(lua_State *lua)
  105 {
  106     FILE **fp;
  107 
  108     if (lua_gettop(lua) != 2)
  109         luaL_error(lua, "wrong number of arguments");
  110     luaL_checktype(lua, 1, LUA_TSTRING);
  111     luaL_checktype(lua, 2, LUA_TSTRING);
  112 
  113 #if LUA_VERSION_NUM < 504
  114     fp = (FILE **) lua_newuserdata(lua, sizeof(FILE *));
  115 #else
  116     fp = (FILE **) lua_newuserdatauv(lua, sizeof(FILE *), 1);
  117 #endif
  118 
  119     *fp = NULL;
  120 
  121     *fp = popen(lua_tostring(lua, 1), lua_tostring(lua, 2));
  122 
  123     lua_remove(lua, 1);
  124     lua_remove(lua, 1);
  125 
  126     return (*fp == NULL ? 0 : 1);
  127 }
  128 
  129 
  130 /*
  131  * Lua implementation of the POSIX pclose() function.
  132  */
  133 static int
  134 ifsys_pclose(lua_State *lua)
  135 {
  136     lua_Number r;
  137     FILE *fp;
  138 
  139     if (lua_gettop(lua) != 1)
  140         luaL_error(lua, "wrong number of arguments");
  141     luaL_checktype(lua, 1, LUA_TUSERDATA);
  142 
  143     fp = *(FILE **) (lua_touserdata(lua, 1));
  144 
  145     r = (lua_Number) (pclose(fp) >> 8);
  146 
  147     lua_pop(lua, 1);
  148 
  149     if (r == -1)
  150         return 0;
  151 
  152     fp = NULL;
  153     lua_pushnumber(lua, r);
  154 
  155     return 1;
  156 }
  157 
  158 
  159 /*
  160  * Reads a line from a file stream.
  161  */
  162 static int
  163 ifsys_read(lua_State *lua)
  164 {
  165     FILE *fp;
  166     luaL_Buffer b;
  167     char *c;
  168     size_t n;
  169 
  170     if (lua_gettop(lua) != 1)
  171         luaL_error(lua, "wrong number of arguments");
  172     luaL_checktype(lua, 1, LUA_TUSERDATA);
  173 
  174     fp = *(FILE **) (lua_touserdata(lua, 1));
  175 
  176     lua_pop(lua, 1);
  177 
  178     luaL_buffinit(lua, &b);
  179 
  180     for (;;) {
  181         c = luaL_prepbuffer(&b);
  182 
  183         if (fgets(c, LUAL_BUFFERSIZE, fp) == NULL && feof(fp)) {
  184             luaL_pushresult(&b);
  185 
  186             return (
  187 #if LUA_VERSION_NUM < 502
  188                 lua_objlen(lua, -1)
  189 #else
  190                 lua_rawlen(lua, -1)
  191 #endif
  192                 > 0);
  193         }
  194         n = strlen(c);
  195 
  196         if (c[n - 1] != '\n')
  197             luaL_addsize(&b, n);
  198         else {
  199             luaL_addsize(&b, n);
  200             luaL_pushresult(&b);
  201 
  202             return 1;
  203         }
  204     }
  205 }
  206 
  207 
  208 /*
  209  * Writes a string to a file stream.
  210  */
  211 static int
  212 ifsys_write(lua_State *lua)
  213 {
  214     size_t n;
  215 
  216     if (lua_gettop(lua) != 2)
  217         luaL_error(lua, "wrong number of arguments");
  218     luaL_checktype(lua, 1, LUA_TUSERDATA);
  219     luaL_checktype(lua, 2, LUA_TSTRING);
  220 
  221     n = fwrite(lua_tostring(lua, 2), sizeof(char), strlen(lua_tostring(lua,
  222         2)), *(FILE **) (lua_touserdata(lua, 1)));
  223 
  224     lua_pop(lua, 2);
  225 
  226     lua_pushboolean(lua, (n != 0));
  227 
  228     return 1;
  229 }
  230 
  231 
  232 /*
  233  * Lua implementation of the POSIX sleep() function.
  234  */
  235 static int
  236 ifsys_sleep(lua_State *lua)
  237 {
  238 
  239     if (lua_gettop(lua) != 1)
  240         luaL_error(lua, "wrong number of arguments");
  241     luaL_checktype(lua, 1, LUA_TNUMBER);
  242 
  243     lua_pushnumber(lua,
  244         (lua_Number) (sleep) ((unsigned int)(lua_tonumber(lua, 1))));
  245 
  246     lua_remove(lua, 1);
  247 
  248     return 1;
  249 }
  250 
  251 
  252 /*
  253  * Lua implementation of the BSD daemon() function.
  254  */
  255 static int
  256 ifsys_daemon(lua_State *lua)
  257 {
  258     int fd;
  259 
  260     if (lua_gettop(lua) != 2)
  261         luaL_error(lua, "wrong number of arguments");
  262     luaL_checktype(lua, 1, LUA_TBOOLEAN);
  263     luaL_checktype(lua, 2, LUA_TBOOLEAN);
  264 
  265     switch (fork()) {
  266     case -1:
  267         fprintf(stderr, "forking; %s\n", strerror(errno));
  268         lua_pushboolean(lua, 0);
  269         return 1;
  270         /* NOTREACHED */
  271         break;
  272     case 0:
  273         break;
  274     default:
  275         exit(0);
  276         /* NOTREACHED */
  277         break;
  278     }
  279 
  280     if (setsid() == -1) {
  281         fprintf(stderr, "creating session; %s\n", strerror(errno));
  282     }
  283 
  284     if (lua_toboolean(lua, 1) == 0)
  285         if (chdir("/") == -1)
  286             fprintf(stderr, "changing working directory; %s\n",
  287                 strerror(errno));
  288 
  289     if (lua_toboolean(lua, 2) == 0) {
  290         if ((fd = open("/dev/null", O_RDWR)) == -1 ||
  291             dup2(fd, STDIN_FILENO) == -1 ||
  292             dup2(fd, STDOUT_FILENO) == -1 ||
  293             dup2(fd, STDERR_FILENO) == -1)
  294             fprintf(stderr, "duplicating file descriptors; %s\n",
  295                 strerror(errno));
  296     }
  297 
  298     write_pidfile();
  299 
  300     return 0;
  301 }
  302 
  303 
  304 /*
  305  * Open imapfilter library of system's functions.
  306  */
  307 LUALIB_API int
  308 luaopen_ifsys(lua_State *lua)
  309 {
  310 
  311 #if LUA_VERSION_NUM < 502
  312     luaL_register(lua, "ifsys", ifsyslib);
  313 #else
  314     luaL_newlib(lua, ifsyslib);
  315     lua_setglobal(lua, "ifsys");
  316 
  317 #endif
  318 
  319     return 1;
  320 }