@@ -202,6 +202,8 @@ if (cb->rc == DNS_SUCCEED)
202202 {
203203 dns_address * da = NULL ;
204204 uschar * addlist = cb -> rhs -> address ;
205+ uschar * orig_dnslist_domain = NULL ;
206+ int filter_rc = FAIL ;
205207
206208 /* For A and AAAA records, there may be multiple addresses from multiple
207209 records. For A6 records (currently not expected to be used) there may be
@@ -213,6 +215,76 @@ if (cb->rc == DNS_SUCCEED)
213215 HDEBUG (D_dnsbl ) debug_printf ("DNS lookup for %s succeeded (yielding %s)\n" ,
214216 query , addlist );
215217
218+ /* Make dnslist_domain available to dnslist_valid_addresses expansion. */
219+ orig_dnslist_domain = dnslist_domain ;
220+ dnslist_domain = domain_txt ;
221+
222+ for (da = cb -> rhs ; da ; da = da -> next )
223+ {
224+ switch (verify_check_this_host (& dnslist_valid_addresses , NULL , US "" , da -> address , NULL ))
225+ {
226+ case OK :
227+ da -> dnsbl_invalid = FALSE;
228+
229+ if (filter_rc != DEFER )
230+ filter_rc = OK ;
231+ break ;
232+
233+ case FAIL :
234+ da -> dnsbl_invalid = TRUE;
235+ addlist = NULL ;
236+
237+ log_write (0 , LOG_MAIN ,
238+ "DNS list lookup for %s at %s returned %s;"
239+ " invalid address discarded" ,
240+ keydomain , domain , da -> address );
241+ break ;
242+
243+ case DEFER :
244+ log_write (0 , LOG_MAIN ,
245+ "DNS list lookup for %s at %s returned %s;"
246+ " unable to verify, returned DEFER" ,
247+ keydomain , domain , da -> address );
248+
249+ filter_rc = DEFER ;
250+ break ;
251+ }
252+ }
253+
254+ dnslist_domain = orig_dnslist_domain ;
255+
256+ if (filter_rc == FAIL )
257+ {
258+ HDEBUG (D_dnsbl )
259+ {
260+ debug_printf ("=> all addresses are invalid\n" );
261+ debug_printf ("=> that means %s is not listed at %s\n" ,
262+ keydomain , domain );
263+ }
264+ }
265+
266+ if (filter_rc != OK ) return filter_rc ;
267+
268+ /* Need to recreate addlist without filtered addresses. */
269+ if (addlist == NULL )
270+ {
271+ for (da = cb -> rhs ; da ; da = da -> next )
272+ {
273+ if (da -> dnsbl_invalid )
274+ continue ;
275+
276+ if (addlist == NULL )
277+ addlist = da -> address ;
278+ else
279+ addlist = string_sprintf ("%s, %s" , addlist , da -> address );
280+ }
281+
282+ HDEBUG (D_dnsbl )
283+ {
284+ debug_printf ("=> updated address list: %s\n" , addlist );
285+ }
286+ }
287+
216288 /* Address list check; this can be either for equality, or via a bitmask.
217289 In the latter case, all the bits must match. */
218290
@@ -224,6 +296,9 @@ if (cb->rc == DNS_SUCCEED)
224296 const uschar * ptr = iplist ;
225297 uschar * res ;
226298
299+ if (da -> dnsbl_invalid )
300+ continue ;
301+
227302 /* Handle exact matching */
228303
229304 if (!bitmask )
@@ -248,14 +323,7 @@ if (cb->rc == DNS_SUCCEED)
248323 We change this only for IPv4 addresses in the list. */
249324
250325 if (host_aton (da -> address , address ) == 1 )
251- if ((address [0 ] & 0xff000000 ) != 0x7f000000 ) /* 127.0.0.0/8 */
252- log_write (0 , LOG_MAIN ,
253- "DNS list lookup for %s at %s returned %s;"
254- " not in 127.0/8 and discarded" ,
255- keydomain , domain , da -> address );
256-
257- else
258- mask = address [0 ];
326+ mask = address [0 ];
259327
260328 /* Scan the returned addresses, skipping any that are IPv6 */
261329
@@ -309,29 +377,6 @@ if (cb->rc == DNS_SUCCEED)
309377 }
310378 }
311379
312- /* No address list check; discard any illegal returns and give up if
313- none remain. */
314-
315- else
316- {
317- BOOL ok = FALSE;
318- for (da = cb -> rhs ; da ; da = da -> next )
319- {
320- int address [4 ];
321-
322- if ( host_aton (da -> address , address ) == 1 /* ipv4 */
323- && (address [0 ] & 0xff000000 ) == 0x7f000000 /* 127.0.0.0/8 */
324- )
325- ok = TRUE;
326- else
327- log_write (0 , LOG_MAIN ,
328- "DNS list lookup for %s at %s returned %s;"
329- " not in 127.0/8 and discarded" ,
330- keydomain , domain , da -> address );
331- }
332- if (!ok ) return FAIL ;
333- }
334-
335380 /* Either there was no IP list, or the record matched, implying that the
336381 domain is on the list. We now want to find a corresponding TXT record. If an
337382 alternate domain is specified for the TXT record, call this function
0 commit comments