2
0
mirror of https://github.com/sudo-project/sudo.git synced 2025-08-22 01:49:11 +00:00

For intercepted commands, log an offset into the current I/O log.

This can be used with sudoreplay to jump to when a specific command
was executed within a session log.
This commit is contained in:
Todd C. Miller 2021-08-13 16:00:00 -06:00
parent 695f4bea05
commit 4aefd43948
4 changed files with 56 additions and 5 deletions

View File

@ -111,6 +111,7 @@ struct eventlog {
char **env_add;
char **envp;
struct timespec submit_time;
struct timespec iolog_offset;
int lines;
int columns;
uid_t runuid;

View File

@ -100,7 +100,7 @@ new_logline(int event_type, int flags, struct eventlog_args *args,
const char *iolog_file = evlog->iolog_file;
const char *tty, *tsid = NULL;
char exit_str[(((sizeof(int) * 8) + 2) / 3) + 2];
char sessid[7];
char sessid[7], offsetstr[64] = "";
size_t len = 0;
int i;
debug_decl(new_logline, SUDO_DEBUG_UTIL);
@ -132,6 +132,10 @@ new_logline(int event_type, int flags, struct eventlog_args *args,
} else {
tsid = iolog_file;
}
if (sudo_timespecisset(&evlog->iolog_offset)) {
(void)snprintf(offsetstr, sizeof(offsetstr), "@%lld.%09ld",
evlog->iolog_offset.tv_sec, evlog->iolog_offset.tv_nsec);
}
}
/* Sudo-format logs use the short form of the ttyname. */
@ -159,8 +163,9 @@ new_logline(int event_type, int flags, struct eventlog_args *args,
len += sizeof(LL_USER_STR) + 2 + strlen(evlog->runuser);
if (evlog->rungroup != NULL)
len += sizeof(LL_GROUP_STR) + 2 + strlen(evlog->rungroup);
if (tsid != NULL)
len += sizeof(LL_TSID_STR) + 2 + strlen(tsid);
if (tsid != NULL) {
len += sizeof(LL_TSID_STR) + 2 + strlen(tsid) + strlen(offsetstr);
}
if (evlog->env_add != NULL) {
size_t evlen = 0;
char * const *ep;
@ -251,6 +256,7 @@ new_logline(int event_type, int flags, struct eventlog_args *args,
if (tsid != NULL) {
if (strlcat(line, LL_TSID_STR, len) >= len ||
strlcat(line, tsid, len) >= len ||
strlcat(line, offsetstr, len) >= len ||
strlcat(line, " ; ", len) >= len)
goto toobig;
}
@ -860,14 +866,14 @@ format_json(int event_type, struct eventlog_args *args,
/* Log event time on server (set earlier) */
if (!json_add_timestamp(&json, "server_time", &now, true)) {
sudo_debug_printf(SUDO_DEBUG_ERROR|SUDO_DEBUG_ERRNO|SUDO_DEBUG_LINENO,
sudo_debug_printf(SUDO_DEBUG_ERROR|SUDO_DEBUG_LINENO,
"unable format timestamp");
goto bad;
}
/* Log event time from client */
if (!json_add_timestamp(&json, time_str, args->event_time, format_timestamp)) {
sudo_debug_printf(SUDO_DEBUG_ERROR|SUDO_DEBUG_ERRNO|SUDO_DEBUG_LINENO,
sudo_debug_printf(SUDO_DEBUG_ERROR|SUDO_DEBUG_LINENO,
"unable format timestamp");
goto bad;
}
@ -910,6 +916,14 @@ format_json(int event_type, struct eventlog_args *args,
json_value.u.string = evlog->iolog_path;
if (!sudo_json_add_value(&json, "iolog_path", &json_value))
goto bad;
if (sudo_timespecisset(&evlog->iolog_offset)) {
if (!json_add_timestamp(&json, "iolog_offset", &evlog->iolog_offset, false)) {
sudo_debug_printf(SUDO_DEBUG_ERROR|SUDO_DEBUG_LINENO,
"unable format timestamp");
goto bad;
}
}
}
}

View File

@ -166,6 +166,20 @@ store_accept_local(AcceptMessage *msg, uint8_t *buf, size_t len,
closure->log_io = true;
log_id = closure->evlog->iolog_path;
}
} else if (closure->log_io) {
/* Sub-command from an existing session, set iolog and offset. */
evlog->iolog_path = strdup(closure->evlog->iolog_path);
if (evlog->iolog_path == NULL) {
sudo_warnx(U_("%s: %s"), __func__, U_("unable to allocate memory"));
closure->errstr = _("unable to allocate memory");
goto done;
}
if (closure->evlog->iolog_file != NULL) {
evlog->iolog_file = evlog->iolog_path +
(closure->evlog->iolog_file - closure->evlog->iolog_path);
}
sudo_timespecsub(&evlog->submit_time, &closure->evlog->submit_time,
&evlog->iolog_offset);
}
if (!eventlog_accept(evlog, 0, logsrvd_json_log_cb, &info)) {
@ -215,6 +229,20 @@ store_reject_local(RejectMessage *msg, uint8_t *buf, size_t len,
if (closure->evlog == NULL) {
/* Initial command in session. */
closure->evlog = evlog;
} else if (closure->log_io) {
/* Sub-command from an existing session, set iolog and offset. */
evlog->iolog_path = strdup(closure->evlog->iolog_path);
if (evlog->iolog_path == NULL) {
sudo_warnx(U_("%s: %s"), __func__, U_("unable to allocate memory"));
closure->errstr = _("unable to allocate memory");
goto done;
}
if (closure->evlog->iolog_file != NULL) {
evlog->iolog_file = evlog->iolog_path +
(closure->evlog->iolog_file - closure->evlog->iolog_path);
}
sudo_timespecsub(&evlog->submit_time, &closure->evlog->submit_time,
&evlog->iolog_offset);
}
if (!eventlog_reject(evlog, 0, msg->reason, logsrvd_json_log_cb, &info)) {

View File

@ -804,6 +804,14 @@ sudoers_to_eventlog(struct eventlog *evlog, char * const argv[],
} else {
strlcpy(evlog->uuid_str, uuid_str, sizeof(evlog->uuid_str));
}
if (ISSET(sudo_mode, MODE_POLICY_INTERCEPTED)) {
struct timespec now;
if (sudo_gettime_real(&now) == -1) {
sudo_warn("%s", U_("unable to get time of day"));
} else {
sudo_timespecsub(&now, &sudo_user.submit_time, &evlog->iolog_offset);
}
}
debug_return;
}