]> git.pld-linux.org Git - packages/postfix.git/blame - postfix-ident.patch
- ident lookup support for postfix
[packages/postfix.git] / postfix-ident.patch
CommitLineData
949c99f8
JR
1Based on patch by: James F. Hranicky (jfhcise.ufl.edu)
2
3diff -urN -x '*~' -x '*.orig' postfix-2.2.5/src/global/mail_params.h postfix-2.2.5-ident/src/global/mail_params.h
4--- postfix-2.2.5/src/global/mail_params.h 2006-02-15 23:44:13.000000000 +0100
5+++ postfix-2.2.5-ident/src/global/mail_params.h 2006-02-15 23:30:50.000000000 +0100
6@@ -2346,6 +2346,9 @@
7 #define DEF_SMTP_EHLO_DIS_MAPS ""
8 extern char *var_smtp_ehlo_dis_maps;
9
10+#define VAR_SMTPD_IDENT_LOOKUP "smtpd_ident_lookup"
11+#define DEF_SMTPD_IDENT_LOOKUP 0
12+extern bool var_smtpd_ident_lookup;
13 /*
14 * SMTPD messages
15 */
16Files postfix-2.2.5/src/smtpd/.smtpd_peer.c.swp and postfix-2.2.5-ident/src/smtpd/.smtpd_peer.c.swp differ
17diff -urN -x '*~' -x '*.orig' postfix-2.2.5/src/smtpd/Makefile.in postfix-2.2.5-ident/src/smtpd/Makefile.in
18--- postfix-2.2.5/src/smtpd/Makefile.in 2005-04-29 23:12:28.000000000 +0200
19+++ postfix-2.2.5-ident/src/smtpd/Makefile.in 2006-02-15 22:09:42.000000000 +0100
20@@ -1,10 +1,10 @@
21 SHELL = /bin/sh
22 SRCS = smtpd.c smtpd_token.c smtpd_check.c smtpd_chat.c smtpd_state.c \
23 smtpd_peer.c smtpd_sasl_proto.c smtpd_sasl_glue.c smtpd_proxy.c \
24- smtpd_xforward.c
25+ smtpd_xforward.c smtpd_ident.c
26 OBJS = smtpd.o smtpd_token.o smtpd_check.o smtpd_chat.o smtpd_state.o \
27 smtpd_peer.o smtpd_sasl_proto.o smtpd_sasl_glue.o smtpd_proxy.o \
28- smtpd_xforward.o
29+ smtpd_xforward.o smtpd_ident.o
30 HDRS = smtpd_token.h smtpd_check.h smtpd_chat.h smtpd_sasl_proto.h \
31 smtpd_sasl_glue.h smtpd_proxy.h
32 TESTSRC = smtpd_token_test.c
33diff -urN -x '*~' -x '*.orig' postfix-2.2.5/src/smtpd/smtpd.c postfix-2.2.5-ident/src/smtpd/smtpd.c
34--- postfix-2.2.5/src/smtpd/smtpd.c 2006-02-15 23:44:13.000000000 +0100
35+++ postfix-2.2.5-ident/src/smtpd/smtpd.c 2006-02-15 22:31:33.000000000 +0100
36@@ -900,6 +900,7 @@
37 char *var_local_rwr_clients;
38 char *var_smtpd_ehlo_dis_words;
39 char *var_smtpd_ehlo_dis_maps;
40+bool var_smtpd_ident_lookup;
41
42 bool var_smtpd_use_tls;
43 bool var_smtpd_enforce_tls;
44@@ -1951,10 +1952,18 @@
45 * intermediate proxy.
46 */
47 if (!state->proxy || state->xforward.flags == 0) {
48- out_fprintf(out_stream, REC_TYPE_NORM,
49- "Received: from %s (%s [%s])",
50- state->helo_name ? state->helo_name : state->name,
51- state->name, state->rfc_addr);
52+ if (var_smtpd_ident_lookup) {
53+ out_fprintf(out_stream, REC_TYPE_NORM,
54+ "Received: from %s (%s [%s] ident=%s)",
55+ state->helo_name ? state->helo_name : state->name,
56+ state->name, state->rfc_addr,
57+ state->ident_user);
58+ } else {
59+ out_fprintf(out_stream, REC_TYPE_NORM,
60+ "Received: from %s (%s [%s])",
61+ state->helo_name ? state->helo_name : state->name,
62+ state->name, state->rfc_addr);
63+ }
64 #ifdef USE_TLS
65 if (var_smtpd_tls_received_header && state->tls_context) {
66 out_fprintf(out_stream, REC_TYPE_NORM,
67@@ -3375,6 +3384,7 @@
68 VAR_SMTPD_USE_TLS, DEF_SMTPD_USE_TLS, &var_smtpd_use_tls,
69 VAR_SMTPD_ENFORCE_TLS, DEF_SMTPD_ENFORCE_TLS, &var_smtpd_enforce_tls,
70 VAR_SMTPD_TLS_WRAPPER, DEF_SMTPD_TLS_WRAPPER, &var_smtpd_tls_wrappermode,
71+ VAR_SMTPD_IDENT_LOOKUP, DEF_SMTPD_IDENT_LOOKUP, &var_smtpd_ident_lookup,
72 #ifdef USE_TLS
73 VAR_SMTPD_TLS_AUTH_ONLY, DEF_SMTPD_TLS_AUTH_ONLY, &var_smtpd_tls_auth_only,
74 VAR_SMTPD_TLS_ACERT, DEF_SMTPD_TLS_ACERT, &var_smtpd_tls_ask_ccert,
75diff -urN -x '*~' -x '*.orig' postfix-2.2.5/src/smtpd/smtpd.h postfix-2.2.5-ident/src/smtpd/smtpd.h
76--- postfix-2.2.5/src/smtpd/smtpd.h 2005-01-30 22:45:31.000000000 +0100
77+++ postfix-2.2.5-ident/src/smtpd/smtpd.h 2006-02-15 21:11:46.000000000 +0100
78@@ -75,6 +75,7 @@
79 char *addr; /* client host address string */
80 char *namaddr; /* combined name and address */
81 char *rfc_addr; /* address for RFC 2821 */
82+ char *ident_user; /* user name returned by ident RFC 1413 */
83 struct sockaddr_storage sockaddr; /* binary client endpoint */
84 int peer_code; /* 2=ok, 4=soft, 5=hard */
85 int error_count; /* reset after DOT */
86@@ -232,6 +233,8 @@
87 extern void smtpd_peer_init(SMTPD_STATE *state);
88 extern void smtpd_peer_reset(SMTPD_STATE *state);
89
90+extern char *smtpd_ident(struct sockaddr_in *peer_addr, struct sockaddr_in *smtpd_addr);
91+
92 #define SMTPD_PEER_CODE_OK 2
93 #define SMTPD_PEER_CODE_TEMP 4
94 #define SMTPD_PEER_CODE_PERM 5
95diff -urN -x '*~' -x '*.orig' postfix-2.2.5/src/smtpd/smtpd_ident.c postfix-2.2.5-ident/src/smtpd/smtpd_ident.c
96--- postfix-2.2.5/src/smtpd/smtpd_ident.c 1970-01-01 01:00:00.000000000 +0100
97+++ postfix-2.2.5-ident/src/smtpd/smtpd_ident.c 2006-02-15 23:44:04.000000000 +0100
98@@ -0,0 +1,138 @@
99+#include <sys_defs.h>
100+#include <sys/socket.h>
101+#include <netinet/in.h>
102+#include <arpa/inet.h>
103+#include <stdio.h> /* strerror() */
104+#include <errno.h>
105+#include <string.h>
106+#include <mymalloc.h>
107+#include <sys/types.h>
108+#include <sys/time.h>
109+#include <unistd.h>
110+#include <vstream.h>
111+
112+#include <iostuff.h>
113+#include "smtpd.h"
114+
115+#define IDENT_MSGSIZE 256
116+#define IDENT_TIMEOUT 10
117+
118+#define CHOMP(STR) { char *tmp; tmp = STR; while (*tmp) { \
119+ if (*tmp == '\n' || *tmp == '\r') *tmp = '\0'; tmp++ ; } }
120+
121+char *smtpd_ident(struct sockaddr_in *peer_addr, struct sockaddr_in *smtpd_addr)
122+{
123+ int ident_sock;
124+ char ident_msg[IDENT_MSGSIZE + 1], *sp;
125+ char ident_user[IDENT_MSGSIZE + 1];
126+ struct sockaddr_in local_addr;
127+ struct sockaddr_in ident_addr;
128+ char *return_val;
129+ VSTREAM *ident_stream;
130+
131+ memset(ident_msg, 0, IDENT_MSGSIZE + 1);
132+ memset(ident_user, 0, IDENT_MSGSIZE + 1);
133+
134+ /*
135+ * Bind the local sockaddr to the same interface as smtpd before
136+ * connecting back to the auth port on the peer. This helps
137+ * with multihomed postfix servers. First, set up the address.
138+ */
139+
140+ /* Local sockname */
141+
142+ memset((char *) &local_addr, 0, sizeof(local_addr));
143+ local_addr.sin_family = AF_INET;
144+ memcpy((void *) &local_addr.sin_addr, (void *) &smtpd_addr->sin_addr, sizeof(local_addr.sin_addr));
145+
146+ /* Remote sockname + port */
147+
148+ memset((char *) &ident_addr, 0, sizeof(ident_addr));
149+ ident_addr.sin_family = AF_INET;
150+ memcpy((void *) &ident_addr.sin_addr, (void *) &peer_addr->sin_addr, sizeof(ident_addr.sin_addr));
151+ ident_addr.sin_port = htons(113);
152+
153+ do {
154+ /* socket call */
155+
156+ if ((ident_sock = socket(ident_addr.sin_family, SOCK_STREAM, 0)) < 0) {
157+ msg_warn("Can't allocate socket for ident lookup: %s", strerror(errno));
158+ break;
159+ }
160+
161+ /* Now bind the local sock to the interface */
162+
163+ if (bind(ident_sock, (struct sockaddr *)&local_addr, sizeof(local_addr)) < 0) {
164+ msg_warn("local bind of ident sock failed: %s", strerror(errno));
165+ break;
166+ }
167+
168+ /* connect() back to the smtp client host on port 113 */
169+
170+ if (connect(ident_sock, (struct sockaddr *) &ident_addr, sizeof(ident_addr )) < 0) {
171+ msg_warn( "ident connect to %s: %s", inet_ntoa(peer_addr->sin_addr),
172+ strerror(errno));
173+ break;
174+ }
175+
176+ /* Ok, make this a vstream */
177+
178+ ident_stream = vstream_fdopen(ident_sock, O_RDWR);
179+ ident_stream->timeout = IDENT_TIMEOUT;
180+
181+ /* Print the ident message to the remote host */
182+
183+ vstream_fprintf(ident_stream, "%d, %d\n", ntohs(peer_addr->sin_port), ntohs(smtpd_addr->sin_port));
184+ if (vstream_ftimeout(ident_stream)) {
185+ msg_warn( "ident write timed out to %s", inet_ntoa(peer_addr->sin_addr));
186+ break;
187+ }
188+
189+ /* Read back the result */
190+
191+ vstream_fread(ident_stream, ident_msg, IDENT_MSGSIZE);
192+ if (vstream_ftimeout(ident_stream)) {
193+ msg_warn( "ident read timed out to %s", inet_ntoa(peer_addr->sin_addr));
194+ break;
195+ }
196+
197+ /*
198+ * Should I even bother with this?
199+ *
200+ * Even if so, don't worry about this failing, set the timeout low
201+ */
202+
203+ ident_stream->timeout = 2;
204+ vstream_fwrite(ident_stream, "quit\n", strlen("quit\n"));
205+
206+ if (strlen(ident_msg) == 0) {
207+ msg_warn( "Failed to get ident string from %s", inet_ntoa(peer_addr->sin_addr));
208+ break;
209+ }
210+
211+ if ((sp = strrchr(ident_msg, ':')) == NULL) {
212+ msg_warn( "Invalid ident string from %s", inet_ntoa(peer_addr->sin_addr));
213+ break;
214+ }
215+ sp++;
216+ CHOMP(sp);
217+ while (*sp && (*sp == ' ' || *sp == '\t')) {
218+ sp++;
219+ }
220+
221+ /* If we break before this line, we know we had some sort of bad error */
222+
223+ strncpy(ident_user, sp, IDENT_MSGSIZE);
224+ msg_info( "Received ident string %s from %s", sp, inet_ntoa(peer_addr->sin_addr));
225+
226+ } while (0);
227+
228+ if (strlen(ident_user) == 0) {
229+ msg_warn( "Failed to get ident user for %s", inet_ntoa(peer_addr->sin_addr));
230+ return NULL;
231+ }
232+
233+ vstream_fclose(ident_stream);
234+ return_val = mystrdup(ident_user);
235+ return return_val;
236+}
237diff -urN -x '*~' -x '*.orig' postfix-2.2.5/src/smtpd/smtpd_peer.c postfix-2.2.5-ident/src/smtpd/smtpd_peer.c
238--- postfix-2.2.5/src/smtpd/smtpd_peer.c 2005-01-30 22:42:18.000000000 +0100
239+++ postfix-2.2.5-ident/src/smtpd/smtpd_peer.c 2006-02-15 23:29:08.000000000 +0100
240@@ -56,6 +56,7 @@
241
242 #include <sys_defs.h>
243 #include <sys/socket.h>
244+#include <sys/types.h>
245 #include <netinet/in.h>
246 #include <arpa/inet.h>
247 #include <stdio.h> /* strerror() */
248@@ -75,6 +76,7 @@
249 /* Global library. */
250
251 #include <mail_proto.h>
252+#include <mail_params.h>
253 #include <valid_mailhost_addr.h>
254
255 /* Application-specific. */
256@@ -88,6 +90,8 @@
257 char *myname = "smtpd_peer_init";
258 SOCKADDR_SIZE sa_len;
259 struct sockaddr *sa;
260+ struct sockaddr_in serv_sin;
261+ char *ident_user = NULL;
262 INET_PROTO_INFO *proto_info = inet_proto_info();
263
264 sa = (struct sockaddr *) & (state->sockaddr);
265@@ -108,6 +112,9 @@
266 state->addr = mystrdup(CLIENT_ADDR_UNKNOWN);
267 state->rfc_addr = mystrdup(CLIENT_ADDR_UNKNOWN);
268 state->peer_code = SMTPD_PEER_CODE_PERM;
269+ if (var_smtpd_ident_lookup) {
270+ state->ident_user = mystrdup("NO-USER");
271+ }
272 }
273
274 /*
275@@ -218,6 +225,9 @@
276 if (aierr) {
277 msg_warn("%s: hostname %s verification failed: %s",
278 state->addr, state->name, MAI_STRERROR(aierr));
279+ if (var_smtpd_ident_lookup) {
280+ state->ident_user = mystrdup("NO-USER");
281+ }
282 REJECT_PEER_NAME(state, (TEMP_AI_ERROR(aierr) ?
283 SMTPD_PEER_CODE_TEMP : SMTPD_PEER_CODE_PERM));
284 } else {
285@@ -239,6 +249,19 @@
286 freeaddrinfo(res0);
287 }
288 }
289+
290+ if (var_smtpd_ident_lookup) {
291+ /* If getsockname fails, just forget it */
292+ sa_len = sizeof(serv_sin);
293+ if (getsockname(vstream_fileno(state->client), (struct sockaddr *)&serv_sin, &sa_len) >= 0) {
294+ ident_user = smtpd_ident((struct sockaddr_in *)sa, &serv_sin);
295+ if (ident_user == NULL)
296+ state->ident_user = mystrdup("NO-USER");
297+ else
298+ state->ident_user = ident_user;
299+ } else
300+ msg_warn("getsockname failed while doing ident lookup: %s", strerror(errno));
301+ }
302 }
303
304 /*
305@@ -250,6 +273,9 @@
306 state->addr = mystrdup("127.0.0.1"); /* XXX bogus. */
307 state->rfc_addr = mystrdup("127.0.0.1");/* XXX bogus. */
308 state->peer_code = SMTPD_PEER_CODE_OK;
309+ if (var_smtpd_ident_lookup) {
310+ state->ident_user = mystrdup("NO-USER");
311+ }
312 }
313
314 /*
315@@ -267,4 +293,7 @@
316 myfree(state->addr);
317 myfree(state->namaddr);
318 myfree(state->rfc_addr);
319+ if (var_smtpd_ident_lookup) {
320+ myfree(state->ident_user);
321+ }
322 }
This page took 0.706083 seconds and 4 git commands to generate.