Check last received header against blocklists

pull/199/head
M66B 4 years ago
parent e45e0bb2bd
commit 8471b06dde

@ -3377,21 +3377,12 @@ class Core {
} }
boolean check_blocklist = prefs.getBoolean("check_blocklist", false); boolean check_blocklist = prefs.getBoolean("check_blocklist", false);
if (check_blocklist && !self) { if (check_blocklist && !EntityFolder.isOutgoing(folder.type))
List<Address> senders = new ArrayList<>(); try {
if (message.from != null) message.blocklist = DnsBlockList.isJunk(
senders.addAll(Arrays.asList(message.from)); context, imessage.getHeader("Received"));
if (message.reply != null) } catch (Throwable ex) {
senders.addAll(Arrays.asList(message.reply)); Log.w(folder.name, ex);
boolean blocklist = false;
for (Address sender : senders) {
String email = ((InternetAddress) sender).getAddress();
if (DnsBlockList.isJunk(context, email)) {
blocklist = true;
break;
}
}
message.blocklist = blocklist;
} }
try { try {

@ -35,8 +35,11 @@ import java.util.Collections;
import java.util.Date; import java.util.Date;
import java.util.Hashtable; import java.util.Hashtable;
import java.util.List; import java.util.List;
import java.util.Locale;
import java.util.Map; import java.util.Map;
import javax.mail.internet.MimeUtility;
public class DnsBlockList { public class DnsBlockList {
static final List<BlockList> BLOCKLISTS = Collections.unmodifiableList(Arrays.asList( static final List<BlockList> BLOCKLISTS = Collections.unmodifiableList(Arrays.asList(
// https://www.spamhaus.org/zen/ // https://www.spamhaus.org/zen/
@ -115,46 +118,61 @@ public class DnsBlockList {
return names; return names;
} }
static boolean isJunk(Context context, String email) { static Boolean isJunk(Context context, String[] received) {
if (TextUtils.isEmpty(email)) if (received == null || received.length == 0)
return false; return null;
int at = email.indexOf('@'); String h = MimeUtility.unfold(received[received.length - 1]);
if (at < 0) String[] words = h.split("\\s+");
return false; for (int i = 0; i < words.length - 1; i++)
if ("from".equalsIgnoreCase(words[i])) {
String host = words[i + 1].toLowerCase(Locale.ROOT);
if (!TextUtils.isEmpty(host))
return isJunk(context, host, BLOCKLISTS);
}
return isJunk(context, email.substring(at + 1), BLOCKLISTS); return null;
} }
private static boolean isJunk(Context context, String domain, List<BlockList> blocklists) { private static boolean isJunk(Context context, String host, List<BlockList> blocklists) {
synchronized (cache) { synchronized (cache) {
CacheEntry entry = cache.get(domain); CacheEntry entry = cache.get(host);
if (entry != null && !entry.isExpired()) if (entry != null && !entry.isExpired())
return entry.isJunk(); return entry.isJunk();
} }
boolean blocked = false; boolean blocked = false;
for (BlockList blocklist : blocklists) for (BlockList blocklist : blocklists)
if (isEnabled(context, blocklist) && isJunk(domain, blocklist)) { if (isEnabled(context, blocklist) && isJunk(host, blocklist)) {
blocked = true; blocked = true;
break; break;
} }
synchronized (cache) { synchronized (cache) {
cache.put(domain, new CacheEntry(blocked)); cache.put(host, new CacheEntry(blocked));
} }
return blocked; return blocked;
} }
private static boolean isJunk(String domain, BlockList blocklist) { private static boolean isJunk(String host, BlockList blocklist) {
boolean numeric = host.startsWith("[") && host.endsWith("]");
if (numeric)
host = host.substring(1, host.length() - 1);
try { try {
if (blocklist.numeric) { if (blocklist.numeric) {
long start = new Date().getTime(); long start = new Date().getTime();
InetAddress[] addresses = InetAddress.getAllByName(domain); InetAddress[] addresses = InetAddress.getAllByName(host);
long elapsed = new Date().getTime() - start; long elapsed = new Date().getTime() - start;
Log.i("isJunk resolved=" + domain + " elapse=" + elapsed + " ms"); Log.i("isJunk resolved=" + host + " elapse=" + elapsed + " ms");
for (InetAddress addr : addresses) for (InetAddress addr : addresses) {
if (addr.isLoopbackAddress() ||
addr.isLinkLocalAddress() ||
addr.isSiteLocalAddress() ||
addr.isMulticastAddress()) {
Log.i("isJunk local=" + addr);
continue;
}
try { try {
StringBuilder lookup = new StringBuilder(); StringBuilder lookup = new StringBuilder();
if (addr instanceof Inet4Address) { if (addr instanceof Inet4Address) {
@ -177,9 +195,10 @@ public class DnsBlockList {
} catch (Throwable ex) { } catch (Throwable ex) {
Log.w(ex); Log.w(ex);
} }
} else { }
} else if (!numeric) {
long start = new Date().getTime(); long start = new Date().getTime();
String lookup = domain + "." + blocklist.address; String lookup = host + "." + blocklist.address;
boolean junk = isJunk(lookup, blocklist.responses); boolean junk = isJunk(lookup, blocklist.responses);
long elapsed = new Date().getTime() - start; long elapsed = new Date().getTime() - start;
Log.i("isJunk" + " " + lookup + "=" + junk + " elapsed=" + elapsed); Log.i("isJunk" + " " + lookup + "=" + junk + " elapsed=" + elapsed);

Loading…
Cancel
Save