Start the station link on launch and beacon on every interface
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
using System.Collections.Concurrent;
|
||||
using System.Net;
|
||||
using System.Net.NetworkInformation;
|
||||
using System.Net.Sockets;
|
||||
using System.Text;
|
||||
using Nonemm.Core;
|
||||
@@ -525,9 +526,12 @@ public sealed class StationLink : IDisposable
|
||||
StationBeacon beacon = new(computerName, Address(), port, version, mine.Operator);
|
||||
myAddress = beacon.Address;
|
||||
byte[] message = Encoding.UTF8.GetBytes(beacon.ToWire());
|
||||
await beacons!
|
||||
.SendAsync(message, new IPEndPoint(IPAddress.Broadcast, port), cancellation)
|
||||
.ConfigureAwait(false);
|
||||
foreach (IPAddress target in BroadcastAddresses())
|
||||
{
|
||||
await beacons!
|
||||
.SendAsync(message, new IPEndPoint(target, port), cancellation)
|
||||
.ConfigureAwait(false);
|
||||
}
|
||||
mine.Address = beacon.Address;
|
||||
mine.LastHeardUtc = DateTime.UtcNow;
|
||||
Forget();
|
||||
@@ -1138,6 +1142,38 @@ public sealed class StationLink : IDisposable
|
||||
}
|
||||
}
|
||||
|
||||
/// The broadcast address of each network this computer is on. The limited
|
||||
/// broadcast (255.255.255.255) leaves by one interface only, so a computer
|
||||
/// with a second adapter or a VPN would miss the stations on the others.
|
||||
private static List<IPAddress> BroadcastAddresses()
|
||||
{
|
||||
List<IPAddress> found = [IPAddress.Broadcast];
|
||||
foreach (NetworkInterface adapter in NetworkInterface.GetAllNetworkInterfaces())
|
||||
{
|
||||
if (adapter.OperationalStatus != OperationalStatus.Up
|
||||
|| adapter.NetworkInterfaceType == NetworkInterfaceType.Loopback
|
||||
|| !adapter.SupportsMulticast)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
foreach (UnicastIPAddressInformation info in adapter.GetIPProperties().UnicastAddresses)
|
||||
{
|
||||
if (info.Address.AddressFamily != AddressFamily.InterNetwork || info.IPv4Mask is null)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
byte[] address = info.Address.GetAddressBytes();
|
||||
byte[] mask = info.IPv4Mask.GetAddressBytes();
|
||||
IPAddress directed = new(address.Select((b, i) => (byte)(b | ~mask[i])).ToArray());
|
||||
if (!found.Contains(directed))
|
||||
{
|
||||
found.Add(directed);
|
||||
}
|
||||
}
|
||||
}
|
||||
return found;
|
||||
}
|
||||
|
||||
/// This computer's address on the network it can reach the others on. It is
|
||||
/// only for the beacon: the other end uses the address the packet came
|
||||
/// from, so a wrong answer here costs nothing.
|
||||
|
||||
Reference in New Issue
Block a user