From: Timo Sirainen Date: Sat, 10 Mar 2012 13:53:39 +0000 (+0200) Subject: stats: Fixes to handling per-command stats updates. X-Git-Tag: 2.1.2~31 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=8d513b613ff048a3ec1bccd6e9fa5016f04e28f0;p=thirdparty%2Fdovecot%2Fcore.git stats: Fixes to handling per-command stats updates. --- diff --git a/src/plugins/imap-stats/imap-stats-plugin.c b/src/plugins/imap-stats/imap-stats-plugin.c index e1a1dc3f3a..9cb89a51ce 100644 --- a/src/plugins/imap-stats/imap-stats-plugin.c +++ b/src/plugins/imap-stats/imap-stats-plugin.c @@ -56,7 +56,6 @@ static void stats_command_post(struct client_command_context *cmd) struct mail_stats stats, pre_trans_stats, trans_stats; unsigned int args_pos = 0; string_t *str; - bool done; if (scmd == NULL) return; @@ -76,11 +75,13 @@ static void stats_command_post(struct client_command_context *cmd) str_append(str, "UPDATE-CMD\t"); str_append(str, guid_128_to_string(suser->session_guid)); - done = cmd->state == CLIENT_COMMAND_STATE_DONE; - str_printfa(str, "\t%u\t%d\t", scmd->id, done); + str_printfa(str, "\t%u\t", scmd->id); + if (cmd->state == CLIENT_COMMAND_STATE_DONE) + str_append_c(str, 'd'); if (scmd->continued) - str_append_c(str, '\t'); + str_append_c(str, 'c'); else { + str_append_c(str, '\t'); str_append(str, cmd->name); str_append_c(str, '\t'); args_pos = str_len(str); diff --git a/src/stats/mail-command.c b/src/stats/mail-command.c index 61269e12a5..343823f10c 100644 --- a/src/stats/mail-command.c +++ b/src/stats/mail-command.c @@ -100,11 +100,12 @@ int mail_command_update_parse(const char *const *args, const char **error_r) struct mail_command *cmd; struct mail_stats stats, diff_stats; const char *error; - unsigned int cmd_id; - bool done; + unsigned int i, cmd_id; + bool done = FALSE, continued = FALSE; - /* [key=value ..] */ - if (str_array_length(args) < 4) { + /* [d] [key=value ..] + c[d] [key=value ..] */ + if (str_array_length(args) < 3) { *error_r = "UPDATE-CMD: Too few parameters"; return -1; } @@ -115,38 +116,62 @@ int mail_command_update_parse(const char *const *args, const char **error_r) *error_r = "UPDATE-CMD: Invalid command id"; return -1; } - if (strcmp(args[2], "0") != 0 && - strcmp(args[2], "1") != 0) { - *error_r = "UPDATE-CMD: Invalid done parameter"; - return -1; - } - done = args[2][0] == '1'; - if (mail_stats_parse(args+5, &stats, error_r) < 0) { - *error_r = t_strconcat("UPDATE-CMD: ", *error_r, NULL); - return -1; + for (i = 0; args[2][i] != '\0'; i++) { + switch (args[2][i]) { + case 'd': + done = TRUE; + break; + case 'c': + continued = TRUE; + break; + default: + *error_r = "UPDATE-CMD: Invalid flags parameter"; + return -1; + } } cmd = mail_command_find(session, cmd_id); - if (cmd == NULL) { + if (!continued) { + /* new command */ + if (cmd != NULL) { + *error_r = "UPDATE-CMD: Duplicate new command id"; + return -1; + } + if (str_array_length(args) < 5) { + *error_r = "UPDATE-CMD: Too few parameters"; + return -1; + } cmd = mail_command_add(session, args[3], args[4]); cmd->id = cmd_id; - cmd->stats = stats; + session->highest_cmd_id = + I_MAX(session->highest_cmd_id, cmd_id); session->num_cmds++; session->user->num_cmds++; session->user->domain->num_cmds++; if (session->ip != NULL) session->ip->num_cmds++; + args += 5; } else { - if (!mail_stats_diff(&cmd->stats, &stats, &diff_stats, - &error)) { - *error_r = t_strconcat("UPDATE-CMD: stats shrank: ", - error, NULL); - return -1; + if (cmd == NULL) { + /* already expired command, ignore */ + i_warning("UPDATE-CMD: Already expired"); + return 0; } + args += 3; cmd->last_update = ioloop_timeval; - mail_stats_add(&cmd->stats, &diff_stats); } + if (mail_stats_parse(args, &stats, error_r) < 0) { + *error_r = t_strconcat("UPDATE-CMD: ", *error_r, NULL); + return -1; + } + if (!mail_stats_diff(&cmd->stats, &stats, &diff_stats, &error)) { + *error_r = t_strconcat("UPDATE-CMD: stats shrank: ", + error, NULL); + return -1; + } + mail_stats_add(&cmd->stats, &diff_stats); + if (done) { cmd->id = 0; mail_command_unref(&cmd);