mirror of
https://github.com/permissionlesstech/bitchat-android.git
synced 2026-07-25 14:05:19 +00:00
Enhance Wi-Fi Aware robustness and debug UI display
- Clean up transport resources (sockets, server sockets, network callbacks) immediately on peer disconnection. - Implement resolveScopedAddress to show scoped IPv6 (e.g., %aware0) in Debug UI. - Fix Map type mismatch warning in ChatViewModel bridge. - Filter self-ID from peer cleanup tables to prevent recursive self-removal.
This commit is contained in:
@@ -654,7 +654,7 @@ class ChatViewModel(
|
|||||||
|
|
||||||
// Merge nicknames from BLE and Wi‑Fi Aware to display names for all peers
|
// Merge nicknames from BLE and Wi‑Fi Aware to display names for all peers
|
||||||
val bleNick = meshService.getPeerNicknames()
|
val bleNick = meshService.getPeerNicknames()
|
||||||
val awareNick = try { com.bitchat.android.wifiaware.WifiAwareController.getService()?.getPeerNicknames() } catch (_: Exception) { null }
|
val awareNick = try { com.bitchat.android.wifiaware.WifiAwareController.getService()?.getPeerNicknamesMap() } catch (_: Exception) { null }
|
||||||
val mergedNick = if (awareNick != null) bleNick + awareNick.filterKeys { it !in bleNick || bleNick[it].isNullOrBlank() } else bleNick
|
val mergedNick = if (awareNick != null) bleNick + awareNick.filterKeys { it !in bleNick || bleNick[it].isNullOrBlank() } else bleNick
|
||||||
state.setPeerNicknames(mergedNick)
|
state.setPeerNicknames(mergedNick)
|
||||||
|
|
||||||
|
|||||||
@@ -826,24 +826,30 @@ class WifiAwareMeshService(private val context: Context) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (routedPeerId == null) {
|
if (routedPeerId == null) {
|
||||||
routedPeerId = senderPeerHex
|
|
||||||
peerSockets[routedPeerId] = socket
|
|
||||||
}
|
|
||||||
|
|
||||||
Log.d(TAG, "RX: packet type=${pkt.type} from ${senderPeerHex.take(8)}… (bytes=${raw.size})")
|
Log.d(TAG, "RX: packet type=${pkt.type} from ${senderPeerHex.take(8)}… (bytes=${raw.size})")
|
||||||
packetProcessor.processPacket(RoutedPacket(pkt, routedPeerId))
|
packetProcessor.processPacket(RoutedPacket(pkt, routedPeerId))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Loop break -> disconnection
|
||||||
|
handlePeerDisconnection(initialLogicalPeerId, routedPeerId)
|
||||||
socket.closeQuietly()
|
socket.closeQuietly()
|
||||||
routedPeerId?.let {
|
}
|
||||||
peerSockets.remove(it)
|
|
||||||
peerManager.removePeer(it)
|
private fun handlePeerDisconnection(initialId: String, routedId: String?) {
|
||||||
|
serviceScope.launch {
|
||||||
|
Log.w(TAG, "Cleaning up peer: $initialId / $routedId")
|
||||||
|
val possible = setOfNotNull(initialId, routedId).filter { it.isNotEmpty() && it != myPeerID }
|
||||||
|
possible.forEach { id ->
|
||||||
|
peerSockets.remove(id)?.closeQuietly()
|
||||||
|
serverSockets.remove(id)?.closeQuietly()
|
||||||
|
networkCallbacks.remove(id)?.let { runCatching { cm.unregisterNetworkCallback(it) } }
|
||||||
|
peerManager.removePeer(id)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sends a broadcast message to all peers.
|
* Sends a broadcast message to all peers.
|
||||||
*
|
|
||||||
* @param content Text content of the message
|
* @param content Text content of the message
|
||||||
* @param mentions Optional list of mentioned peer IDs
|
* @param mentions Optional list of mentioned peer IDs
|
||||||
* @param channel Optional channel name
|
* @param channel Optional channel name
|
||||||
@@ -1160,15 +1166,43 @@ class WifiAwareMeshService(private val context: Context) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* @return the current IPv4/IPv6 address of a connected peer, if any.
|
* @return the current IPv4/IPv6 address of a connected peer, if any.
|
||||||
|
* Prefers the scoped IPv6 address format.
|
||||||
*/
|
*/
|
||||||
fun getDeviceAddressForPeer(peerID: String): String? =
|
fun getDeviceAddressForPeer(peerID: String): String? =
|
||||||
peerSockets[peerID]?.inetAddress?.hostAddress
|
peerSockets[peerID]?.let { resolveScopedAddress(it) }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Helper to resolve a scoped IPv6 address from a socket for UI display.
|
||||||
|
*/
|
||||||
|
private fun resolveScopedAddress(sock: Socket): String? {
|
||||||
|
val addr = sock.inetAddress as? Inet6Address ?: return sock.inetAddress?.hostAddress
|
||||||
|
if (addr.scopeId != 0 || addr.isLoopbackAddress) return addr.hostAddress
|
||||||
|
|
||||||
|
// If address has no scope but we are on Aware (Link-Local fe80), attempt interface resolution
|
||||||
|
val iface = try {
|
||||||
|
val lp = cm.getLinkProperties(cm.activeNetwork)
|
||||||
|
lp?.interfaceName ?: "aware0"
|
||||||
|
} catch (_: Exception) { "aware0" }
|
||||||
|
|
||||||
|
return "${addr.hostAddress}%$iface"
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return a mapping of peerID → connected device IP address for all active sockets.
|
* @return a mapping of peerID → connected device IP address for all active sockets.
|
||||||
|
* Results are formatted as scoped addresses if applicable.
|
||||||
*/
|
*/
|
||||||
fun getDeviceAddressToPeerMapping(): Map<String, String> =
|
fun getDeviceAddressToPeerMapping(): Map<String, String> {
|
||||||
peerSockets.mapValues { it.value.inetAddress.hostAddress }
|
val map = mutableMapOf<String, String>()
|
||||||
|
peerSockets.forEach { (pid, sock) ->
|
||||||
|
map[pid] = resolveScopedAddress(sock) ?: "unknown"
|
||||||
|
}
|
||||||
|
return map
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return map of peer ID to nickname, bridged for UI warning fix.
|
||||||
|
*/
|
||||||
|
fun getPeerNicknamesMap(): Map<String, String?> = peerManager.getAllPeerNicknames()
|
||||||
|
|
||||||
/** Returns recently discovered peer IDs via Aware discovery (may not be connected). */
|
/** Returns recently discovered peer IDs via Aware discovery (may not be connected). */
|
||||||
fun getDiscoveredPeerIds(): Set<String> =
|
fun getDiscoveredPeerIds(): Set<String> =
|
||||||
|
|||||||
Reference in New Issue
Block a user