aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/main/java/de/measite/minidns/Client.java87
-rw-r--r--src/main/java/de/measite/minidns/DNSMessage.java14
2 files changed, 92 insertions, 9 deletions
diff --git a/src/main/java/de/measite/minidns/Client.java b/src/main/java/de/measite/minidns/Client.java
index 26e3ba01..3f152346 100644
--- a/src/main/java/de/measite/minidns/Client.java
+++ b/src/main/java/de/measite/minidns/Client.java
@@ -13,12 +13,12 @@ import java.security.SecureRandom;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashSet;
+import java.util.LinkedHashMap;
+import java.util.Map.Entry;
import java.util.Random;
import java.util.logging.Level;
import java.util.logging.Logger;
-import org.jxmpp.util.cache.ExpirationCache;
-
import de.measite.minidns.Record.CLASS;
import de.measite.minidns.Record.TYPE;
@@ -30,9 +30,6 @@ public class Client {
private static final Logger LOGGER = Logger.getLogger(Client.class.getName());
- protected static final ExpirationCache<Question, DNSMessage> cache = new ExpirationCache<Question, DNSMessage>(
- 10, 1000 * 60 * 60 * 24);
-
/**
* The internal random class for sequence generation.
*/
@@ -49,6 +46,16 @@ public class Client {
protected int timeout = 5000;
/**
+ * The internal DNS cache.
+ */
+ protected LinkedHashMap<Question, DNSMessage> cache;
+
+ /**
+ * Maximum acceptable ttl.
+ */
+ protected long maxTTL = 60 * 60 * 1000;
+
+ /**
* Create a new DNS client.
*/
public Client() {
@@ -57,6 +64,7 @@ public class Client {
} catch (NoSuchAlgorithmException e1) {
random = new SecureRandom();
}
+ setCacheSize(10);
}
/**
@@ -123,9 +131,20 @@ public class Client {
* @throws IOException On IOErrors.
*/
public DNSMessage query(Question q, String host, int port) throws IOException {
- DNSMessage dnsMessage = cache.get(q);
- if (dnsMessage != null) {
- return dnsMessage;
+ DNSMessage dnsMessage = (cache == null) ? null : cache.get(q);
+ if (dnsMessage != null && dnsMessage.getReceiveTimestamp() > 0l) {
+ // check the ttl
+ long ttl = maxTTL;
+ for (Record r : dnsMessage.getAnswers()) {
+ ttl = Math.min(ttl, r.ttl);
+ }
+ for (Record r : dnsMessage.getAdditionalResourceRecords()) {
+ ttl = Math.min(ttl, r.ttl);
+ }
+ if (dnsMessage.getReceiveTimestamp() + ttl <
+ System.currentTimeMillis()) {
+ return dnsMessage;
+ }
}
DNSMessage message = new DNSMessage();
message.setQuestions(new Question[]{q});
@@ -145,7 +164,9 @@ public class Client {
}
for (Record record : dnsMessage.getAnswers()) {
if (record.isAnswer(q)) {
- cache.put(q, dnsMessage, record.ttl);
+ if (cache != null) {
+ cache.put(q, dnsMessage);
+ }
break;
}
}
@@ -305,4 +326,52 @@ public class Client {
return null;
}
+ /**
+ * Configure the cache size (default 10).
+ * @param maximumSize The new cache size or 0 to disable.
+ */
+ @SuppressWarnings("serial")
+ public void setCacheSize(final int maximumSize) {
+ if (maximumSize == 0) {
+ this.cache = null;
+ } else {
+ LinkedHashMap<Question,DNSMessage> old = cache;
+ cache = new LinkedHashMap<Question,DNSMessage>() {
+ @Override
+ protected boolean removeEldestEntry(
+ Entry<Question, DNSMessage> eldest) {
+ return size() > maximumSize;
+ }
+ };
+ if (old != null) {
+ cache.putAll(old);
+ }
+ }
+ }
+
+ /**
+ * Flush the DNS cache.
+ */
+ public void flushCache() {
+ if (cache != null) {
+ cache.clear();
+ }
+ }
+
+ /**
+ * Get the current maximum record ttl.
+ * @return The maximum record ttl.
+ */
+ public long getMaxTTL() {
+ return maxTTL;
+ }
+
+ /**
+ * Set the maximum record ttl.
+ * @param maxTTL The new maximum ttl.
+ */
+ public void setMaxTTL(long maxTTL) {
+ this.maxTTL = maxTTL;
+ }
+
}
diff --git a/src/main/java/de/measite/minidns/DNSMessage.java b/src/main/java/de/measite/minidns/DNSMessage.java
index ea1b25c8..977c08d0 100644
--- a/src/main/java/de/measite/minidns/DNSMessage.java
+++ b/src/main/java/de/measite/minidns/DNSMessage.java
@@ -196,6 +196,11 @@ public class DNSMessage {
protected Record additionalResourceRecords[];
/**
+ * The receive timestamp of this message.
+ */
+ protected long receiveTimestamp;
+
+ /**
* Retrieve the current DNS message id.
* @return The current DNS message id.
*/
@@ -212,6 +217,14 @@ public class DNSMessage {
}
/**
+ * Get the receive timestamp if this message was created via parse.
+ * This should be used to evaluate TTLs.
+ */
+ public long getReceiveTimestamp() {
+ return receiveTimestamp;
+ }
+
+ /**
* Retrieve the query type (true or false;
* @return True if this DNS message is a query.
*/
@@ -410,6 +423,7 @@ public class DNSMessage {
message.authenticData = ((header >> 5) & 1) == 1;
message.checkDisabled = ((header >> 4) & 1) == 1;
message.responseCode = RESPONSE_CODE.getResponseCode(header & 0xf);
+ message.receiveTimestamp = System.currentTimeMillis();
int questionCount = dis.readUnsignedShort();
int answerCount = dis.readUnsignedShort();
int nameserverCount = dis.readUnsignedShort();