+static void
+send_mail(char* where, int copy, struct list* hash)
+{
+ int pd[2];
+ int pid, status;
+ int res;
+ struct email em = prepare_email(hash);
+
+ res = pipe(pd);
+ if (res < 0)
+ goto end;
+
+ if ((pid = fork()) < 0)
+ goto end;
+ else if (pid == 0) {
+ close(0);
+ dup(pd[0]);
+ close(pd[0]);
+ //FIXME From?
+ res = execl("/usr/lib/sendmail", "sendmail", where, NULL);
+ }
+ close(pd[0]);
+ write_email_to_fd(pd[1], &em);
+ close(pd[1]);
+ wait(&status);
+end:
+ destroy_email(em);
+ if (!copy) {
+ if (res)
+ bye(EX_TEMPFAIL, "%m");
+ else
+ bye(0, NULL);
+ }
+}
+
+void
+interp(struct list* ins, struct list* hash)
+{
+ struct code* p;
+ char* result;
+ int v;
+
+ LIST_FOREACH(p, ins) {
+ switch (p->opcode) {
+ case OPC_SET:
+ set_var(p->u.set.l, get_var(p->u.set.r));
+ break;
+ case OPC_JUMP:
+ p = p->u.jump.target;
+ continue;
+ break;
+ case OPC_JUMP_IF:
+ if (eval_cond(p->u.jump_if.cond))
+ p = p->u.jump_if.target;
+ continue;
+ break;
+ case OPC_JUMP_UNLESS:
+ if (!eval_cond(p->u.jump_unless.cond))
+ p = p->u.jump_unless.target;
+ continue;
+ break;
+ case OPC_NOP:
+ continue;
+ break;
+ case OPC_GT:
+ case OPC_LT:
+ case OPC_LE:
+ case OPC_GE:
+ case OPC_EQ:
+ case OPC_NEQ:
+ case OPC_AND:
+ case OPC_OR:
+ case OPC_XOR:
+ case OPC_PLUS:
+ case OPC_MINUS:
+ case OPC_MUL:
+ case OPC_DIV:
+ do_num_ternary_op(p);
+ break;
+ case OPC_NOT:
+ result = xmalloc(INT_TO_STRING_LEN);
+ sscanf(get_var(p->u.tpop.l),"%d", &v);
+ sprintf(result, "%d", !v);
+ set_var(p->u.tpop.res, result);
+ case OPC_CAT:
+ case OPC_RE:
+ case OPC_NRE:
+ do_string_ternary_op(p);
+ break;
+ case OPC_PIPE:
+ break;
+ case OPC_MAIL:
+ send_mail(get_var(p->u.arrow.what),
+ p->u.arrow.copy, hash);
+ break;
+ case OPC_DELIVER:
+ deliver(get_var(p->u.arrow.what),
+ p->u.arrow.copy, hash);
+ break;
+ case OPC_CALL_EXT:
+ break;
+ case OPC_DISCARD:
+ bye(0, NULL);
+ break;
+ }}
+ deliver(default_mailbox, 0, hash);
+}
+
+void
+print_vars(struct list* hash)
+{
+ int i;
+ struct variable* p;
+
+ for (i=0; i<HASHSIZE; i++){
+ LIST_FOREACH(p, hash + i)
+ printf("%s=%s\n",p->name, get_var(p->varcode));
+ }