From ba057f0092fa6ce8c86cdb49096d3204352dc914 Mon Sep 17 00:00:00 2001 From: hacklab Date: Sat, 10 Oct 2026 15:54:42 +0200 Subject: [PATCH] android: permisos y MulticastLock para ver moviles en la misma wifi El anuncio LAN de SSB va por UDP broadcast y Android lo filtra sin un MulticastLock. La oficial declara ACCESS_WIFI_STATE y CHANGE_WIFI_MULTICAST_STATE; esta no, asi que dos moviles en la misma red no se encontraban. --- android/app/src/main/AndroidManifest.xml | 4 ++++ .../main/java/net/laenre/oasis/NodeService.kt | 22 +++++++++++++++++++ 2 files changed, 26 insertions(+) diff --git a/android/app/src/main/AndroidManifest.xml b/android/app/src/main/AndroidManifest.xml index edcd992..22102a4 100644 --- a/android/app/src/main/AndroidManifest.xml +++ b/android/app/src/main/AndroidManifest.xml @@ -3,6 +3,10 @@ + + + diff --git a/android/app/src/main/java/net/laenre/oasis/NodeService.kt b/android/app/src/main/java/net/laenre/oasis/NodeService.kt index 9bd6f07..f7796ee 100644 --- a/android/app/src/main/java/net/laenre/oasis/NodeService.kt +++ b/android/app/src/main/java/net/laenre/oasis/NodeService.kt @@ -6,6 +6,7 @@ import android.app.NotificationManager import android.app.Service import android.content.Context import android.content.Intent +import android.net.wifi.WifiManager import android.os.Build import android.os.IBinder import android.system.Os @@ -33,16 +34,37 @@ class NodeService : Service() { @Volatile private var started = false } + // Sin esto Android tira los paquetes multicast/broadcast que llegan por wifi y el + // descubrimiento LAN de SSB no ve a nadie: dos moviles en la misma red no se encuentran. + private var multicastLock: WifiManager.MulticastLock? = null + override fun onBind(intent: Intent?): IBinder? = null override fun onCreate() { super.onCreate() startForeground(NOTIF_ID, buildNotification()) + acquireMulticastLock() if (started) return started = true Thread({ runNode() }, "node-main").start() } + override fun onDestroy() { + try { multicastLock?.takeIf { it.isHeld }?.release() } catch (e: Throwable) { Log.w(TAG, "soltando MulticastLock", e) } + super.onDestroy() + } + + private fun acquireMulticastLock() { + if (multicastLock?.isHeld == true) return + try { + val wifi = applicationContext.getSystemService(Context.WIFI_SERVICE) as WifiManager + multicastLock = wifi.createMulticastLock("oasis-lan").apply { setReferenceCounted(false); acquire() } + } catch (e: Throwable) { + // sin wifi o sin permiso: los pubs siguen funcionando, solo se pierde la LAN + Log.w(TAG, "no se ha podido coger el MulticastLock; sin descubrimiento LAN", e) + } + } + private fun buildNotification(): Notification { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { val ch = NotificationChannel(CHANNEL, getString(R.string.node_channel), NotificationManager.IMPORTANCE_LOW)