xref: /openbsd/usr.sbin/smtpd/smtpd-api.h (revision 47388f99)
1 /*	$OpenBSD: smtpd-api.h,v 1.37 2024/06/09 10:13:05 gilles Exp $	*/
2 
3 /*
4  * Copyright (c) 2013 Eric Faurot <eric@openbsd.org>
5  * Copyright (c) 2011 Gilles Chehade <gilles@poolp.org>
6  *
7  * Permission to use, copy, modify, and distribute this software for any
8  * purpose with or without fee is hereby granted, provided that the above
9  * copyright notice and this permission notice appear in all copies.
10  *
11  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
12  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
13  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
14  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
15  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
16  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
17  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
18  */
19 
20 #ifndef	_SMTPD_API_H_
21 #define	_SMTPD_API_H_
22 
23 #include "dict.h"
24 #include "tree.h"
25 
26 struct mailaddr {
27 	char	user[SMTPD_MAXLOCALPARTSIZE];
28 	char	domain[SMTPD_MAXDOMAINPARTSIZE];
29 };
30 
31 #define PROC_QUEUE_API_VERSION	2
32 
33 enum {
34 	PROC_QUEUE_OK,
35 	PROC_QUEUE_FAIL,
36 	PROC_QUEUE_INIT,
37 	PROC_QUEUE_CLOSE,
38 	PROC_QUEUE_MESSAGE_CREATE,
39 	PROC_QUEUE_MESSAGE_DELETE,
40 	PROC_QUEUE_MESSAGE_COMMIT,
41 	PROC_QUEUE_MESSAGE_FD_R,
42 	PROC_QUEUE_ENVELOPE_CREATE,
43 	PROC_QUEUE_ENVELOPE_DELETE,
44 	PROC_QUEUE_ENVELOPE_LOAD,
45 	PROC_QUEUE_ENVELOPE_UPDATE,
46 	PROC_QUEUE_ENVELOPE_WALK,
47 };
48 
49 #define PROC_SCHEDULER_API_VERSION	2
50 
51 struct scheduler_info;
52 
53 enum {
54 	PROC_SCHEDULER_OK,
55 	PROC_SCHEDULER_FAIL,
56 	PROC_SCHEDULER_INIT,
57 	PROC_SCHEDULER_INSERT,
58 	PROC_SCHEDULER_COMMIT,
59 	PROC_SCHEDULER_ROLLBACK,
60 	PROC_SCHEDULER_UPDATE,
61 	PROC_SCHEDULER_DELETE,
62 	PROC_SCHEDULER_HOLD,
63 	PROC_SCHEDULER_RELEASE,
64 	PROC_SCHEDULER_BATCH,
65 	PROC_SCHEDULER_MESSAGES,
66 	PROC_SCHEDULER_ENVELOPES,
67 	PROC_SCHEDULER_SCHEDULE,
68 	PROC_SCHEDULER_REMOVE,
69 	PROC_SCHEDULER_SUSPEND,
70 	PROC_SCHEDULER_RESUME,
71 };
72 
73 enum envelope_flags {
74 	EF_AUTHENTICATED	= 0x01,
75 	EF_BOUNCE		= 0x02,
76 	EF_INTERNAL		= 0x04, /* Internal expansion forward */
77 
78 	/* runstate, not saved on disk */
79 
80 	EF_PENDING		= 0x10,
81 	EF_INFLIGHT		= 0x20,
82 	EF_SUSPEND		= 0x40,
83 	EF_HOLD			= 0x80,
84 };
85 
86 struct evpstate {
87 	uint64_t		evpid;
88 	uint16_t		flags;
89 	uint16_t		retry;
90 	time_t			time;
91 };
92 
93 enum delivery_type {
94 	D_MDA,
95 	D_MTA,
96 	D_BOUNCE,
97 };
98 
99 struct scheduler_info {
100 	uint64_t		evpid;
101 	enum delivery_type	type;
102 	uint16_t		retry;
103 	time_t			creation;
104 	time_t			ttl;
105 	time_t			lasttry;
106 	time_t			lastbounce;
107 	time_t			nexttry;
108 };
109 
110 #define SCHED_REMOVE		0x01
111 #define SCHED_EXPIRE		0x02
112 #define SCHED_UPDATE		0x04
113 #define SCHED_BOUNCE		0x08
114 #define SCHED_MDA		0x10
115 #define SCHED_MTA		0x20
116 
117 #define PROC_TABLE_API_VERSION	2
118 
119 struct table_open_params {
120 	uint32_t	version;
121 	char		name[LINE_MAX];
122 };
123 
124 enum table_service {
125 	K_NONE		= 0x000,
126 	K_ALIAS		= 0x001,	/* returns struct expand	*/
127 	K_DOMAIN	= 0x002,	/* returns struct destination	*/
128 	K_CREDENTIALS	= 0x004,	/* returns struct credentials	*/
129 	K_NETADDR	= 0x008,	/* returns struct netaddr	*/
130 	K_USERINFO	= 0x010,	/* returns struct userinfo	*/
131 	K_SOURCE	= 0x020,	/* returns struct source	*/
132 	K_MAILADDR	= 0x040,	/* returns struct mailaddr	*/
133 	K_ADDRNAME	= 0x080,	/* returns struct addrname	*/
134 	K_MAILADDRMAP	= 0x100,	/* returns struct maddrmap	*/
135 	K_RELAYHOST	= 0x200,	/* returns struct relayhost	*/
136 	K_STRING	= 0x400,
137 	K_REGEX		= 0x800,
138 	K_AUTH		= 0x1000,
139 };
140 #define K_ANY		  0xffff
141 
142 enum {
143 	PROC_TABLE_OK,
144 	PROC_TABLE_FAIL,
145 	PROC_TABLE_OPEN,
146 	PROC_TABLE_CLOSE,
147 	PROC_TABLE_UPDATE,
148 	PROC_TABLE_CHECK,
149 	PROC_TABLE_LOOKUP,
150 	PROC_TABLE_FETCH,
151 };
152 
153 enum enhanced_status_code {
154 	/* 0.0 */
155 	ESC_OTHER_STATUS				= 00,
156 
157 	/* 1.x */
158 	ESC_OTHER_ADDRESS_STATUS			= 10,
159 	ESC_BAD_DESTINATION_MAILBOX_ADDRESS		= 11,
160 	ESC_BAD_DESTINATION_SYSTEM_ADDRESS		= 12,
161 	ESC_BAD_DESTINATION_MAILBOX_ADDRESS_SYNTAX     	= 13,
162 	ESC_DESTINATION_MAILBOX_ADDRESS_AMBIGUOUS	= 14,
163 	ESC_DESTINATION_ADDRESS_VALID			= 15,
164 	ESC_DESTINATION_MAILBOX_HAS_MOVED      		= 16,
165 	ESC_BAD_SENDER_MAILBOX_ADDRESS_SYNTAX		= 17,
166 	ESC_BAD_SENDER_SYSTEM_ADDRESS			= 18,
167 
168 	/* 2.x */
169 	ESC_OTHER_MAILBOX_STATUS			= 20,
170 	ESC_MAILBOX_DISABLED				= 21,
171 	ESC_MAILBOX_FULL				= 22,
172 	ESC_MESSAGE_LENGTH_TOO_LARGE   			= 23,
173 	ESC_MAILING_LIST_EXPANSION_PROBLEM		= 24,
174 
175 	/* 3.x */
176 	ESC_OTHER_MAIL_SYSTEM_STATUS			= 30,
177 	ESC_MAIL_SYSTEM_FULL				= 31,
178 	ESC_SYSTEM_NOT_ACCEPTING_MESSAGES		= 32,
179 	ESC_SYSTEM_NOT_CAPABLE_OF_SELECTED_FEATURES    	= 33,
180 	ESC_MESSAGE_TOO_BIG_FOR_SYSTEM		    	= 34,
181 	ESC_SYSTEM_INCORRECTLY_CONFIGURED      	    	= 35,
182 
183 	/* 4.x */
184 	ESC_OTHER_NETWORK_ROUTING_STATUS      	    	= 40,
185 	ESC_NO_ANSWER_FROM_HOST		      	    	= 41,
186 	ESC_BAD_CONNECTION		      	    	= 42,
187 	ESC_DIRECTORY_SERVER_FAILURE   	      	    	= 43,
188 	ESC_UNABLE_TO_ROUTE	   	      	    	= 44,
189 	ESC_MAIL_SYSTEM_CONGESTION   	      	    	= 45,
190 	ESC_ROUTING_LOOP_DETECTED   	      	    	= 46,
191 	ESC_DELIVERY_TIME_EXPIRED   	      	    	= 47,
192 
193 	/* 5.x */
194 	ESC_INVALID_RECIPIENT   	      	    	= 50,
195 	ESC_INVALID_COMMAND	   	      	    	= 51,
196 	ESC_SYNTAX_ERROR	   	      	    	= 52,
197 	ESC_TOO_MANY_RECIPIENTS	   	      	    	= 53,
198 	ESC_INVALID_COMMAND_ARGUMENTS  	      	    	= 54,
199 	ESC_WRONG_PROTOCOL_VERSION  	      	    	= 55,
200 
201 	/* 6.x */
202 	ESC_OTHER_MEDIA_ERROR   	      	    	= 60,
203 	ESC_MEDIA_NOT_SUPPORTED   	      	    	= 61,
204 	ESC_CONVERSION_REQUIRED_AND_PROHIBITED		= 62,
205 	ESC_CONVERSION_REQUIRED_BUT_NOT_SUPPORTED      	= 63,
206 	ESC_CONVERSION_WITH_LOSS_PERFORMED	     	= 64,
207 	ESC_CONVERSION_FAILED			     	= 65,
208 
209 	/* 7.x */
210 	ESC_OTHER_SECURITY_STATUS      		     	= 70,
211 	ESC_DELIVERY_NOT_AUTHORIZED_MESSAGE_REFUSED	= 71,
212 	ESC_MAILING_LIST_EXPANSION_PROHIBITED		= 72,
213 	ESC_SECURITY_CONVERSION_REQUIRED_NOT_POSSIBLE  	= 73,
214 	ESC_SECURITY_FEATURES_NOT_SUPPORTED	  	= 74,
215 	ESC_CRYPTOGRAPHIC_FAILURE			= 75,
216 	ESC_CRYPTOGRAPHIC_ALGORITHM_NOT_SUPPORTED	= 76,
217 	ESC_MESSAGE_INTEGRITY_FAILURE			= 77,
218 };
219 
220 enum enhanced_status_class {
221 	ESC_STATUS_OK		= 2,
222 	ESC_STATUS_TEMPFAIL	= 4,
223 	ESC_STATUS_PERMFAIL	= 5,
224 };
225 
226 static inline uint32_t
evpid_to_msgid(uint64_t evpid)227 evpid_to_msgid(uint64_t evpid)
228 {
229 	return (evpid >> 32);
230 }
231 
232 static inline uint64_t
msgid_to_evpid(uint32_t msgid)233 msgid_to_evpid(uint32_t msgid)
234 {
235         return ((uint64_t)msgid << 32);
236 }
237 
238 
239 /* esc.c */
240 const char *esc_code(enum enhanced_status_class, enum enhanced_status_code);
241 const char *esc_description(enum enhanced_status_code);
242 
243 
244 /* queue */
245 void queue_api_on_close(int(*)(void));
246 void queue_api_on_message_create(int(*)(uint32_t *));
247 void queue_api_on_message_commit(int(*)(uint32_t, const char*));
248 void queue_api_on_message_delete(int(*)(uint32_t));
249 void queue_api_on_message_fd_r(int(*)(uint32_t));
250 void queue_api_on_envelope_create(int(*)(uint32_t, const char *, size_t, uint64_t *));
251 void queue_api_on_envelope_delete(int(*)(uint64_t));
252 void queue_api_on_envelope_update(int(*)(uint64_t, const char *, size_t));
253 void queue_api_on_envelope_load(int(*)(uint64_t, char *, size_t));
254 void queue_api_on_envelope_walk(int(*)(uint64_t *, char *, size_t));
255 void queue_api_on_message_walk(int(*)(uint64_t *, char *, size_t,
256     uint32_t, int *, void **));
257 void queue_api_no_chroot(void);
258 void queue_api_set_chroot(const char *);
259 void queue_api_set_user(const char *);
260 int queue_api_dispatch(void);
261 
262 /* scheduler */
263 void scheduler_api_on_init(int(*)(void));
264 void scheduler_api_on_insert(int(*)(struct scheduler_info *));
265 void scheduler_api_on_commit(size_t(*)(uint32_t));
266 void scheduler_api_on_rollback(size_t(*)(uint32_t));
267 void scheduler_api_on_update(int(*)(struct scheduler_info *));
268 void scheduler_api_on_delete(int(*)(uint64_t));
269 void scheduler_api_on_hold(int(*)(uint64_t, uint64_t));
270 void scheduler_api_on_release(int(*)(int, uint64_t, int));
271 void scheduler_api_on_batch(int(*)(int, int *, size_t *, uint64_t *, int *));
272 void scheduler_api_on_messages(size_t(*)(uint32_t, uint32_t *, size_t));
273 void scheduler_api_on_envelopes(size_t(*)(uint64_t, struct evpstate *, size_t));
274 void scheduler_api_on_schedule(int(*)(uint64_t));
275 void scheduler_api_on_remove(int(*)(uint64_t));
276 void scheduler_api_on_suspend(int(*)(uint64_t));
277 void scheduler_api_on_resume(int(*)(uint64_t));
278 void scheduler_api_no_chroot(void);
279 void scheduler_api_set_chroot(const char *);
280 void scheduler_api_set_user(const char *);
281 int scheduler_api_dispatch(void);
282 
283 /* table */
284 void table_api_on_update(int(*)(void));
285 void table_api_on_check(int(*)(int, struct dict *, const char *));
286 void table_api_on_lookup(int(*)(int, struct dict *, const char *, char *, size_t));
287 void table_api_on_fetch(int(*)(int, struct dict *, char *, size_t));
288 int table_api_dispatch(void);
289 const char *table_api_get_name(void);
290 
291 #endif
292