bool sudoers_warn_setlocale(bool restore, int *cookie) { if (restore) return sudoers_setlocale(*cookie, NULL); return sudoers_setlocale(SUDOERS_LOCALE_USER, cookie); }
/* * Log a message to syslog, pre-pending the username and splitting the * message into parts if it is longer than syslog_maxlen. */ static void do_syslog(int pri, char *msg) { size_t len, maxlen; char *p, *tmp, save; const char *fmt; int oldlocale; debug_decl(do_syslog, SUDOERS_DEBUG_LOGGING) /* A priority of -1 corresponds to "none". */ if (pri == -1) debug_return; sudoers_setlocale(SUDOERS_LOCALE_SUDOERS, &oldlocale); /* * Log the full line, breaking into multiple syslog(3) calls if necessary */ fmt = _("%8s : %s"); maxlen = def_syslog_maxlen - (strlen(fmt) - 5 + strlen(user_name)); for (p = msg; *p != '\0'; ) { len = strlen(p); if (len > maxlen) { /* * Break up the line into what will fit on one syslog(3) line * Try to avoid breaking words into several lines if possible. */ tmp = memrchr(p, ' ', maxlen); if (tmp == NULL) tmp = p + maxlen; /* NULL terminate line, but save the char to restore later */ save = *tmp; *tmp = '\0'; mysyslog(pri, fmt, user_name, p); *tmp = save; /* restore saved character */ /* Advance p and eliminate leading whitespace */ for (p = tmp; *p == ' '; p++) continue; } else { mysyslog(pri, fmt, user_name, p); p += len; } fmt = _("%8s : (command continued) %s"); maxlen = def_syslog_maxlen - (strlen(fmt) - 5 + strlen(user_name)); } sudoers_setlocale(oldlocale, NULL); debug_return; }
/* * Log and potentially mail the allowed command. */ bool log_allowed(int status) { char *logline; int oldlocale; bool uid_changed, ret = true; debug_decl(log_allowed, SUDOERS_DEBUG_LOGGING) /* Log and mail messages should be in the sudoers locale. */ sudoers_setlocale(SUDOERS_LOCALE_SUDOERS, &oldlocale); if ((logline = new_logline(NULL, 0)) == NULL) debug_return_bool(false); /* Become root if we are not already. */ uid_changed = set_perms(PERM_ROOT); /* XXX - return value */ if (should_mail(status)) send_mail("%s", logline); /* send mail based on status */ /* * Log via syslog and/or a file. */ if (def_syslog) do_syslog(def_syslog_goodpri, logline); if (def_logfile && !do_logfile(logline)) ret = false; if (uid_changed) { if (!restore_perms()) ret = false; /* XXX - return -1 instead? */ } free(logline); sudoers_setlocale(oldlocale, NULL); debug_return_bool(ret); }
/* * Perform logging for log_warning()/log_warningx(). */ static bool vlog_warning(int flags, const char *fmt, va_list ap) { int oldlocale, serrno = errno; char *logline, *message; bool uid_changed, ret = true; va_list ap2; int len; debug_decl(vlog_error, SUDOERS_DEBUG_LOGGING) /* Need extra copy of ap for sudo_vwarn()/sudo_vwarnx() below. */ va_copy(ap2, ap); /* Log messages should be in the sudoers locale. */ sudoers_setlocale(SUDOERS_LOCALE_SUDOERS, &oldlocale); /* Expand printf-style format + args (with a special case). */ if (fmt == INCORRECT_PASSWORD_ATTEMPT) { unsigned int tries = va_arg(ap, unsigned int); len = asprintf(&message, ngettext("%u incorrect password attempt", "%u incorrect password attempts", tries), tries); } else {
/* * Log, audit and mail the denial message, optionally informing the user. */ bool log_denial(int status, bool inform_user) { const char *message; char *logline; int oldlocale; bool uid_changed, ret = true; debug_decl(log_denial, SUDOERS_DEBUG_LOGGING) /* Handle auditing first (audit_failure() handles the locale itself). */ if (ISSET(status, FLAG_NO_USER | FLAG_NO_HOST)) audit_failure(NewArgc, NewArgv, N_("No user or host")); else audit_failure(NewArgc, NewArgv, N_("validation failure")); /* Log and mail messages should be in the sudoers locale. */ sudoers_setlocale(SUDOERS_LOCALE_SUDOERS, &oldlocale); /* Set error message. */ if (ISSET(status, FLAG_NO_USER)) message = _("user NOT in sudoers"); else if (ISSET(status, FLAG_NO_HOST)) message = _("user NOT authorized on host"); else message = _("command not allowed"); logline = new_logline(message, 0); if (logline == NULL) debug_return_bool(false); /* Become root if we are not already. */ uid_changed = set_perms(PERM_ROOT); if (should_mail(status)) send_mail("%s", logline); /* send mail based on status */ /* * Log via syslog and/or a file. */ if (def_syslog) do_syslog(def_syslog_badpri, logline); if (def_logfile && !do_logfile(logline)) ret = false; if (uid_changed) { if (!restore_perms()) ret = false; /* XXX - return -1 instead? */ } free(logline); /* Restore locale. */ sudoers_setlocale(oldlocale, NULL); /* Inform the user if they failed to authenticate (in their locale). */ if (inform_user) { sudoers_setlocale(SUDOERS_LOCALE_USER, &oldlocale); if (ISSET(status, FLAG_NO_USER)) { sudo_printf(SUDO_CONV_ERROR_MSG, _("%s is not in the sudoers " "file. This incident will be reported.\n"), user_name); } else if (ISSET(status, FLAG_NO_HOST)) { sudo_printf(SUDO_CONV_ERROR_MSG, _("%s is not allowed to run sudo " "on %s. This incident will be reported.\n"), user_name, user_srunhost); } else if (ISSET(status, FLAG_NO_CHECK)) { sudo_printf(SUDO_CONV_ERROR_MSG, _("Sorry, user %s may not run " "sudo on %s.\n"), user_name, user_srunhost); } else { sudo_printf(SUDO_CONV_ERROR_MSG, _("Sorry, user %s is not allowed " "to execute '%s%s%s' as %s%s%s on %s.\n"), user_name, user_cmnd, user_args ? " " : "", user_args ? user_args : "", list_pw ? list_pw->pw_name : runas_pw ? runas_pw->pw_name : user_name, runas_gr ? ":" : "", runas_gr ? runas_gr->gr_name : "", user_host); } sudoers_setlocale(oldlocale, NULL); } debug_return_bool(ret); }
static bool do_logfile(const char *msg) { static bool warned = false; const char *timestr; int len, oldlocale; bool ret = false; char *full_line; mode_t oldmask; FILE *fp; debug_decl(do_logfile, SUDOERS_DEBUG_LOGGING) sudoers_setlocale(SUDOERS_LOCALE_SUDOERS, &oldlocale); oldmask = umask(S_IRWXG|S_IRWXO); fp = fopen(def_logfile, "a"); (void) umask(oldmask); if (fp == NULL) { if (!warned) { log_warning(SLOG_SEND_MAIL|SLOG_NO_LOG, N_("unable to open log file: %s"), def_logfile); warned = true; } goto done; } if (!sudo_lock_file(fileno(fp), SUDO_LOCK)) { if (!warned) { log_warning(SLOG_SEND_MAIL|SLOG_NO_LOG, N_("unable to lock log file: %s"), def_logfile); warned = true; } goto done; } timestr = get_timestr(time(NULL), def_log_year); if (timestr == NULL) timestr = "invalid date"; if (def_log_host) { len = asprintf(&full_line, "%s : %s : HOST=%s : %s", timestr, user_name, user_srunhost, msg); } else { len = asprintf(&full_line, "%s : %s : %s", timestr, user_name, msg); } if (len == -1) { sudo_warnx(U_("%s: %s"), __func__, U_("unable to allocate memory")); goto done; } if ((size_t)def_loglinelen < sizeof(LOG_INDENT)) { /* Don't pretty-print long log file lines (hard to grep). */ (void) fputs(full_line, fp); (void) fputc('\n', fp); } else { /* Write line with word wrap around def_loglinelen chars. */ writeln_wrap(fp, full_line, len, def_loglinelen); } free(full_line); (void) fflush(fp); if (ferror(fp)) { if (!warned) { log_warning(SLOG_SEND_MAIL|SLOG_NO_LOG, N_("unable to write log file: %s"), def_logfile); warned = true; } goto done; } ret = true; done: if (fp != NULL) (void) fclose(fp); sudoers_setlocale(oldlocale, NULL); debug_return_bool(ret); }
void warning_restore_locale(void) { sudoers_setlocale(warning_locale, NULL); }
void warning_set_locale(void) { sudoers_setlocale(SUDOERS_LOCALE_USER, &warning_locale); }