Replace Handler with Executor for async DNS API
Bug: 124882626
Test: built, flashed, booted
atest DnsResolverTest DnsPacketTest
Change-Id: Ie1dc27643d4767f2a8a39da755edf388a00962d5
diff --git a/core/java/android/net/DnsResolver.java b/core/java/android/net/DnsResolver.java
index f248958..93b8cf8 100644
--- a/core/java/android/net/DnsResolver.java
+++ b/core/java/android/net/DnsResolver.java
@@ -22,11 +22,11 @@
import static android.os.MessageQueue.OnFileDescriptorEventListener.EVENT_ERROR;
import static android.os.MessageQueue.OnFileDescriptorEventListener.EVENT_INPUT;
+import android.annotation.CallbackExecutor;
import android.annotation.IntDef;
import android.annotation.NonNull;
import android.annotation.Nullable;
-import android.os.Handler;
-import android.os.MessageQueue;
+import android.os.Looper;
import android.system.ErrnoException;
import android.util.Log;
@@ -37,6 +37,7 @@
import java.net.UnknownHostException;
import java.util.ArrayList;
import java.util.List;
+import java.util.concurrent.Executor;
/**
* Dns resolver class for asynchronous dns querying
@@ -182,20 +183,19 @@
}
/**
- * Pass in a blob and corresponding flags, get an answer back asynchronously
- * through {@link AnswerCallback}.
+ * Send a raw DNS query.
+ * The answer will be provided asynchronously through the provided {@link AnswerCallback}.
*
* @param network {@link Network} specifying which network for querying.
* {@code null} for query on default network.
* @param query blob message
* @param flags flags as a combination of the FLAGS_* constants
- * @param handler {@link Handler} to specify the thread
- * upon which the {@link AnswerCallback} will be invoked.
+ * @param executor The {@link Executor} that the callback should be executed on.
* @param callback an {@link AnswerCallback} which will be called to notify the caller
* of the result of dns query.
*/
public <T> void query(@Nullable Network network, @NonNull byte[] query, @QueryFlag int flags,
- @NonNull Handler handler, @NonNull AnswerCallback<T> callback) {
+ @NonNull @CallbackExecutor Executor executor, @NonNull AnswerCallback<T> callback) {
final FileDescriptor queryfd;
try {
queryfd = resNetworkSend((network != null
@@ -205,12 +205,12 @@
return;
}
- registerFDListener(handler.getLooper().getQueue(), queryfd, callback);
+ registerFDListener(executor, queryfd, callback);
}
/**
- * Pass in a domain name and corresponding setting, get an answer back asynchronously
- * through {@link AnswerCallback}.
+ * Send a DNS query with the specified name, class and query type.
+ * The answer will be provided asynchronously through the provided {@link AnswerCallback}.
*
* @param network {@link Network} specifying which network for querying.
* {@code null} for query on default network.
@@ -218,14 +218,13 @@
* @param nsClass dns class as one of the CLASS_* constants
* @param nsType dns resource record (RR) type as one of the TYPE_* constants
* @param flags flags as a combination of the FLAGS_* constants
- * @param handler {@link Handler} to specify the thread
- * upon which the {@link AnswerCallback} will be invoked.
+ * @param executor The {@link Executor} that the callback should be executed on.
* @param callback an {@link AnswerCallback} which will be called to notify the caller
* of the result of dns query.
*/
public <T> void query(@Nullable Network network, @NonNull String domain,
@QueryClass int nsClass, @QueryType int nsType, @QueryFlag int flags,
- @NonNull Handler handler, @NonNull AnswerCallback<T> callback) {
+ @NonNull @CallbackExecutor Executor executor, @NonNull AnswerCallback<T> callback) {
final FileDescriptor queryfd;
try {
queryfd = resNetworkQuery((network != null
@@ -234,33 +233,32 @@
callback.onQueryException(e);
return;
}
- registerFDListener(handler.getLooper().getQueue(), queryfd, callback);
+ registerFDListener(executor, queryfd, callback);
}
- private <T> void registerFDListener(@NonNull MessageQueue queue,
+ private <T> void registerFDListener(@NonNull Executor executor,
@NonNull FileDescriptor queryfd, @NonNull AnswerCallback<T> answerCallback) {
- queue.addOnFileDescriptorEventListener(
+ Looper.getMainLooper().getQueue().addOnFileDescriptorEventListener(
queryfd,
FD_EVENTS,
(fd, events) -> {
- byte[] answerbuf = null;
- try {
- // TODO: Implement result function in Java side instead of using JNI
- // Because JNI method close fd prior than unregistering fd on
- // event listener.
- answerbuf = resNetworkResult(fd);
- } catch (ErrnoException e) {
- Log.e(TAG, "resNetworkResult:" + e.toString());
- answerCallback.onQueryException(e);
- return 0;
- }
+ executor.execute(() -> {
+ byte[] answerbuf = null;
+ try {
+ answerbuf = resNetworkResult(fd);
+ } catch (ErrnoException e) {
+ Log.e(TAG, "resNetworkResult:" + e.toString());
+ answerCallback.onQueryException(e);
+ return;
+ }
- try {
- answerCallback.onAnswer(answerCallback.parser.parse(answerbuf));
- } catch (ParseException e) {
- answerCallback.onParseException(e);
- }
-
+ try {
+ answerCallback.onAnswer(
+ answerCallback.parser.parse(answerbuf));
+ } catch (ParseException e) {
+ answerCallback.onParseException(e);
+ }
+ });
// Unregister this fd listener
return 0;
});