Jabber WindowGram Client (JWGC)

Introduction Screenshots Installation Downloads
Documentation Browse Source Resources Project Site

Stable Version
-none-

Latest Version
beta5



Main Page | Alphabetical List | Data Structures | Directories | File List | Data Fields | Globals

exec.c

Go to the documentation of this file.
00001 /*
00002  *      Copyright (c) 1989 by the Massachusetts Institute of Technology.
00003  *      For copying and distribution information, see the file
00004  *      "mit-copyright.h".
00005  *
00006  *      Modified for jwgc by Daniel Henninger.
00007  */
00008 
00009 #include "mit-copyright.h"
00010 
00011 /****************************************************************************/
00012 /* */
00013 /* Module containing code to execute a program:               */
00014 /* */
00015 /****************************************************************************/
00016 
00017 #include "main.h"
00018 #include "exec.h"
00019 #include "eval.h"
00020 #include "node.h"
00021 #include "buffer.h"
00022 #include "port.h"
00023 #include "variables.h"
00024 #include "notice.h"
00025 
00026 static int exec_subtree(), exec_fields();
00027 
00028 /****************************************************************************/
00029 /* */
00030 /* Utility subroutines:                          */
00031 /* */
00032 /****************************************************************************/
00033 
00034 static string 
00035 eval_exprlist_to_string(exprlist)
00036         Node *exprlist;
00037 {
00038         string result = string_Copy("");
00039         string temp;
00040         int first_time = 1;
00041 
00042         for (; exprlist; exprlist = exprlist->next) {
00043                 if (!first_time)
00044                         result = string_Concat2(result, " ");
00045                 else
00046                         first_time = 0;
00047 
00048                 temp = eval_expr(exprlist);
00049                 result = string_Concat2(result, temp);
00050                 free(temp);
00051         }
00052 
00053         return (result);
00054 }
00055 
00056 static char **
00057 eval_exprlist_to_args(exprlist)
00058         Node *exprlist;
00059 {
00060         char **result = (char **) malloc(sizeof(char *));
00061         int argc = 0;
00062 
00063         for (; exprlist; exprlist = exprlist->next) {
00064                 result[argc] = eval_expr(exprlist);
00065                 argc++;
00066                 result = (char **) realloc(result, (argc + 1) * sizeof(char *));
00067         }
00068 
00069         result[argc] = NULL;
00070         return (result);
00071 }
00072 
00073 static void 
00074 free_args(args)
00075         char **args;
00076 {
00077         char **p;
00078 
00079         for (p = args; *p; p++) {
00080                 free(*p);
00081         }
00082 
00083         free(args);
00084 }
00085 
00086 /****************************************************************************/
00087 /* */
00088 /* Subroutines to handle each particular statement type:           */
00089 /* */
00090 /****************************************************************************/
00091 
00092 #define  NOBREAK   0
00093 #define  BREAK     1
00094 #define  EXIT      2
00095 
00096 /* ARGSUSED */
00097 static int 
00098 exec_noop(node)
00099         Node *node;
00100 {
00101         return (NOBREAK);
00102 }
00103 
00104 /* ARGSUSED */
00105 static int 
00106 exec_break(node)
00107         Node *node;
00108 {
00109         return (BREAK);
00110 }
00111 
00112 /* ARGSUSED */
00113 static int 
00114 exec_exit(node)
00115         Node *node;
00116 {
00117         return (EXIT);
00118 }
00119 
00120 static int 
00121 exec_set(node)
00122         Node *node;
00123 {
00124         var_set_variable_then_free_value(node->d.nodes.first->d.string_constant,
00125                                          eval_expr(node->d.nodes.second));
00126 
00127         return (NOBREAK);
00128 }
00129 
00130 static int 
00131 exec_execport(node)
00132         Node *node;
00133 {
00134         string name = eval_expr(node->d.nodes.first);
00135         char **argv = eval_exprlist_to_args(node->d.nodes.second);
00136 
00137         create_subprocess_port(name, argv);
00138 
00139         free(name);
00140         free_args(argv);
00141         return (NOBREAK);
00142 }
00143 
00144 static int 
00145 exec_appendport(node)
00146         Node *node;
00147 {
00148         string name, filename;
00149 
00150         name = eval_expr(node->d.nodes.first);
00151         filename = eval_expr(node->d.nodes.second);
00152 
00153         create_file_append_port(name, filename);
00154 
00155         free(name);
00156         free(filename);
00157         return (NOBREAK);
00158 }
00159 
00160 static int 
00161 exec_inputport(node)
00162         Node *node;
00163 {
00164         string name, filename;
00165 
00166         name = eval_expr(node->d.nodes.first);
00167         filename = eval_expr(node->d.nodes.second);
00168 
00169         create_file_input_port(name, filename);
00170 
00171         free(name);
00172         free(filename);
00173         return (NOBREAK);
00174 }
00175 
00176 static int 
00177 exec_outputport(node)
00178         Node *node;
00179 {
00180         string name, filename;
00181 
00182         name = eval_expr(node->d.nodes.first);
00183         filename = eval_expr(node->d.nodes.second);
00184 
00185         create_file_output_port(name, filename);
00186 
00187         free(name);
00188         free(filename);
00189         return (NOBREAK);
00190 }
00191 
00192 static int 
00193 exec_closeinput(node)
00194         Node *node;
00195 {
00196         string name;
00197 
00198         name = eval_expr(node->d.nodes.first);
00199         close_port_input(name);
00200 
00201         free(name);
00202         return (NOBREAK);
00203 }
00204 
00205 static int 
00206 exec_closeoutput(node)
00207         Node *node;
00208 {
00209         string name;
00210 
00211         name = eval_expr(node->d.nodes.first);
00212         close_port_output(name);
00213 
00214         free(name);
00215         return (NOBREAK);
00216 }
00217 
00218 static int 
00219 exec_closeport(node)
00220         Node *node;
00221 {
00222         string name;
00223 
00224         name = eval_expr(node->d.nodes.first);
00225         close_port_input(name);
00226         close_port_output(name);
00227 
00228         free(name);
00229         return (NOBREAK);
00230 }
00231 
00232 static int 
00233 exec_put(node)
00234         Node *node;
00235 {
00236         string name, temp;
00237 
00238         if (node->d.nodes.second)
00239                 temp = eval_exprlist_to_string(node->d.nodes.second);
00240         else
00241                 temp = string_Copy(buffer_to_string());
00242 
00243         if (node->d.nodes.first) {
00244                 name = eval_expr(node->d.nodes.first);
00245 
00246                 write_on_port(name, temp, strlen(temp));
00247                 free(name);
00248         }
00249         else
00250                 write_on_port(var_get_variable("output_driver"), temp, strlen(temp));
00251 
00252         free(temp);
00253         return (NOBREAK);
00254 }
00255 
00256 static int 
00257 exec_print(node)
00258         Node *node;
00259 {
00260         string temp;
00261 
00262         temp = eval_exprlist_to_string(node->d.nodes.first);
00263         append_buffer(temp);
00264         free(temp);
00265 
00266         return (NOBREAK);
00267 }
00268 
00269 /* ARGSUSED */
00270 static int 
00271 exec_clearbuf(node)
00272         Node *node;
00273 {
00274         clear_buffer();
00275 
00276         return (NOBREAK);
00277 }
00278 
00279 static int 
00280 exec_case(node)
00281         Node *node;
00282 {
00283         string constant, temp;
00284         Node *match, *cond;
00285         int equal_p;
00286 
00287         constant = string_Downcase(eval_expr(node->d.nodes.first));
00288 
00289         for (match = node->d.nodes.second; match; match = match->next) {
00290                 cond = match->d.nodes.first;
00291                 if (!cond) {    /* default case */
00292                         free(constant);
00293                         return (exec_subtree(match->d.nodes.second));
00294                 }
00295                 for (; cond; cond = cond->next) {
00296                         temp = string_Downcase(eval_expr(cond));
00297                         equal_p = string_Eq(constant, temp);
00298                         free(temp);
00299                         if (equal_p) {
00300                                 free(constant);
00301                                 return (exec_subtree(match->d.nodes.second));
00302                         }
00303                 }
00304         }
00305 
00306         free(constant);
00307         return (NOBREAK);
00308 }
00309 
00310 static int 
00311 exec_while(node)
00312         Node *node;
00313 {
00314         int continue_code = NOBREAK;
00315 
00316         while (eval_bool_expr(node->d.nodes.first)) {
00317                 continue_code = exec_subtree(node->d.nodes.second);
00318                 if (continue_code != NOBREAK)
00319                         break;
00320         }
00321 
00322         if (continue_code == BREAK)
00323                 continue_code = NOBREAK;
00324 
00325         return (continue_code);
00326 }
00327 
00328 static int 
00329 exec_if(node)
00330         Node *node;
00331 {
00332         Node *conds;
00333 
00334         for (conds = node->d.nodes.first; conds; conds = conds->next)
00335                 if (eval_bool_expr(conds->d.nodes.first))
00336                         return (exec_subtree(conds->d.nodes.second));
00337 
00338         return (NOBREAK);
00339 }
00340 
00341 static int 
00342 exec_exec(node)
00343         Node *node;
00344 {
00345         int pid;
00346         char **argv = eval_exprlist_to_args(node->d.nodes.first);
00347 
00348         pid = fork();
00349         if (pid == -1) {
00350                 fprintf(stderr, "jwgc: error while attempting to fork: ");
00351                 perror("");
00352         }
00353         else if (pid == 0) {    /* in child */
00354                 execvp(argv[0], argv);
00355                 fprintf(stderr, "jwgc: unable to exec %s: ", argv[0]);
00356                 perror("");
00357                 _exit(errno);
00358         }
00359 
00360         free_args(argv);
00361         return (NOBREAK);
00362 }
00363 
00364 static struct _Opstuff {
00365         int (*exec) ();
00366 } const opstuff[] = {
00367         {exec_noop},            /* string_constant */
00368         {exec_noop},            /* varref */
00369         {exec_noop},            /* varname */
00370         {exec_noop},            /* not */
00371         {exec_noop},            /* plus */
00372         {exec_noop},            /* and */
00373         {exec_noop},            /* or */
00374         {exec_noop},            /* eq */
00375         {exec_noop},            /* neq */
00376         {exec_noop},            /* regeq */
00377         {exec_noop},            /* regneq */
00378         {exec_noop},            /* buffer */
00379         {exec_noop},            /* substitute */
00380         {exec_noop},            /* protect */
00381         {exec_noop},            /* verbatim */
00382         {exec_noop},            /* getenv */
00383         {exec_noop},            /* upcase */
00384         {exec_noop},            /* downcase */
00385         {exec_noop},            /* jvar */
00386         {exec_noop},            /* get */
00387         {exec_noop},            /* lany */
00388         {exec_noop},            /* rany */
00389         {exec_noop},            /* lbreak */
00390         {exec_noop},            /* rbreak */
00391         {exec_noop},            /* lspan */
00392         {exec_noop},            /* rspan */
00393         {exec_noop},            /* paragraph */
00394 
00395         {exec_noop},            /* noop statement */
00396         {exec_set},
00397         {exec_fields},
00398 
00399         {exec_print},
00400         {exec_clearbuf},
00401 
00402         {exec_appendport},
00403         {exec_execport},
00404         {exec_inputport},
00405         {exec_outputport},
00406         {exec_put},
00407         {exec_closeinput},
00408         {exec_closeoutput},
00409         {exec_closeport},
00410 
00411         {exec_exec},
00412 
00413         {exec_if},
00414         {exec_case},
00415         {exec_while},
00416         {exec_break},
00417         {exec_exit},
00418 
00419         {exec_noop},            /* if */
00420         {exec_noop},            /* elseif */
00421         {exec_noop},            /* else */
00422         {exec_noop},            /* matchlist */
00423         {exec_noop},            /* default */
00424 };
00425 
00426 static int 
00427 exec_subtree(node)
00428         Node *node;
00429 {
00430         int retval = NOBREAK;
00431 
00432         for (; node; node = node->next) {
00433                 retval = (opstuff[node->opcode].exec) (node);
00434                 if (retval != NOBREAK)
00435                         return (retval);
00436         }
00437 
00438         return (NOBREAK);
00439 }
00440 
00441 /***************************************************************************/
00442 
00443 static char *notice_fields;
00444 static int notice_fields_length = 0;
00445 static int number_of_fields = 0;
00446 
00447 static int 
00448 exec_fields(node)
00449         Node *node;
00450 {
00451         for (node = node->d.nodes.first; node; node = node->next) {
00452                 var_set_variable_then_free_value(node->d.string_constant,
00453                                               get_next_field(&notice_fields,
00454                                                     &notice_fields_length));
00455                 if (number_of_fields)
00456                         number_of_fields--;
00457         }
00458 
00459         var_set_variable_to_number("number_of_fields", number_of_fields);
00460 
00461         return (NOBREAK);
00462 }
00463 
00464 void 
00465 exec_process_packet(program, notice, body, body_sz)
00466         Node *program;
00467         struct jpacket_struct *notice;
00468         char *body;
00469         int body_sz;
00470 {
00471         notice_fields = body;
00472         notice_fields_length = body_sz;
00473 
00474         var_set_number_variables_to_fields(notice_fields, notice_fields_length);
00475 
00476         number_of_fields = count_nulls(notice_fields, notice_fields_length) + 1;
00477         /* workaround for bug in old zwrite */
00478         if (notice_fields[notice_fields_length - 1] == '\0')
00479                 number_of_fields--;
00480         var_set_variable_to_number("number_of_fields", number_of_fields);
00481 
00482         clear_buffer();
00483         (void) exec_subtree(program);
00484 }


Last updated at Tue Dec 18 21:07:42 PST 2007. This site and project hosted by...SourceForge.net Logo
Source Perspective by Fisheye