From 1a1beee654a8ad06cc65be0e0f420249071236e5 Mon Sep 17 00:00:00 2001 From: Kangping Dong Date: Fri, 22 Sep 2023 18:32:02 +0800 Subject: [PATCH] [mdns] exclude mDNS advertiser code from standalone build test service-connectivity-mdns-standalone-build-test builds the mDNS discovery and advertisement implementation against API level 21. This stops the advertisement code from calling new NsdServiceInfo public or private APIs which are required by Thread. This commit removes the mDNS advertisement code from the standalone build to loose the check given this will never be used by GMS Core. Bug: 265095929 Test: verified that it can build with aosp/2608627 Change-Id: I32cfce7b994d51a4b4ec468e9f79ffc2be6635ff --- service-t/Android.bp | 7 ++- .../connectivity/mdns/MdnsAnnouncer.java | 2 +- .../connectivity/mdns/MdnsConstants.java | 7 ++- .../mdns/MdnsInterfaceAdvertiser.java | 4 +- .../connectivity/mdns/MdnsPacketRepeater.java | 20 +++---- .../server/connectivity/mdns/MdnsProber.java | 5 +- .../mdns/MdnsRecordRepository.java | 46 +++------------- .../connectivity/mdns/MdnsReplyInfo.java | 53 +++++++++++++++++++ .../connectivity/mdns/MdnsReplySender.java | 15 +++--- .../connectivity/mdns/MdnsAnnouncerTest.kt | 3 +- .../mdns/MdnsInterfaceAdvertiserTest.kt | 6 +-- .../connectivity/mdns/MdnsProberTest.kt | 9 ++-- 12 files changed, 106 insertions(+), 71 deletions(-) create mode 100644 service-t/src/com/android/server/connectivity/mdns/MdnsReplyInfo.java diff --git a/service-t/Android.bp b/service-t/Android.bp index 7e2d2f46a5..bc49f0e749 100644 --- a/service-t/Android.bp +++ b/service-t/Android.bp @@ -102,7 +102,12 @@ java_library { ], exclude_srcs: [ "src/com/android/server/connectivity/mdns/internal/SocketNetlinkMonitor.java", - "src/com/android/server/connectivity/mdns/SocketNetLinkMonitorFactory.java" + "src/com/android/server/connectivity/mdns/SocketNetLinkMonitorFactory.java", + "src/com/android/server/connectivity/mdns/MdnsAdvertiser.java", + "src/com/android/server/connectivity/mdns/MdnsAnnouncer.java", + "src/com/android/server/connectivity/mdns/MdnsInterfaceAdvertiser.java", + "src/com/android/server/connectivity/mdns/MdnsProber.java", + "src/com/android/server/connectivity/mdns/MdnsRecordRepository.java", ], static_libs: [ "net-utils-device-common-mdns-standalone-build-test", diff --git a/service-t/src/com/android/server/connectivity/mdns/MdnsAnnouncer.java b/service-t/src/com/android/server/connectivity/mdns/MdnsAnnouncer.java index d9bc64305f..5812797b71 100644 --- a/service-t/src/com/android/server/connectivity/mdns/MdnsAnnouncer.java +++ b/service-t/src/com/android/server/connectivity/mdns/MdnsAnnouncer.java @@ -110,7 +110,7 @@ public class MdnsAnnouncer extends MdnsPacketRepeater cb, @NonNull SharedLog sharedLog) { - super(looper, replySender, cb, sharedLog); + super(looper, replySender, cb, sharedLog, MdnsAdvertiser.DBG); } // TODO: Notify MdnsRecordRepository that the records were announced for that service ID, diff --git a/service-t/src/com/android/server/connectivity/mdns/MdnsConstants.java b/service-t/src/com/android/server/connectivity/mdns/MdnsConstants.java index 1251170d4a..b83a6a02e6 100644 --- a/service-t/src/com/android/server/connectivity/mdns/MdnsConstants.java +++ b/service-t/src/com/android/server/connectivity/mdns/MdnsConstants.java @@ -19,6 +19,7 @@ package com.android.server.connectivity.mdns; import static java.nio.charset.StandardCharsets.UTF_8; import java.net.InetAddress; +import java.net.InetSocketAddress; import java.net.UnknownHostException; import java.nio.charset.Charset; @@ -42,6 +43,10 @@ public final class MdnsConstants { public static final String SUBTYPE_PREFIX = "_"; private static final String MDNS_IPV4_HOST_ADDRESS = "224.0.0.251"; private static final String MDNS_IPV6_HOST_ADDRESS = "FF02::FB"; + public static final InetSocketAddress IPV6_SOCKET_ADDR = new InetSocketAddress( + getMdnsIPv6Address(), MDNS_PORT); + public static final InetSocketAddress IPV4_SOCKET_ADDR = new InetSocketAddress( + getMdnsIPv4Address(), MDNS_PORT); private static InetAddress mdnsAddress; private MdnsConstants() { } @@ -75,4 +80,4 @@ public final class MdnsConstants { public static Charset getUtf8Charset() { return UTF_8; } -} \ No newline at end of file +} diff --git a/service-t/src/com/android/server/connectivity/mdns/MdnsInterfaceAdvertiser.java b/service-t/src/com/android/server/connectivity/mdns/MdnsInterfaceAdvertiser.java index 40dfd571fa..37e9743f09 100644 --- a/service-t/src/com/android/server/connectivity/mdns/MdnsInterfaceAdvertiser.java +++ b/service-t/src/com/android/server/connectivity/mdns/MdnsInterfaceAdvertiser.java @@ -161,7 +161,7 @@ public class MdnsInterfaceAdvertiser implements MulticastPacketReader.PacketHand @NonNull SharedLog sharedLog) { return new MdnsReplySender(looper, socket, packetCreationBuffer, sharedLog.forSubComponent( - MdnsReplySender.class.getSimpleName() + "/" + interfaceTag)); + MdnsReplySender.class.getSimpleName() + "/" + interfaceTag), DBG); } /** @see MdnsAnnouncer */ @@ -370,7 +370,7 @@ public class MdnsInterfaceAdvertiser implements MulticastPacketReader.PacketHand // happen when the incoming packet has answer records (not a question), so there will be no // answer. One exception is simultaneous probe tiebreaking (rfc6762 8.2), in which case the // conflicting service is still probing and won't reply either. - final MdnsRecordRepository.ReplyInfo answers = mRecordRepository.getReply(packet, src); + final MdnsReplyInfo answers = mRecordRepository.getReply(packet, src); if (answers == null) return; mReplySender.queueReply(answers); diff --git a/service-t/src/com/android/server/connectivity/mdns/MdnsPacketRepeater.java b/service-t/src/com/android/server/connectivity/mdns/MdnsPacketRepeater.java index fd0f5c9eaf..e84ceadae6 100644 --- a/service-t/src/com/android/server/connectivity/mdns/MdnsPacketRepeater.java +++ b/service-t/src/com/android/server/connectivity/mdns/MdnsPacketRepeater.java @@ -16,8 +16,8 @@ package com.android.server.connectivity.mdns; -import static com.android.server.connectivity.mdns.MdnsRecordRepository.IPV4_ADDR; -import static com.android.server.connectivity.mdns.MdnsRecordRepository.IPV6_ADDR; +import static com.android.server.connectivity.mdns.MdnsConstants.IPV4_SOCKET_ADDR; +import static com.android.server.connectivity.mdns.MdnsConstants.IPV6_SOCKET_ADDR; import android.annotation.NonNull; import android.annotation.Nullable; @@ -38,9 +38,8 @@ import java.net.InetSocketAddress; */ @RequiresApi(Build.VERSION_CODES.TIRAMISU) public abstract class MdnsPacketRepeater { - private static final boolean DBG = MdnsAdvertiser.DBG; private static final InetSocketAddress[] ALL_ADDRS = new InetSocketAddress[] { - IPV4_ADDR, IPV6_ADDR + IPV4_SOCKET_ADDR, IPV6_SOCKET_ADDR }; @NonNull @@ -51,6 +50,7 @@ public abstract class MdnsPacketRepeater { private final PacketRepeaterCallback mCb; @NonNull private final SharedLog mSharedLog; + private final boolean mEnableDebugLog; /** * Status callback from {@link MdnsPacketRepeater}. @@ -111,7 +111,7 @@ public abstract class MdnsPacketRepeater { } final MdnsPacket packet = request.getPacket(index); - if (DBG) { + if (mEnableDebugLog) { mSharedLog.v("Sending packets for iteration " + index + " out of " + request.getNumSends() + " for ID " + msg.what); } @@ -134,7 +134,7 @@ public abstract class MdnsPacketRepeater { // likely not to be available since the device is in deep sleep anyway. final long delay = request.getDelayMs(nextIndex); sendMessageDelayed(obtainMessage(msg.what, nextIndex, 0, request), delay); - if (DBG) mSharedLog.v("Scheduled next packet in " + delay + "ms"); + if (mEnableDebugLog) mSharedLog.v("Scheduled next packet in " + delay + "ms"); } // Call onSent after scheduling the next run, to allow the callback to cancel it @@ -145,15 +145,17 @@ public abstract class MdnsPacketRepeater { } protected MdnsPacketRepeater(@NonNull Looper looper, @NonNull MdnsReplySender replySender, - @Nullable PacketRepeaterCallback cb, @NonNull SharedLog sharedLog) { + @Nullable PacketRepeaterCallback cb, @NonNull SharedLog sharedLog, + boolean enableDebugLog) { mHandler = new ProbeHandler(looper); mReplySender = replySender; mCb = cb; mSharedLog = sharedLog; + mEnableDebugLog = enableDebugLog; } protected void startSending(int id, @NonNull T request, long initialDelayMs) { - if (DBG) { + if (mEnableDebugLog) { mSharedLog.v("Starting send with id " + id + ", request " + request.getClass().getSimpleName() + ", delay " + initialDelayMs); } @@ -172,7 +174,7 @@ public abstract class MdnsPacketRepeater { // all in the handler queue; unless this method is called from a message, but the current // message cannot be cancelled. if (mHandler.hasMessages(id)) { - if (DBG) { + if (mEnableDebugLog) { mSharedLog.v("Stopping send on id " + id); } mHandler.removeMessages(id); diff --git a/service-t/src/com/android/server/connectivity/mdns/MdnsProber.java b/service-t/src/com/android/server/connectivity/mdns/MdnsProber.java index f2b562ace3..e88947ab53 100644 --- a/service-t/src/com/android/server/connectivity/mdns/MdnsProber.java +++ b/service-t/src/com/android/server/connectivity/mdns/MdnsProber.java @@ -40,9 +40,8 @@ public class MdnsProber extends MdnsPacketRepeater { private static final long CONFLICT_RETRY_DELAY_MS = 5_000L; public MdnsProber(@NonNull Looper looper, @NonNull MdnsReplySender replySender, - @NonNull PacketRepeaterCallback cb, - @NonNull SharedLog sharedLog) { - super(looper, replySender, cb, sharedLog); + @NonNull PacketRepeaterCallback cb, @NonNull SharedLog sharedLog) { + super(looper, replySender, cb, sharedLog, MdnsAdvertiser.DBG); } /** Probing request to send with {@link MdnsProber}. */ diff --git a/service-t/src/com/android/server/connectivity/mdns/MdnsRecordRepository.java b/service-t/src/com/android/server/connectivity/mdns/MdnsRecordRepository.java index f5323720c0..130ff485d1 100644 --- a/service-t/src/com/android/server/connectivity/mdns/MdnsRecordRepository.java +++ b/service-t/src/com/android/server/connectivity/mdns/MdnsRecordRepository.java @@ -16,6 +16,8 @@ package com.android.server.connectivity.mdns; +import static com.android.server.connectivity.mdns.MdnsConstants.IPV4_SOCKET_ADDR; +import static com.android.server.connectivity.mdns.MdnsConstants.IPV6_SOCKET_ADDR; import static com.android.server.connectivity.mdns.MdnsConstants.NO_PACKET; import android.annotation.NonNull; @@ -79,11 +81,6 @@ public class MdnsRecordRepository { private static final String[] DNS_SD_SERVICE_TYPE = new String[] { "_services", "_dns-sd", "_udp", LOCAL_TLD }; - public static final InetSocketAddress IPV6_ADDR = new InetSocketAddress( - MdnsConstants.getMdnsIPv6Address(), MdnsConstants.MDNS_PORT); - public static final InetSocketAddress IPV4_ADDR = new InetSocketAddress( - MdnsConstants.getMdnsIPv4Address(), MdnsConstants.MDNS_PORT); - @NonNull private final Random mDelayGenerator = new Random(); // Map of service unique ID -> records for service @@ -454,37 +451,6 @@ public class MdnsRecordRepository { return ret; } - /** - * Info about a reply to be sent. - */ - public static class ReplyInfo { - @NonNull - public final List answers; - @NonNull - public final List additionalAnswers; - public final long sendDelayMs; - @NonNull - public final InetSocketAddress destination; - - public ReplyInfo( - @NonNull List answers, - @NonNull List additionalAnswers, - long sendDelayMs, - @NonNull InetSocketAddress destination) { - this.answers = answers; - this.additionalAnswers = additionalAnswers; - this.sendDelayMs = sendDelayMs; - this.destination = destination; - } - - @Override - public String toString() { - return "{ReplyInfo to " + destination + ", answers: " + answers.size() - + ", additionalAnswers: " + additionalAnswers.size() - + ", sendDelayMs " + sendDelayMs + "}"; - } - } - /** * Get the reply to send to an incoming packet. * @@ -492,7 +458,7 @@ public class MdnsRecordRepository { * @param src The source address of the incoming packet. */ @Nullable - public ReplyInfo getReply(MdnsPacket packet, InetSocketAddress src) { + public MdnsReplyInfo getReply(MdnsPacket packet, InetSocketAddress src) { final long now = SystemClock.elapsedRealtime(); final boolean replyUnicast = (packet.flags & MdnsConstants.QCLASS_UNICAST) != 0; final ArrayList additionalAnswerRecords = new ArrayList<>(); @@ -543,9 +509,9 @@ public class MdnsRecordRepository { if (replyUnicast) { dest = src; } else if (src.getAddress() instanceof Inet4Address) { - dest = IPV4_ADDR; + dest = IPV4_SOCKET_ADDR; } else { - dest = IPV6_ADDR; + dest = IPV6_SOCKET_ADDR; } // Build the list of answer records from their RecordInfo @@ -559,7 +525,7 @@ public class MdnsRecordRepository { answerRecords.add(info.record); } - return new ReplyInfo(answerRecords, additionalAnswerRecords, delayMs, dest); + return new MdnsReplyInfo(answerRecords, additionalAnswerRecords, delayMs, dest); } /** diff --git a/service-t/src/com/android/server/connectivity/mdns/MdnsReplyInfo.java b/service-t/src/com/android/server/connectivity/mdns/MdnsReplyInfo.java new file mode 100644 index 0000000000..ce61b54493 --- /dev/null +++ b/service-t/src/com/android/server/connectivity/mdns/MdnsReplyInfo.java @@ -0,0 +1,53 @@ +/* + * Copyright (C) 2023 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.server.connectivity.mdns; + +import android.annotation.NonNull; + +import java.net.InetSocketAddress; +import java.util.List; + +/** + * Info about a mDNS reply to be sent. + */ +public final class MdnsReplyInfo { + @NonNull + public final List answers; + @NonNull + public final List additionalAnswers; + public final long sendDelayMs; + @NonNull + public final InetSocketAddress destination; + + public MdnsReplyInfo( + @NonNull List answers, + @NonNull List additionalAnswers, + long sendDelayMs, + @NonNull InetSocketAddress destination) { + this.answers = answers; + this.additionalAnswers = additionalAnswers; + this.sendDelayMs = sendDelayMs; + this.destination = destination; + } + + @Override + public String toString() { + return "{MdnsReplyInfo to " + destination + ", answers: " + answers.size() + + ", additionalAnswers: " + additionalAnswers.size() + + ", sendDelayMs " + sendDelayMs + "}"; + } +} diff --git a/service-t/src/com/android/server/connectivity/mdns/MdnsReplySender.java b/service-t/src/com/android/server/connectivity/mdns/MdnsReplySender.java index 3d64b5ab04..abf5d99518 100644 --- a/service-t/src/com/android/server/connectivity/mdns/MdnsReplySender.java +++ b/service-t/src/com/android/server/connectivity/mdns/MdnsReplySender.java @@ -26,7 +26,6 @@ import android.os.Looper; import android.os.Message; import com.android.net.module.util.SharedLog; -import com.android.server.connectivity.mdns.MdnsRecordRepository.ReplyInfo; import com.android.server.connectivity.mdns.util.MdnsUtils; import java.io.IOException; @@ -45,7 +44,6 @@ import java.util.Collections; */ @RequiresApi(Build.VERSION_CODES.TIRAMISU) public class MdnsReplySender { - private static final boolean DBG = MdnsAdvertiser.DBG; private static final int MSG_SEND = 1; private static final int PACKET_NOT_SENT = 0; private static final int PACKET_SENT = 1; @@ -58,24 +56,27 @@ public class MdnsReplySender { private final byte[] mPacketCreationBuffer; @NonNull private final SharedLog mSharedLog; + private final boolean mEnableDebugLog; public MdnsReplySender(@NonNull Looper looper, @NonNull MdnsInterfaceSocket socket, - @NonNull byte[] packetCreationBuffer, @NonNull SharedLog sharedLog) { + @NonNull byte[] packetCreationBuffer, @NonNull SharedLog sharedLog, + boolean enableDebugLog) { mHandler = new SendHandler(looper); mSocket = socket; mPacketCreationBuffer = packetCreationBuffer; mSharedLog = sharedLog; + mEnableDebugLog = enableDebugLog; } /** * Queue a reply to be sent when its send delay expires. */ - public void queueReply(@NonNull ReplyInfo reply) { + public void queueReply(@NonNull MdnsReplyInfo reply) { ensureRunningOnHandlerThread(mHandler); // TODO: implement response aggregation (RFC 6762 6.4) mHandler.sendMessageDelayed(mHandler.obtainMessage(MSG_SEND, reply), reply.sendDelayMs); - if (DBG) { + if (mEnableDebugLog) { mSharedLog.v("Scheduling " + reply); } } @@ -118,8 +119,8 @@ public class MdnsReplySender { @Override public void handleMessage(@NonNull Message msg) { - final ReplyInfo replyInfo = (ReplyInfo) msg.obj; - if (DBG) mSharedLog.v("Sending " + replyInfo); + final MdnsReplyInfo replyInfo = (MdnsReplyInfo) msg.obj; + if (mEnableDebugLog) mSharedLog.v("Sending " + replyInfo); final int flags = 0x8400; // Response, authoritative (rfc6762 18.4) final MdnsPacket packet = new MdnsPacket(flags, diff --git a/tests/unit/java/com/android/server/connectivity/mdns/MdnsAnnouncerTest.kt b/tests/unit/java/com/android/server/connectivity/mdns/MdnsAnnouncerTest.kt index c39ee1e1c7..27974620b3 100644 --- a/tests/unit/java/com/android/server/connectivity/mdns/MdnsAnnouncerTest.kt +++ b/tests/unit/java/com/android/server/connectivity/mdns/MdnsAnnouncerTest.kt @@ -82,7 +82,8 @@ class MdnsAnnouncerTest { @Test fun testAnnounce() { - val replySender = MdnsReplySender( thread.looper, socket, buffer, sharedLog) + val replySender = MdnsReplySender( + thread.looper, socket, buffer, sharedLog, true /* enableDebugLog */) @Suppress("UNCHECKED_CAST") val cb = mock(MdnsPacketRepeater.PacketRepeaterCallback::class.java) as MdnsPacketRepeater.PacketRepeaterCallback diff --git a/tests/unit/java/com/android/server/connectivity/mdns/MdnsInterfaceAdvertiserTest.kt b/tests/unit/java/com/android/server/connectivity/mdns/MdnsInterfaceAdvertiserTest.kt index c19747e65e..a67dc5e9a9 100644 --- a/tests/unit/java/com/android/server/connectivity/mdns/MdnsInterfaceAdvertiserTest.kt +++ b/tests/unit/java/com/android/server/connectivity/mdns/MdnsInterfaceAdvertiserTest.kt @@ -190,8 +190,8 @@ class MdnsInterfaceAdvertiserTest { fun testReplyToQuery() { addServiceAndFinishProbing(TEST_SERVICE_ID_1, TEST_SERVICE_1) - val mockReply = mock(MdnsRecordRepository.ReplyInfo::class.java) - doReturn(mockReply).`when`(repository).getReply(any(), any()) + val testReply = MdnsReplyInfo(emptyList(), emptyList(), 0, InetSocketAddress(0)) + doReturn(testReply).`when`(repository).getReply(any(), any()) // Query obtained with: // scapy.raw(scapy.DNS( @@ -216,7 +216,7 @@ class MdnsInterfaceAdvertiserTest { assertContentEquals(arrayOf("_testservice", "_tcp", "local"), it.questions[0].name) } - verify(replySender).queueReply(mockReply) + verify(replySender).queueReply(testReply) } @Test diff --git a/tests/unit/java/com/android/server/connectivity/mdns/MdnsProberTest.kt b/tests/unit/java/com/android/server/connectivity/mdns/MdnsProberTest.kt index f28481995e..5b7c0bacc0 100644 --- a/tests/unit/java/com/android/server/connectivity/mdns/MdnsProberTest.kt +++ b/tests/unit/java/com/android/server/connectivity/mdns/MdnsProberTest.kt @@ -119,7 +119,8 @@ class MdnsProberTest { @Test fun testProbe() { - val replySender = MdnsReplySender(thread.looper, socket, buffer, sharedLog) + val replySender = MdnsReplySender( + thread.looper, socket, buffer, sharedLog, true /* enableDebugLog */) val prober = TestProber(thread.looper, replySender, cb, sharedLog) val probeInfo = TestProbeInfo( listOf(makeServiceRecord(TEST_SERVICE_NAME_1, 37890))) @@ -143,7 +144,8 @@ class MdnsProberTest { @Test fun testProbeMultipleRecords() { - val replySender = MdnsReplySender(thread.looper, socket, buffer, sharedLog) + val replySender = MdnsReplySender( + thread.looper, socket, buffer, sharedLog, true /* enableDebugLog */) val prober = TestProber(thread.looper, replySender, cb, sharedLog) val probeInfo = TestProbeInfo(listOf( makeServiceRecord(TEST_SERVICE_NAME_1, 37890), @@ -181,7 +183,8 @@ class MdnsProberTest { @Test fun testStopProbing() { - val replySender = MdnsReplySender(thread.looper, socket, buffer, sharedLog) + val replySender = MdnsReplySender( + thread.looper, socket, buffer, sharedLog, true /* enableDebugLog */) val prober = TestProber(thread.looper, replySender, cb, sharedLog) val probeInfo = TestProbeInfo( listOf(makeServiceRecord(TEST_SERVICE_NAME_1, 37890)),