summaryrefslogtreecommitdiffstats
path: root/src/submission/submission-backend.h
diff options
context:
space:
mode:
Diffstat (limited to 'src/submission/submission-backend.h')
-rw-r--r--src/submission/submission-backend.h170
1 files changed, 170 insertions, 0 deletions
diff --git a/src/submission/submission-backend.h b/src/submission/submission-backend.h
new file mode 100644
index 0000000..25d2389
--- /dev/null
+++ b/src/submission/submission-backend.h
@@ -0,0 +1,170 @@
+#ifndef SUBMISSION_BACKEND_H
+#define SUBMISSION_BACKEND_H
+
+struct submission_recipient;
+struct submission_backend;
+union submission_backend_module_context;
+
+struct submission_backend_vfuncs {
+ void (*destroy)(struct submission_backend *backend);
+
+ void (*start)(struct submission_backend *backend);
+ void (*ready)(struct submission_backend *backend,
+ enum smtp_capability caps);
+
+ void (*fail)(struct submission_backend *backend, const char *enh_code,
+ const char *reason);
+
+ void (*client_input_pre)(struct submission_backend *backend);
+ void (*client_input_post)(struct submission_backend *backend);
+
+ uoff_t (*get_max_mail_size)(struct submission_backend *backend);
+
+ void (*trans_start)(struct submission_backend *backend,
+ struct smtp_server_transaction *trans,
+ const struct smtp_address *path,
+ const struct smtp_params_mail *params);
+ void (*trans_free)(struct submission_backend *backend,
+ struct smtp_server_transaction *trans);
+
+ /* Command handlers:
+
+ These implement the behavior of the various core SMTP commands.
+ SMTP commands are handled asynchronously, which means that the
+ command is not necessarily finished when these handlers end. A
+ command is finished either when 1 is returned or a reply is submitted
+ for it. When a handler returns 0, the command implementation is
+ waiting for an external event and when it returns -1 an error
+ occurred. When 1 is returned, a default success reply is submitted
+ implicitly. Not submitting an error reply when -1 is returned causes
+ an assert fail. See src/lib-smtp/smtp-server.h for details.
+
+ When overriding these handler vfuncs, the base implementation should
+ usually be called at some point. When it is called immediately, its
+ result can be returned as normal. When the override returns 0, the
+ base implementation would be called at a later time when some
+ external state is achieved. Note that the overriding function then
+ assumes the responsibility to submit the default reply when none is
+ submitted and the base implementation returns 1.
+
+ Also note that only the default backend actually triggers all of
+ these command callbacks. Secondary backends only get called for
+ transaction commands and only when that backend is tied to the
+ transaction somehow; e.g., as the primary transaction backend or when
+ it is tied to one of the approved recipients.
+ */
+ int (*cmd_helo)(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd,
+ struct smtp_server_cmd_helo *data);
+
+ int (*cmd_mail)(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd,
+ struct smtp_server_cmd_mail *data);
+ int (*cmd_rcpt)(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd,
+ struct submission_recipient *srcpt);
+ int (*cmd_rset)(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd);
+ int (*cmd_data)(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd,
+ struct smtp_server_transaction *trans,
+ struct istream *data_input, uoff_t data_size);
+
+ int (*cmd_vrfy)(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd,
+ const char *param);
+ int (*cmd_noop)(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd);
+
+ int (*cmd_quit)(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd);
+};
+
+struct submission_backend {
+ pool_t pool;
+ struct client *client;
+
+ struct submission_backend *prev, *next;
+
+ struct submission_backend_vfuncs v;
+
+ struct istream *data_input;
+ uoff_t data_size;
+
+ char *fail_enh_code;
+ char *fail_reason;
+
+ /* Module-specific contexts. */
+ ARRAY(union submission_backend_module_context *) module_contexts;
+
+ bool started:1;
+ bool ready:1;
+ bool trans_started:1;
+};
+
+struct submission_backend_module_register {
+ unsigned int id;
+};
+
+union submission_backend_module_context {
+ struct submission_backend_module_register *reg;
+};
+extern struct submission_backend_module_register
+submission_backend_module_register;
+
+void submission_backend_init(struct submission_backend *backend,
+ pool_t pool, struct client *client,
+ const struct submission_backend_vfuncs *vfunc);
+void submission_backends_destroy_all(struct client *client);
+
+void submission_backend_start(struct submission_backend *backend);
+void submission_backend_started(struct submission_backend *backend,
+ enum smtp_capability caps);
+
+void submission_backend_fail(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd,
+ const char *enh_code, const char *reason)
+ ATTR_NULL(2);
+
+void submission_backends_client_input_pre(struct client *client);
+void submission_backends_client_input_post(struct client *client);
+
+uoff_t submission_backend_get_max_mail_size(struct submission_backend *backend);
+
+void submission_backend_trans_start(struct submission_backend *backend,
+ struct smtp_server_transaction *trans);
+void submission_backends_trans_start(struct client *client,
+ struct smtp_server_transaction *trans);
+void submission_backends_trans_free(struct client *client,
+ struct smtp_server_transaction *trans);
+
+void submission_backend_helo_reply_submit(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd,
+ struct smtp_server_cmd_helo *data);
+int submission_backend_cmd_helo(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd,
+ struct smtp_server_cmd_helo *data);
+
+int submission_backend_cmd_mail(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd,
+ struct smtp_server_cmd_mail *data);
+int submission_backend_cmd_rcpt(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd,
+ struct submission_recipient *srcpt);
+int submission_backend_cmd_rset(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd);
+int submission_backends_cmd_data(struct client *client,
+ struct smtp_server_cmd_ctx *cmd,
+ struct smtp_server_transaction *trans,
+ struct istream *data_input, uoff_t data_size);
+
+int submission_backend_cmd_vrfy(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd,
+ const char *param);
+int submission_backend_cmd_noop(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd);
+
+int submission_backend_cmd_quit(struct submission_backend *backend,
+ struct smtp_server_cmd_ctx *cmd);
+
+#endif