new method to query client ip
parent
38958bad95
commit
3b43758054
Binary file not shown.
|
|
@ -123,9 +123,25 @@ namespace Lobbies
|
||||||
_ = Task.Run(async () => { await tcpClient.Send(messageData, 0, len); bufferRental.Return(messageData); });
|
_ = Task.Run(async () => { await tcpClient.Send(messageData, 0, len); bufferRental.Return(messageData); });
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// This callback is called if the nat punch requires the game server/client udp sockets sends a packet to a server so that
|
||||||
|
/// the external mapped port by the firewall can be seen by the external point.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="remoteEndpoint">The endpoint to send data to</param>
|
||||||
|
/// <param name="messageBuffer">The message byte buffer to send</param>
|
||||||
|
/// <param name="messageLength">Length of the data to send</param>
|
||||||
public delegate void SendUdpMessageCallback(IPEndPoint remoteEndpoint, byte[] messageBuffer, int messageLength);
|
public delegate void SendUdpMessageCallback(IPEndPoint remoteEndpoint, byte[] messageBuffer, int messageLength);
|
||||||
public void RequestLobbyNatPunch(Guid lobbyId, string? password, SendUdpMessageCallback sendUdpCallback)
|
|
||||||
|
/// <summary>
|
||||||
|
/// This function requests a nat punch for this client from the game host. First the external port for our game client is detected by
|
||||||
|
/// sending a udp packet to the lobby server who then forwards the nat punch request to the host with the seen external ip and port.
|
||||||
|
/// The game host then sends a udp packet to the client to open it's nat bridge and when done sends a event to the client via the lobby server.
|
||||||
|
/// The client receives the external port and ip seen by the lobby server for the host and can connect to the host.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="lobbyId">The lobby to request a nat punch for</param>
|
||||||
|
/// <param name="password">Optional password of lobby</param>
|
||||||
|
/// <param name="sendUdpToGetExternalPortMappingCallback">A callback to send udp data if you have a udp game client ready and bound</param>
|
||||||
|
public void RequestLobbyNatPunch(Guid lobbyId, string? password, SendUdpMessageCallback sendUdpToGetExternalPortMappingCallback)
|
||||||
{
|
{
|
||||||
byte[]? passwordHash = null;
|
byte[]? passwordHash = null;
|
||||||
if (!string.IsNullOrEmpty(password) && lobbyInformation.ContainsKey(lobbyId) && lobbyInformation[lobbyId].PasswordSalt != null)
|
if (!string.IsNullOrEmpty(password) && lobbyInformation.ContainsKey(lobbyId) && lobbyInformation[lobbyId].PasswordSalt != null)
|
||||||
|
|
@ -133,7 +149,45 @@ namespace Lobbies
|
||||||
|
|
||||||
Task.Run(() =>
|
Task.Run(() =>
|
||||||
{
|
{
|
||||||
QueryExternalIpAndPort(sendUdpCallback);
|
QueryExternalIpAndPort(sendUdpToGetExternalPortMappingCallback);
|
||||||
|
var lobbyRequestNatPunch = new LobbyRequestNatPunch()
|
||||||
|
{
|
||||||
|
LobbyId = lobbyId,
|
||||||
|
PasswordHash = passwordHash,
|
||||||
|
ClientIp = externalIp,
|
||||||
|
ClientPort = externalPort
|
||||||
|
};
|
||||||
|
|
||||||
|
byte[] messageData = bufferRental.Rent();
|
||||||
|
var len = lobbyRequestNatPunch.Serialize(messageData);
|
||||||
|
_ = Task.Run(async () => { await tcpClient.Send(messageData, 0, len); bufferRental.Return(messageData); });
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// This function requests a nat punch for this client from the game host. First the external port for our game client is detected by
|
||||||
|
/// sending a udp packet to the lobby server who then forwards the nat punch request to the host with the seen external ip and port.
|
||||||
|
/// The game host then sends a udp packet to the client to open it's nat bridge and when done sends a event to the client via the lobby server.
|
||||||
|
/// The client receives the external port and ip seen by the lobby server for the host and can connect to the host.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="lobbyId">The lobby to request a nat punch for</param>
|
||||||
|
/// <param name="password">Optional password of lobby</param>
|
||||||
|
/// <param name="port">The port the game client will later use. We create a udp socket on it and send a packet to the lobby server to get the firewall to map that port for a short period of time
|
||||||
|
/// after that the udp client will be disposed</param>
|
||||||
|
public void RequestLobbyNatPunch(Guid lobbyId, string? password, int port = 0)
|
||||||
|
{
|
||||||
|
byte[]? passwordHash = null;
|
||||||
|
if (!string.IsNullOrEmpty(password) && lobbyInformation.ContainsKey(lobbyId) && lobbyInformation[lobbyId].PasswordSalt != null)
|
||||||
|
passwordHash = PasswordHash.Hash(password, lobbyInformation[lobbyId].PasswordSalt!);
|
||||||
|
|
||||||
|
Task.Run(() =>
|
||||||
|
{
|
||||||
|
using (var udpEchoServer = new UdpEchoServer())
|
||||||
|
{
|
||||||
|
udpEchoServer.Start(port);
|
||||||
|
QueryExternalIpAndPort(udpEchoServer.Send);
|
||||||
|
}
|
||||||
|
|
||||||
var lobbyRequestNatPunch = new LobbyRequestNatPunch()
|
var lobbyRequestNatPunch = new LobbyRequestNatPunch()
|
||||||
{
|
{
|
||||||
LobbyId = lobbyId,
|
LobbyId = lobbyId,
|
||||||
|
|
|
||||||
|
|
@ -40,6 +40,18 @@ namespace Lobbies
|
||||||
serverSocketV6.Send(magicRequest, magicRequest.Length, remoteEndpoint);
|
serverSocketV6.Send(magicRequest, magicRequest.Length, remoteEndpoint);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void Send(IPEndPoint remoteEndpoint, byte[] messageData, int messageLength)
|
||||||
|
{
|
||||||
|
if (!running || serverSocketV4 == null || serverSocketV6 == null)
|
||||||
|
throw new Exception("Listener not running!");
|
||||||
|
|
||||||
|
for (int i = 0; i < 16; i++)
|
||||||
|
if (remoteEndpoint.AddressFamily == AddressFamily.InterNetwork)
|
||||||
|
serverSocketV4.Send(messageData, messageLength, remoteEndpoint);
|
||||||
|
else
|
||||||
|
serverSocketV6.Send(messageData, messageLength, remoteEndpoint);
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Listen to requests and fire events
|
/// Listen to requests and fire events
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
|
|
||||||
|
|
@ -21,7 +21,7 @@ int myExternalPort = -1;
|
||||||
bool running = true;
|
bool running = true;
|
||||||
bool connected = false;
|
bool connected = false;
|
||||||
|
|
||||||
_ = Task.Run(async () =>
|
_ = Task.Run(() =>
|
||||||
{
|
{
|
||||||
while (running)
|
while (running)
|
||||||
{
|
{
|
||||||
|
|
@ -146,7 +146,8 @@ _ = Task.Run(async () =>
|
||||||
|
|
||||||
_ = Task.Run(() =>
|
_ = Task.Run(() =>
|
||||||
{
|
{
|
||||||
lobbyClient.QueryExternalIpAndPort((remoteEndpoint, messageData, messageLength) => {
|
lobbyClient.QueryExternalIpAndPort((remoteEndpoint, messageData, messageLength) =>
|
||||||
|
{
|
||||||
fakeGameHost.Send(remoteEndpoint, messageData, messageLength);
|
fakeGameHost.Send(remoteEndpoint, messageData, messageLength);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue