smtp-server-cmd-data.c (dovecot-2.3.16) | : | smtp-server-cmd-data.c (dovecot-2.3.17) | ||
---|---|---|---|---|
skipping to change at line 15 | skipping to change at line 15 | |||
#include "array.h" | #include "array.h" | |||
#include "istream.h" | #include "istream.h" | |||
#include "istream-chain.h" | #include "istream-chain.h" | |||
#include "smtp-command-parser.h" | #include "smtp-command-parser.h" | |||
#include "smtp-server-private.h" | #include "smtp-server-private.h" | |||
/* DATA/BDAT/B... commands */ | /* DATA/BDAT/B... commands */ | |||
struct cmd_data_context { | struct cmd_data_context { | |||
struct istream *main_input; | ||||
struct istream *chunk_input; | struct istream *chunk_input; | |||
uoff_t chunk_size; | uoff_t chunk_size; | |||
bool chunking:1; | bool chunking:1; | |||
bool client_input:1; | bool client_input:1; | |||
bool chunk_first:1; | bool chunk_first:1; | |||
bool chunk_last:1; | bool chunk_last:1; | |||
}; | }; | |||
static void | static void | |||
skipping to change at line 138 | skipping to change at line 139 | |||
static void | static void | |||
cmd_data_destroy(struct smtp_server_cmd_ctx *cmd, | cmd_data_destroy(struct smtp_server_cmd_ctx *cmd, | |||
struct cmd_data_context *data_cmd) | struct cmd_data_context *data_cmd) | |||
{ | { | |||
struct smtp_server_connection *conn = cmd->conn; | struct smtp_server_connection *conn = cmd->conn; | |||
struct smtp_server_command *command = cmd->cmd; | struct smtp_server_command *command = cmd->cmd; | |||
i_assert(data_cmd != NULL); | i_assert(data_cmd != NULL); | |||
if (data_cmd->chunk_last || | if (data_cmd->main_input == conn->state.data_input && | |||
!smtp_server_command_replied_success(command)) { | (data_cmd->chunk_last || | |||
!smtp_server_command_replied_success(command))) { | ||||
/* clean up */ | /* clean up */ | |||
i_stream_destroy(&conn->state.data_input); | i_stream_destroy(&conn->state.data_input); | |||
i_stream_destroy(&conn->state.data_chain_input); | i_stream_destroy(&conn->state.data_chain_input); | |||
conn->state.data_chain = NULL; | conn->state.data_chain = NULL; | |||
} | } | |||
i_stream_unref(&data_cmd->chunk_input); | i_stream_unref(&data_cmd->chunk_input); | |||
} | } | |||
static void | static void | |||
skipping to change at line 351 | skipping to change at line 353 | |||
{ | { | |||
struct smtp_server_connection *conn = cmd->conn; | struct smtp_server_connection *conn = cmd->conn; | |||
struct smtp_server_transaction *trans = conn->state.trans; | struct smtp_server_transaction *trans = conn->state.trans; | |||
const struct smtp_server_callbacks *callbacks = conn->callbacks; | const struct smtp_server_callbacks *callbacks = conn->callbacks; | |||
struct smtp_server_command *command = cmd->cmd; | struct smtp_server_command *command = cmd->cmd; | |||
/* this command is next to send a reply */ | /* this command is next to send a reply */ | |||
i_assert(data_cmd != NULL); | i_assert(data_cmd != NULL); | |||
i_assert(trans != NULL); | i_assert(trans != NULL); | |||
/* DATA command stops the pipeline, so if it is next to reply, nothing | ||||
else can be pending. */ | ||||
i_assert(conn->state.pending_mail_cmds == 0 && | i_assert(conn->state.pending_mail_cmds == 0 && | |||
conn->state.pending_rcpt_cmds == 0); | conn->state.pending_rcpt_cmds == 0); | |||
i_assert(trans != NULL); | ||||
e_debug(cmd->event, "Command is next to be replied"); | e_debug(cmd->event, "Command is next to be replied"); | |||
if (trans != NULL) | smtp_server_transaction_data_command(trans, cmd); | |||
smtp_server_transaction_data_command(trans, cmd); | ||||
/* check whether we have had successful mail and rcpt commands */ | /* check whether we have had successful mail and rcpt commands */ | |||
if (!smtp_server_connection_data_check_state(cmd)) | if (!smtp_server_connection_data_check_state(cmd)) | |||
return; | return; | |||
if (data_cmd->chunk_last) { | if (data_cmd->chunk_last) { | |||
/* LMTP 'DATA' and 'BDAT LAST' commands need to send more than | /* LMTP 'DATA' and 'BDAT LAST' commands need to send more than | |||
one reply per recipient */ | one reply per recipient */ | |||
if (HAS_ALL_BITS(trans->flags, | if (HAS_ALL_BITS(trans->flags, | |||
SMTP_SERVER_TRANSACTION_FLAG_REPLY_PER_RCPT)) { | SMTP_SERVER_TRANSACTION_FLAG_REPLY_PER_RCPT)) { | |||
skipping to change at line 395 | skipping to change at line 398 | |||
} | } | |||
if (data_cmd->chunk_first) { | if (data_cmd->chunk_first) { | |||
struct smtp_server_command *cmd_temp = command; | struct smtp_server_command *cmd_temp = command; | |||
e_debug(cmd->event, "First chunk"); | e_debug(cmd->event, "First chunk"); | |||
smtp_server_command_ref(cmd_temp); | smtp_server_command_ref(cmd_temp); | |||
i_assert(callbacks != NULL && | i_assert(callbacks != NULL && | |||
callbacks->conn_cmd_data_begin != NULL); | callbacks->conn_cmd_data_begin != NULL); | |||
i_assert(conn->state.data_input != NULL); | ||||
if (callbacks->conn_cmd_data_begin(conn->context, | if (callbacks->conn_cmd_data_begin(conn->context, | |||
cmd, conn->state.trans, conn->state.data_input) < 0) { | cmd, conn->state.trans, conn->state.data_input) < 0) { | |||
i_assert(smtp_server_command_is_replied(cmd_temp)); | i_assert(smtp_server_command_is_replied(cmd_temp)); | |||
/* command failed */ | /* command failed */ | |||
smtp_server_command_unref(&cmd_temp); | smtp_server_command_unref(&cmd_temp); | |||
return; | return; | |||
} | } | |||
if (!smtp_server_command_unref(&cmd_temp)) | if (!smtp_server_command_unref(&cmd_temp)) | |||
return; | return; | |||
} | } | |||
skipping to change at line 430 | skipping to change at line 434 | |||
static void | static void | |||
cmd_data_start_input(struct smtp_server_cmd_ctx *cmd, | cmd_data_start_input(struct smtp_server_cmd_ctx *cmd, | |||
struct cmd_data_context *data_cmd, struct istream *input) | struct cmd_data_context *data_cmd, struct istream *input) | |||
{ | { | |||
struct smtp_server_connection *conn = cmd->conn; | struct smtp_server_connection *conn = cmd->conn; | |||
struct smtp_server_command *command = cmd->cmd; | struct smtp_server_command *command = cmd->cmd; | |||
i_assert(data_cmd != NULL); | i_assert(data_cmd != NULL); | |||
if (input != NULL) { | if (input != NULL) { | |||
i_assert(conn->state.data_input == NULL); | ||||
conn->state.data_input = input; | conn->state.data_input = input; | |||
i_stream_ref(input); | i_stream_ref(input); | |||
} | } | |||
data_cmd->main_input = conn->state.data_input; | ||||
if (data_cmd->client_input) | if (data_cmd->client_input) | |||
smtp_server_command_input_lock(cmd); | smtp_server_command_input_lock(cmd); | |||
if (data_cmd->chunk_last) { | if (data_cmd->chunk_last) { | |||
smtp_server_command_add_hook( | smtp_server_command_add_hook( | |||
command, SMTP_SERVER_COMMAND_HOOK_COMPLETED, | command, SMTP_SERVER_COMMAND_HOOK_COMPLETED, | |||
cmd_data_completed, data_cmd); | cmd_data_completed, data_cmd); | |||
} else { | } else { | |||
smtp_server_command_add_hook( | smtp_server_command_add_hook( | |||
End of changes. 8 change blocks. | ||||
5 lines changed or deleted | 11 lines changed or added |