Merge branch 'cpu-performance' of ssh://opensimulator.org/var/git/opensim into cpu-performance

cpu-performance
Diva Canto 2013-07-18 19:02:46 -07:00
commit 52bb732692
4 changed files with 160 additions and 65 deletions

View File

@ -357,7 +357,9 @@ namespace OpenSim.Region.ClientStack.LindenUDP
/// This does mean that agent updates must be processed synchronously, at least for each client, and called methods /// This does mean that agent updates must be processed synchronously, at least for each client, and called methods
/// cannot retain a reference to it outside of that method. /// cannot retain a reference to it outside of that method.
/// </remarks> /// </remarks>
private AgentUpdateArgs m_lastAgentUpdateArgs; private AgentUpdateArgs m_lastAgentUpdateArgs = new AgentUpdateArgs();
private AgentUpdateArgs m_thisAgentUpdateArgs = new AgentUpdateArgs();
protected Dictionary<PacketType, PacketProcessor> m_packetHandlers = new Dictionary<PacketType, PacketProcessor>(); protected Dictionary<PacketType, PacketProcessor> m_packetHandlers = new Dictionary<PacketType, PacketProcessor>();
protected Dictionary<string, GenericMessage> m_genericPacketHandlers = new Dictionary<string, GenericMessage>(); //PauPaw:Local Generic Message handlers protected Dictionary<string, GenericMessage> m_genericPacketHandlers = new Dictionary<string, GenericMessage>(); //PauPaw:Local Generic Message handlers
@ -5565,32 +5567,22 @@ namespace OpenSim.Region.ClientStack.LindenUDP
#region Packet Handlers #region Packet Handlers
public int TotalSignificantAgentUpdates { get; private set; }
#region Scene/Avatar #region Scene/Avatar
private bool HandleAgentUpdate(IClientAPI sener, Packet packet) /// <summary>
{ /// This checks the update significance against the last update made.
if (OnAgentUpdate != null) /// </summary>
{ /// <remarks>Can only be called by one thread at a time</remarks>
AgentUpdatePacket agentUpdate = (AgentUpdatePacket)packet; /// <returns>/returns>
/// <param name='x'></param>
#region Packet Session and User Check public bool CheckAgentUpdateSignificance(AgentUpdatePacket.AgentDataBlock x)
if (agentUpdate.AgentData.SessionID != SessionId || agentUpdate.AgentData.AgentID != AgentId)
{
PacketPool.Instance.ReturnPacket(packet);
return false;
}
#endregion
bool update = false;
AgentUpdatePacket.AgentDataBlock x = agentUpdate.AgentData;
if (m_lastAgentUpdateArgs != null)
{ {
// These should be ordered from most-likely to // These should be ordered from most-likely to
// least likely to change. I've made an initial // least likely to change. I've made an initial
// guess at that. // guess at that.
update = if (
(
(x.BodyRotation != m_lastAgentUpdateArgs.BodyRotation) || (x.BodyRotation != m_lastAgentUpdateArgs.BodyRotation) ||
(x.CameraAtAxis != m_lastAgentUpdateArgs.CameraAtAxis) || (x.CameraAtAxis != m_lastAgentUpdateArgs.CameraAtAxis) ||
(x.CameraCenter != m_lastAgentUpdateArgs.CameraCenter) || (x.CameraCenter != m_lastAgentUpdateArgs.CameraCenter) ||
@ -5603,17 +5595,10 @@ namespace OpenSim.Region.ClientStack.LindenUDP
(x.HeadRotation != m_lastAgentUpdateArgs.HeadRotation) || (x.HeadRotation != m_lastAgentUpdateArgs.HeadRotation) ||
(x.SessionID != m_lastAgentUpdateArgs.SessionID) || (x.SessionID != m_lastAgentUpdateArgs.SessionID) ||
(x.AgentID != m_lastAgentUpdateArgs.AgentID) (x.AgentID != m_lastAgentUpdateArgs.AgentID)
); )
}
else
{
m_lastAgentUpdateArgs = new AgentUpdateArgs();
update = true;
}
if (update)
{ {
// m_log.DebugFormat("[LLCLIENTVIEW]: Triggered AgentUpdate for {0}", sener.Name); // m_log.DebugFormat("[LLCLIENTVIEW]: Triggered AgentUpdate for {0}", sener.Name);
TotalSignificantAgentUpdates++;
m_lastAgentUpdateArgs.AgentID = x.AgentID; m_lastAgentUpdateArgs.AgentID = x.AgentID;
m_lastAgentUpdateArgs.BodyRotation = x.BodyRotation; m_lastAgentUpdateArgs.BodyRotation = x.BodyRotation;
@ -5628,18 +5613,82 @@ namespace OpenSim.Region.ClientStack.LindenUDP
m_lastAgentUpdateArgs.SessionID = x.SessionID; m_lastAgentUpdateArgs.SessionID = x.SessionID;
m_lastAgentUpdateArgs.State = x.State; m_lastAgentUpdateArgs.State = x.State;
return true;
}
return false;
}
private bool HandleAgentUpdate(IClientAPI sener, Packet packet)
{
if (OnAgentUpdate != null)
{
AgentUpdatePacket agentUpdate = (AgentUpdatePacket)packet;
// Now done earlier
// #region Packet Session and User Check
// if (agentUpdate.AgentData.SessionID != SessionId || agentUpdate.AgentData.AgentID != AgentId)
// {
// PacketPool.Instance.ReturnPacket(packet);
// return false;
// }
// #endregion
//
// bool update = false;
AgentUpdatePacket.AgentDataBlock x = agentUpdate.AgentData;
//
// if (m_lastAgentUpdateArgs != null)
// {
// // These should be ordered from most-likely to
// // least likely to change. I've made an initial
// // guess at that.
// update =
// (
// (x.BodyRotation != m_lastAgentUpdateArgs.BodyRotation) ||
// (x.CameraAtAxis != m_lastAgentUpdateArgs.CameraAtAxis) ||
// (x.CameraCenter != m_lastAgentUpdateArgs.CameraCenter) ||
// (x.CameraLeftAxis != m_lastAgentUpdateArgs.CameraLeftAxis) ||
// (x.CameraUpAxis != m_lastAgentUpdateArgs.CameraUpAxis) ||
// (x.ControlFlags != m_lastAgentUpdateArgs.ControlFlags) ||
// (x.Far != m_lastAgentUpdateArgs.Far) ||
// (x.Flags != m_lastAgentUpdateArgs.Flags) ||
// (x.State != m_lastAgentUpdateArgs.State) ||
// (x.HeadRotation != m_lastAgentUpdateArgs.HeadRotation) ||
// (x.SessionID != m_lastAgentUpdateArgs.SessionID) ||
// (x.AgentID != m_lastAgentUpdateArgs.AgentID)
// );
// }
//
// if (update)
// {
//// m_log.DebugFormat("[LLCLIENTVIEW]: Triggered AgentUpdate for {0}", sener.Name);
TotalSignificantAgentUpdates++;
m_thisAgentUpdateArgs.AgentID = x.AgentID;
m_thisAgentUpdateArgs.BodyRotation = x.BodyRotation;
m_thisAgentUpdateArgs.CameraAtAxis = x.CameraAtAxis;
m_thisAgentUpdateArgs.CameraCenter = x.CameraCenter;
m_thisAgentUpdateArgs.CameraLeftAxis = x.CameraLeftAxis;
m_thisAgentUpdateArgs.CameraUpAxis = x.CameraUpAxis;
m_thisAgentUpdateArgs.ControlFlags = x.ControlFlags;
m_thisAgentUpdateArgs.Far = x.Far;
m_thisAgentUpdateArgs.Flags = x.Flags;
m_thisAgentUpdateArgs.HeadRotation = x.HeadRotation;
m_thisAgentUpdateArgs.SessionID = x.SessionID;
m_thisAgentUpdateArgs.State = x.State;
UpdateAgent handlerAgentUpdate = OnAgentUpdate; UpdateAgent handlerAgentUpdate = OnAgentUpdate;
UpdateAgent handlerPreAgentUpdate = OnPreAgentUpdate; UpdateAgent handlerPreAgentUpdate = OnPreAgentUpdate;
if (handlerPreAgentUpdate != null) if (handlerPreAgentUpdate != null)
OnPreAgentUpdate(this, m_lastAgentUpdateArgs); OnPreAgentUpdate(this, m_thisAgentUpdateArgs);
if (handlerAgentUpdate != null) if (handlerAgentUpdate != null)
OnAgentUpdate(this, m_lastAgentUpdateArgs); OnAgentUpdate(this, m_thisAgentUpdateArgs);
handlerAgentUpdate = null; handlerAgentUpdate = null;
handlerPreAgentUpdate = null; handlerPreAgentUpdate = null;
} // }
} }
PacketPool.Instance.ReturnPacket(packet); PacketPool.Instance.ReturnPacket(packet);

View File

@ -572,6 +572,14 @@ namespace OpenSim.Region.ClientStack.LindenUDP
"debug lludp status", "debug lludp status",
"Return status of LLUDP packet processing.", "Return status of LLUDP packet processing.",
HandleStatusCommand); HandleStatusCommand);
MainConsole.Instance.Commands.AddCommand(
"Debug",
false,
"debug lludp toggle agentupdate",
"debug lludp toggle agentupdate",
"Toggle whether agentupdate packets are processed or simply discarded.",
HandleAgentUpdateCommand);
} }
private void HandlePacketCommand(string module, string[] args) private void HandlePacketCommand(string module, string[] args)
@ -706,6 +714,19 @@ namespace OpenSim.Region.ClientStack.LindenUDP
} }
} }
bool m_discardAgentUpdates;
private void HandleAgentUpdateCommand(string module, string[] args)
{
if (SceneManager.Instance.CurrentScene != null && SceneManager.Instance.CurrentScene != m_scene)
return;
m_discardAgentUpdates = !m_discardAgentUpdates;
MainConsole.Instance.OutputFormat(
"Discard AgentUpdates now {0} for {1}", m_discardAgentUpdates, m_scene.Name);
}
private void HandleStatusCommand(string module, string[] args) private void HandleStatusCommand(string module, string[] args)
{ {
if (SceneManager.Instance.CurrentScene != null && SceneManager.Instance.CurrentScene != m_scene) if (SceneManager.Instance.CurrentScene != null && SceneManager.Instance.CurrentScene != m_scene)
@ -1286,6 +1307,22 @@ namespace OpenSim.Region.ClientStack.LindenUDP
LogPacketHeader(true, udpClient.CircuitCode, 0, packet.Type, (ushort)packet.Length); LogPacketHeader(true, udpClient.CircuitCode, 0, packet.Type, (ushort)packet.Length);
#endregion BinaryStats #endregion BinaryStats
if (packet.Type == PacketType.AgentUpdate)
{
if (m_discardAgentUpdates)
return;
AgentUpdatePacket agentUpdate = (AgentUpdatePacket)packet;
if (agentUpdate.AgentData.SessionID != client.SessionId
|| agentUpdate.AgentData.AgentID != client.AgentId
|| !((LLClientView)client).CheckAgentUpdateSignificance(agentUpdate.AgentData))
{
PacketPool.Instance.ReturnPacket(packet);
return;
}
}
#region Ping Check Handling #region Ping Check Handling
if (packet.Type == PacketType.StartPingCheck) if (packet.Type == PacketType.StartPingCheck)
@ -1662,8 +1699,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP
// Action generic every round // Action generic every round
Action<IClientAPI> clientPacketHandler = ClientOutgoingPacketHandler; Action<IClientAPI> clientPacketHandler = ClientOutgoingPacketHandler;
while (true) while (base.IsRunningOutbound)
// while (base.IsRunningOutbound)
{ {
try try
{ {

View File

@ -111,6 +111,8 @@ namespace OpenMetaverse
if (!IsRunningInbound) if (!IsRunningInbound)
{ {
m_log.DebugFormat("[UDPBASE]: Starting inbound UDP loop");
const int SIO_UDP_CONNRESET = -1744830452; const int SIO_UDP_CONNRESET = -1744830452;
IPEndPoint ipep = new IPEndPoint(m_localBindAddress, m_udpPort); IPEndPoint ipep = new IPEndPoint(m_localBindAddress, m_udpPort);
@ -155,6 +157,8 @@ namespace OpenMetaverse
/// </summary> /// </summary>
public void StartOutbound() public void StartOutbound()
{ {
m_log.DebugFormat("[UDPBASE]: Starting outbound UDP loop");
IsRunningOutbound = true; IsRunningOutbound = true;
} }
@ -162,10 +166,8 @@ namespace OpenMetaverse
{ {
if (IsRunningInbound) if (IsRunningInbound)
{ {
// wait indefinitely for a writer lock. Once this is called, the .NET runtime m_log.DebugFormat("[UDPBASE]: Stopping inbound UDP loop");
// will deny any more reader locks, in effect blocking all other send/receive
// threads. Once we have the lock, we set IsRunningInbound = false to inform the other
// threads that the socket is closed.
IsRunningInbound = false; IsRunningInbound = false;
m_udpSocket.Close(); m_udpSocket.Close();
} }
@ -173,6 +175,8 @@ namespace OpenMetaverse
public void StopOutbound() public void StopOutbound()
{ {
m_log.DebugFormat("[UDPBASE]: Stopping outbound UDP loop");
IsRunningOutbound = false; IsRunningOutbound = false;
} }

View File

@ -611,7 +611,7 @@ namespace OpenSim.Region.OptionalModules.UDP.Linden
// //
if (showParams.Length <= 4) if (showParams.Length <= 4)
{ {
m_log.InfoFormat("[INFO]: {0,-12} {1,20} {2,6} {3,11} {4, 10}", "Region", "Name", "Root", "Time", "Reqs/min"); m_log.InfoFormat("[INFO]: {0,-12} {1,-20} {2,-6} {3,-11} {4,-11} {5,-16}", "Region", "Name", "Root", "Time", "Reqs/min", "Sig. AgentUpdates");
foreach (Scene scene in m_scenes.Values) foreach (Scene scene in m_scenes.Values)
{ {
scene.ForEachClient( scene.ForEachClient(
@ -624,9 +624,15 @@ namespace OpenSim.Region.OptionalModules.UDP.Linden
int avg_reqs = cinfo.AsyncRequests.Values.Sum() + cinfo.GenericRequests.Values.Sum() + cinfo.SyncRequests.Values.Sum(); int avg_reqs = cinfo.AsyncRequests.Values.Sum() + cinfo.GenericRequests.Values.Sum() + cinfo.SyncRequests.Values.Sum();
avg_reqs = avg_reqs / ((DateTime.Now - cinfo.StartedTime).Minutes + 1); avg_reqs = avg_reqs / ((DateTime.Now - cinfo.StartedTime).Minutes + 1);
m_log.InfoFormat("[INFO]: {0,-12} {1,20} {2,4} {3,9}min {4,10}", m_log.InfoFormat("[INFO]: {0,-12} {1,-20} {2,-6} {3,-11} {4,-11} {5,-16}",
scene.RegionInfo.RegionName, llClient.Name, scene.RegionInfo.RegionName, llClient.Name,
(llClient.SceneAgent.IsChildAgent ? "N" : "Y"), (DateTime.Now - cinfo.StartedTime).Minutes, avg_reqs); llClient.SceneAgent.IsChildAgent ? "N" : "Y",
(DateTime.Now - cinfo.StartedTime).Minutes,
avg_reqs,
string.Format(
"{0}, {1}%",
llClient.TotalSignificantAgentUpdates,
(float)llClient.TotalSignificantAgentUpdates / cinfo.SyncRequests["AgentUpdate"] * 100));
} }
}); });
} }