--- embedaddon/sudo/plugins/sudoers/iolog.c 2013/07/22 10:46:12 1.1.1.4 +++ embedaddon/sudo/plugins/sudoers/iolog.c 2013/10/14 07:56:34 1.1.1.5 @@ -50,6 +50,7 @@ #endif #include "sudoers.h" +#include "iolog.h" struct script_buf { int len; /* buffer length (how much read in) */ @@ -73,39 +74,6 @@ struct iolog_details { int cols; }; -union io_fd { - FILE *f; -#ifdef HAVE_ZLIB_H - gzFile g; -#endif - void *v; -}; - -static struct io_log_file { - bool enabled; - const char *suffix; - union io_fd fd; -} io_log_files[] = { -#define IOFD_LOG 0 - { true, "/log" }, -#define IOFD_TIMING 1 - { true, "/timing" }, -#define IOFD_STDIN 2 - { false, "/stdin" }, -#define IOFD_STDOUT 3 - { false, "/stdout" }, -#define IOFD_STDERR 4 - { false, "/stderr" }, -#define IOFD_TTYIN 5 - { false, "/ttyin" }, -#define IOFD_TTYOUT 6 - { false, "/ttyout" }, -#define IOFD_MAX 7 - { false, NULL } -}; - -#define SESSID_MAX 2176782336U - static int iolog_compress; static struct timeval last_time; static unsigned int sessid_max = SESSID_MAX; @@ -330,11 +298,8 @@ open_io_fd(char *pathbuf, size_t len, struct io_log_fi #endif iol->fd.f = fdopen(fd, "w"); } - if (fd == -1 || iol->fd.v == NULL) { + if (fd == -1 || iol->fd.v == NULL) log_fatal(USE_ERRNO, N_("unable to create %s"), pathbuf); - if (fd != -1) - close(fd); - } } else { /* Remove old log file if we recycled sequence numbers. */ unlink(pathbuf); @@ -352,9 +317,10 @@ iolog_deserialize_info(struct iolog_details *details, { const char *runas_uid_str = "0", *runas_euid_str = NULL; const char *runas_gid_str = "0", *runas_egid_str = NULL; - char id[MAX_UID_T_LEN + 2], *ep; + const char *errstr; + char idbuf[MAX_UID_T_LEN + 2]; char * const *cur; - unsigned long ulval; + id_t id; uid_t runas_uid = 0; gid_t runas_gid = 0; debug_decl(iolog_deserialize_info, SUDO_DEBUG_UTIL) @@ -470,37 +436,35 @@ iolog_deserialize_info(struct iolog_details *details, if (runas_euid_str != NULL) runas_uid_str = runas_euid_str; if (runas_uid_str != NULL) { - errno = 0; - ulval = strtoul(runas_uid_str, &ep, 0); - if (*runas_uid_str != '\0' && *ep == '\0' && - (errno != ERANGE || ulval != ULONG_MAX)) { - runas_uid = (uid_t)ulval; - } + id = atoid(runas_uid_str, NULL, NULL, &errstr); + if (errstr != NULL) + warningx("runas uid %s: %s", runas_uid_str, _(errstr)); + else + runas_uid = (uid_t)id; } if (runas_egid_str != NULL) runas_gid_str = runas_egid_str; if (runas_gid_str != NULL) { - errno = 0; - ulval = strtoul(runas_gid_str, &ep, 0); - if (*runas_gid_str != '\0' && *ep == '\0' && - (errno != ERANGE || ulval != ULONG_MAX)) { - runas_gid = (gid_t)ulval; - } + id = atoid(runas_gid_str, NULL, NULL, &errstr); + if (errstr != NULL) + warningx("runas gid %s: %s", runas_gid_str, _(errstr)); + else + runas_gid = (gid_t)id; } details->runas_pw = sudo_getpwuid(runas_uid); if (details->runas_pw == NULL) { - id[0] = '#'; - strlcpy(&id[1], runas_uid_str, sizeof(id) - 1); - details->runas_pw = sudo_fakepwnam(id, runas_gid); + idbuf[0] = '#'; + strlcpy(&idbuf[1], runas_uid_str, sizeof(idbuf) - 1); + details->runas_pw = sudo_fakepwnam(idbuf, runas_gid); } if (runas_gid != details->runas_pw->pw_gid) { details->runas_gr = sudo_getgrgid(runas_gid); if (details->runas_gr == NULL) { - id[0] = '#'; - strlcpy(&id[1], runas_gid_str, sizeof(id) - 1); - details->runas_gr = sudo_fakegrnam(id); + idbuf[0] = '#'; + strlcpy(&idbuf[1], runas_gid_str, sizeof(idbuf) - 1); + details->runas_gr = sudo_fakegrnam(idbuf); } } debug_return_bool( @@ -509,6 +473,37 @@ iolog_deserialize_info(struct iolog_details *details, io_log_files[IOFD_TTYOUT].enabled); } +/* + * Write the "/log" file that contains the user and command info. + */ +void +write_info_log(char *pathbuf, size_t len, struct iolog_details *details, + char * const argv[], struct timeval *now) +{ + char * const *av; + FILE *fp; + int fd; + + pathbuf[len] = '\0'; + strlcat(pathbuf, "/log", PATH_MAX); + fd = open(pathbuf, O_CREAT|O_WRONLY, S_IRUSR|S_IWUSR); + if (fd == -1 || (fp = fdopen(fd, "w")) == NULL) + log_fatal(USE_ERRNO, N_("unable to create %s"), pathbuf); + + fprintf(fp, "%lld:%s:%s:%s:%s:%d:%d\n%s\n%s", (long long)now->tv_sec, + details->user ? details->user : "unknown", details->runas_pw->pw_name, + details->runas_gr ? details->runas_gr->gr_name : "", + details->tty ? details->tty : "unknown", details->lines, details->cols, + details->cwd ? details->cwd : "unknown", + details->command ? details->command : "unknown"); + for (av = argv + 1; *av != NULL; av++) { + fputc(' ', fp); + fputs(*av, fp); + } + fputc('\n', fp); + fclose(fp); +} + static int sudoers_io_open(unsigned int version, sudo_conv_t conversation, sudo_printf_t plugin_printf, char * const settings[], @@ -582,28 +577,13 @@ sudoers_io_open(unsigned int version, sudo_conv_t conv if (len >= sizeof(pathbuf)) goto done; - /* - * We create 7 files: a log file, a timing file and 5 for input/output. - */ - for (i = 0; i < IOFD_MAX; i++) { - open_io_fd(pathbuf, len, &io_log_files[i], i ? iolog_compress : false); - } - + /* Write log file with user and command details. */ gettimeofday(&last_time, NULL); - fprintf(io_log_files[IOFD_LOG].fd.f, "%lld:%s:%s:%s:%s:%d:%d\n%s\n%s", - (long long)last_time.tv_sec, - details.user ? details.user : "unknown", details.runas_pw->pw_name, - details.runas_gr ? details.runas_gr->gr_name : "", - details.tty ? details.tty : "unknown", details.lines, details.cols, - details.cwd ? details.cwd : "unknown", - details.command ? details.command : "unknown"); - for (cur = &argv[1]; *cur != NULL; cur++) { - fputc(' ', io_log_files[IOFD_LOG].fd.f); - fputs(*cur, io_log_files[IOFD_LOG].fd.f); - } - fputc('\n', io_log_files[IOFD_LOG].fd.f); - fclose(io_log_files[IOFD_LOG].fd.f); - io_log_files[IOFD_LOG].fd.f = NULL; + write_info_log(pathbuf, len, &details, argv, &last_time); + + /* Create the timing I/O log files. */ + for (i = 0; i < IOFD_MAX; i++) + open_io_fd(pathbuf, len, &io_log_files[i], iolog_compress); /* * Clear I/O log function pointers for disabled log functions.