int cli_main(int argc, char* argv[]) { nistp224key sec; nistp224key pub; obuf out; str str = {0,0,0}; const char* home; const char* keypath; uskey_path = "secret"; upkey_path = "public"; if (argc > 0) keypath = argv[0]; else { if ((home = getenv("HOME")) == 0) die1(1, "$HOME is not set."); if (chdir(home) != 0) die3sys(1, "Could not change directory to '", home, "'"); mkdir(".srcmd", 0700); keypath = ".srcmd/key"; } mkdir(keypath, 0755); if (chdir(keypath) != 0) die3sys(1, "Could not chdir to '", keypath, "'"); random_key(sec); nistp224wrap(pub, BASEP224, sec); base64_encode_line(sec, sizeof sec, &str); if (!obuf_open(&out, uskey_path, OBUF_CREATE|OBUF_EXCLUSIVE, 0400, 0) || !obuf_putstr(&out, &str) || !obuf_putc(&out, '\n') || !obuf_close(&out)) die3sys(1, "Could not create secret key file '", uskey_path, "'"); str_truncate(&str, 0); base64_encode_line(pub, sizeof pub, &str); if (!obuf_open(&out, upkey_path, OBUF_CREATE|OBUF_EXCLUSIVE, 0444, 0) || !obuf_putstr(&out, &str) || !obuf_putc(&out, '\n') || !obuf_close(&out)) die3sys(1, "Could not create public key file '", upkey_path, "'"); msg3("Your public key is '", str.s, "'"); return 0; argc = 1; }
int main(int argc, char* argv[]) { const char* dir; int fd; struct stat s; char fdstr[32]; if (argc < 2) die1(1, "usage: relay-ctrl-chdir program [arguments]\n"); if ((dir = getenv("RELAY_CTRL_DIR")) == 0) die1(111, "$RELAY_CTRL_DIR is not set."); else if ((fd = open(dir, O_RDONLY)) == -1) die3sys(111, "Could not open dir '", dir, "'"); else if (fstat(fd, &s) == -1) die1sys(111, "Could not stat opened file"); else if (!S_ISDIR(s.st_mode)) die3(111, "'", dir, "' is not a directory"); else { fd = move_high(fd); utoa2(fd, fdstr); if (setenv("RELAY_CTRL_DIR_FD", fdstr, 1) == -1) die1(111, "Could not set environment variable"); } execvp(argv[1], argv+1); die1(111, "execution of program failed!\n"); return 111; argc = 0; }
static int fixup(int fd) { int pid; int status; int newfd; if (fixup_argv != 0) { if (lseek(fd, 0, SEEK_SET) != 0) respond("ZCould not seek in temporary file"); if ((newfd = tempfile("tmp/spool")) == -1) respond("ZCould not create temporary file"); if ((pid = fork()) == -1) respond("ZCould not fork fixup program"); if (pid == 0) { dup2(fd, 0); close(fd); dup2(newfd, 1); close(newfd); execvp(fixup_argv[0], fixup_argv); die3sys(111, "Could not exec '", fixup_argv[0], "'"); } if (waitpid(pid, &status, 0) != pid) respond("ZWaitpid failed"); if (status != 0) respond("ZFilter failed"); fd = newfd; } return fd; }
static void exec_cmd(int fdin, int fdout, const char** argv, const str* env, const struct passwd* pw) { selfpipe_close(); dup2(fdin, 0); dup2(fdout, 1); dup2(fdout, 2); close(fdin); close(fdout); if (!testmode) { if (initgroups(pw->pw_name, pw->pw_gid) != 0) die1sys(111, "Could not initgroups"); if (setgid(pw->pw_gid) != 0) die1sys(111, "Could not setgid"); if (setuid(pw->pw_uid) != 0) die1sys(111, "Could not setuid"); } if (chdir(pw->pw_dir) != 0) die1sys(111, "Could not change directory"); if (env) if ((environ = envstr_make_array(env)) == 0) die_oom(111); execv(argv[0], (char**)argv); die3sys(111, "Could not execute '", argv[0], "'"); exit(111); }
void scan_info(const char* filename) { struct stat statbuf; char infoname[100]; time_t expiry; int fd; unsigned i; strcpy(infoname, "info/"); strcpy(infoname+5, filename); if((fd = open(infoname, O_RDONLY)) == -1 || fstat(fd, &statbuf) == -1) { /* This could race with qmail-clean, ignore missing files. */ if (errno == ENOENT) return; die3sys(111, "Can't open or stat info file '", infoname, "'"); } /* Handle the file only if it's expiry time (creation time + opt_age) is before now and after the last run */ for (i = 0; i < opt_age_count; ++i) { expiry = statbuf.st_mtime + opt_ages[i]; debug4(1, "filename=", filename, " expiry=", utoa(expiry)); if(expiry > now) debug1(1, "ignoring, has not yet expired"); else if(expiry <= lastrun) { debug1(1, "ignoring, was previously expired"); break; } else { /* Load the sender address from the info file */ char* sender = malloc(statbuf.st_size); if (read(fd, sender, statbuf.st_size) != statbuf.st_size) die3sys(111, "Reading from info file '", infoname, "' failed"); if(check_rcpt(sender+1)) make_bounce(sender+1, filename, opt_ages[i]); else debug2(1, "ignoring, sender was not in rcpthosts: ", sender+1); free(sender); break; } } close(fd); }
void ministat(const char* path, struct ministat* s) { struct stat st; if (stat(path, &st) != 0) { if (errno == ENOENT) memset(s, 0, sizeof *s); else die3sys(111, "Could not stat '", path, "'"); } else copystat(s, &st); }
static void respond(const char* msg) { obuf_putnetstring(&outbuf, msg, strlen(msg)); obuf_flush(&outbuf); switch (msg[0]) { case 'K': exit(0); case 'Z': die3sys(111, username, ": ", msg + 1); default: die3(100, username, ": ", msg + 1); } }
char* read_file(const char* prefix, const char* filename) { struct stat statbuf; char* data; int fd = open_file(prefix, filename); if(fd == -1 || fstat(fd, &statbuf) == -1) { data = malloc(1); data[0] = 0; } else { data = malloc(statbuf.st_size+1); if (read(fd, data, statbuf.st_size) != statbuf.st_size) die3sys(111, "Could not read data from '", filename, "'"); data[statbuf.st_size] = 0; } close(fd); return data; }
void wrap_chdir(const char* dir) { if (chdir(dir) != 0) die3sys(wrap_exit, "Could not chdir to '", dir, "'"); }