From afe63faa2ee9cbdb8a8e0ee755a4d5ef06fe770b Mon Sep 17 00:00:00 2001
From: Teravus Ovares
Date: Tue, 18 Dec 2007 00:34:42 +0000
Subject: * Fix for mantis 0000040 After client logout remote host closed
connection on Simulator makes sim unuseable->'Closed Connection Called' *
I've fundamentally changed a few things, so this is experimental * The
routine that I used needs to be tested on Linux. I don't expect it to cause
a problem, but hey, it might. * Child agents are still not logged off
properly, so when the first set time out, the second set get logged off also,
on the second log in if the second login is initiated before the first one
fully times out.
---
OpenSim/Framework/IScene.cs | 1 +
OpenSim/Region/ClientStack/ClientView.cs | 8 +++-
OpenSim/Region/ClientStack/PacketServer.cs | 5 ++-
OpenSim/Region/ClientStack/UDPServer.cs | 53 +++++++++++++++++++++++---
OpenSim/Region/Environment/Scenes/Scene.cs | 5 +++
OpenSim/Region/Environment/Scenes/SceneBase.cs | 2 +
6 files changed, 66 insertions(+), 8 deletions(-)
(limited to 'OpenSim')
diff --git a/OpenSim/Framework/IScene.cs b/OpenSim/Framework/IScene.cs
index d7071da..4b6e9a5 100644
--- a/OpenSim/Framework/IScene.cs
+++ b/OpenSim/Framework/IScene.cs
@@ -46,6 +46,7 @@ namespace OpenSim.Framework
void AddNewClient(IClientAPI client, bool child);
void RemoveClient(LLUUID agentID);
+ void CloseAllAgents(uint circuitcode);
void Restart(int seconds);
bool OtherRegionUp(RegionInfo thisRegion);
diff --git a/OpenSim/Region/ClientStack/ClientView.cs b/OpenSim/Region/ClientStack/ClientView.cs
index 5e0ab65..df52745 100644
--- a/OpenSim/Region/ClientStack/ClientView.cs
+++ b/OpenSim/Region/ClientStack/ClientView.cs
@@ -209,8 +209,8 @@ namespace OpenSim.Region.ClientStack
m_scene.RemoveClient(AgentId);
// Send the STOP packet
- //libsecondlife.Packets.DisableSimulatorPacket disable = new libsecondlife.Packets.DisableSimulatorPacket();
- //OutPacket(disable, ThrottleOutPacketType.Task);
+ DisableSimulatorPacket disable = new DisableSimulatorPacket();
+ OutPacket(disable, ThrottleOutPacketType.Task);
// FLUSH Packets
m_packetQueue.Close();
@@ -225,6 +225,10 @@ namespace OpenSim.Region.ClientStack
// This is just to give the client a reasonable chance of
// flushing out all it's packets. There should probably
// be a better mechanism here
+
+ // We can't reach into other scenes and close the connection
+ // We need to do this over grid communications
+ m_scene.CloseAllAgents(CircuitCode);
m_clientThread.Abort();
}
diff --git a/OpenSim/Region/ClientStack/PacketServer.cs b/OpenSim/Region/ClientStack/PacketServer.cs
index 39c3d32..308728e 100644
--- a/OpenSim/Region/ClientStack/PacketServer.cs
+++ b/OpenSim/Region/ClientStack/PacketServer.cs
@@ -123,13 +123,16 @@ namespace OpenSim.Region.ClientStack
///
public virtual void CloseCircuit(uint circuitcode)
{
+ OpenSim.Framework.Console.MainLog.Instance.Debug("PACKETSERVER", "Removing Circuit Code");
m_networkHandler.RemoveClientCircuit(circuitcode);
- m_scene.ClientManager.CloseAllAgents(circuitcode);
+ OpenSim.Framework.Console.MainLog.Instance.Debug("PACKETSERVER", "Removed Circuit Code");
+ //m_scene.ClientManager.CloseAllAgents(circuitcode);
}
public virtual void CloseClient(IClientAPI client)
{
CloseCircuit(client.CircuitCode);
+ client.Close();
}
}
}
diff --git a/OpenSim/Region/ClientStack/UDPServer.cs b/OpenSim/Region/ClientStack/UDPServer.cs
index 55ef4a4..2b2269e 100644
--- a/OpenSim/Region/ClientStack/UDPServer.cs
+++ b/OpenSim/Region/ClientStack/UDPServer.cs
@@ -119,16 +119,48 @@ namespace OpenSim.Region.ClientStack
{
case SocketError.AlreadyInProgress:
case SocketError.NetworkReset:
+ case SocketError.ConnectionReset:
+ try
+ {
+ CloseEndPoint(epSender);
+ }
+ catch (System.Exception a)
+ {
+ MainLog.Instance.Verbose("UDPSERVER", a.ToString());
+ }
+ try
+ {
+ Server.BeginReceiveFrom(RecvBuffer, 0, RecvBuffer.Length, SocketFlags.None, ref epSender, ReceivedData, null);
+
+ // Ter: For some stupid reason ConnectionReset basically kills our async event structure..
+ // so therefore.. we've got to tell the server to BeginReceiveFrom again.
+ // This will happen over and over until we've gone through all packets
+ // sent to and from this particular user.
+ // Stupid I know..
+ // but Flusing the buffer would be even more stupid... so, we're stuck with this ugly method.
+
+ }
+ catch (SocketException)
+ {
+
+ }
+ break;
default:
- Console.WriteLine("Remote host Closed connection");
- CloseEndPoint(epSender);
+ // Here's some reference code! :D
+ // Shutdown and restart the UDP listener! hehe
+ // Shiny
+
+ //Server.Shutdown(SocketShutdown.Both);
+ //CloseEndPoint(epSender);
+ //ServerListener();
break;
}
return;
}
- catch (System.ObjectDisposedException)
+ catch (System.ObjectDisposedException e)
{
+ MainLog.Instance.Debug("UDPSERVER", e.ToString());
return;
}
@@ -138,8 +170,9 @@ namespace OpenSim.Region.ClientStack
{
packet = Packet.BuildPacket(RecvBuffer, ref packetEnd, ZeroBuffer);
}
- catch(Exception)
+ catch(Exception e)
{
+ MainLog.Instance.Debug("UDPSERVER", e.ToString());
}
// do we already have a circuit for this endpoint
@@ -147,18 +180,21 @@ namespace OpenSim.Region.ClientStack
if (clientCircuits.TryGetValue(epSender, out circuit))
{
//if so then send packet to the packetserver
+ //MainLog.Instance.Warn("UDPSERVER", "ALREADY HAVE Circuit!");
m_packetServer.InPacket(circuit, packet);
}
else if (packet.Type == PacketType.UseCircuitCode)
{
// new client
+ MainLog.Instance.Debug("UDPSERVER", "Adding New Client");
AddNewClient(packet);
}
else
{
+
// invalid client
//CFK: This message seems to have served its usefullness as of 12-15 so I am commenting it out for now
- //CFK: m_log.Warn("client", "Got a packet from an invalid client - " + epSender.ToString());
+ //m_log.Warn("client", "Got a packet from an invalid client - " + epSender.ToString());
}
Server.BeginReceiveFrom(RecvBuffer, 0, RecvBuffer.Length, SocketFlags.None, ref epSender, ReceivedData, null);
@@ -169,7 +205,9 @@ namespace OpenSim.Region.ClientStack
uint circuit;
if (clientCircuits.TryGetValue(sender, out circuit))
{
+ MainLog.Instance.Debug("UDPSERVER", "CloseEndPoint:ClosingCircuit");
m_packetServer.CloseCircuit(circuit);
+ MainLog.Instance.Debug("UDPSERVER", "CloseEndPoint:ClosedCircuit");
}
}
@@ -222,8 +260,13 @@ namespace OpenSim.Region.ClientStack
EndPoint sendto = null;
if (clientCircuits_reverse.TryGetValue(circuitcode, out sendto))
{
+ MainLog.Instance.Debug("UDPSERVER", "RemovingClientCircuit");
clientCircuits.Remove(sendto);
+ MainLog.Instance.Debug("UDPSERVER", "Removed Client Circuit");
+
+ MainLog.Instance.Debug("UDPSERVER", "Removing Reverse ClientCircuit");
clientCircuits_reverse.Remove(circuitcode);
+ MainLog.Instance.Debug("UDPSERVER", "Removed Reverse ClientCircuit");
}
}
}
diff --git a/OpenSim/Region/Environment/Scenes/Scene.cs b/OpenSim/Region/Environment/Scenes/Scene.cs
index 1145b00..bfdf517 100644
--- a/OpenSim/Region/Environment/Scenes/Scene.cs
+++ b/OpenSim/Region/Environment/Scenes/Scene.cs
@@ -1243,7 +1243,12 @@ namespace OpenSim.Region.Environment.Scenes
// Remove client agent from profile, so new logins will work
CommsManager.UserService.clearUserAgent(agentID);
}
+ public override void CloseAllAgents(uint circuitcode)
+ {
+ // Called by ClientView to kill all circuit codes
+ ClientManager.CloseAllAgents(circuitcode);
+ }
public void NotifyMyCoarseLocationChange()
{
ForEachScenePresence(delegate(ScenePresence presence) { presence.CoarseLocationChange(); });
diff --git a/OpenSim/Region/Environment/Scenes/SceneBase.cs b/OpenSim/Region/Environment/Scenes/SceneBase.cs
index 75118e2..35d88eb 100644
--- a/OpenSim/Region/Environment/Scenes/SceneBase.cs
+++ b/OpenSim/Region/Environment/Scenes/SceneBase.cs
@@ -130,6 +130,8 @@ namespace OpenSim.Region.Environment.Scenes
///
public abstract void RemoveClient(LLUUID agentID);
+ public abstract void CloseAllAgents(uint circuitcode);
+
#endregion
///
--
cgit v1.1