Merge branch 'cpu-performance' of ssh://opensimulator.org/var/git/opensim into cpu-performance
commit
be4034fd1c
|
@ -359,12 +359,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
/// 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_thisAgentUpdateArgs = new AgentUpdateArgs();
|
private AgentUpdateArgs m_thisAgentUpdateArgs = new AgentUpdateArgs();
|
||||||
private float qdelta1;
|
|
||||||
private float qdelta2;
|
|
||||||
private float vdelta1;
|
|
||||||
private float vdelta2;
|
|
||||||
private float vdelta3;
|
|
||||||
private float vdelta4;
|
|
||||||
|
|
||||||
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
|
||||||
|
@ -5576,7 +5570,9 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
|
|
||||||
#region Scene/Avatar
|
#region Scene/Avatar
|
||||||
|
|
||||||
|
// Threshold for body rotation to be a significant agent update
|
||||||
private const float QDELTA = 0.000001f;
|
private const float QDELTA = 0.000001f;
|
||||||
|
// Threshold for camera rotation to be a significant agent update
|
||||||
private const float VDELTA = 0.01f;
|
private const float VDELTA = 0.01f;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -5587,14 +5583,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
/// <param name='x'></param>
|
/// <param name='x'></param>
|
||||||
public bool CheckAgentUpdateSignificance(AgentUpdatePacket.AgentDataBlock x)
|
public bool CheckAgentUpdateSignificance(AgentUpdatePacket.AgentDataBlock x)
|
||||||
{
|
{
|
||||||
// Compute these only once, when this function is called from down below
|
|
||||||
qdelta1 = 1 - (float)Math.Pow(Quaternion.Dot(x.BodyRotation, m_thisAgentUpdateArgs.BodyRotation), 2);
|
|
||||||
//qdelta2 = 1 - (float)Math.Pow(Quaternion.Dot(x.HeadRotation, m_thisAgentUpdateArgs.HeadRotation), 2);
|
|
||||||
vdelta1 = Vector3.Distance(x.CameraAtAxis, m_thisAgentUpdateArgs.CameraAtAxis);
|
|
||||||
vdelta2 = Vector3.Distance(x.CameraCenter, m_thisAgentUpdateArgs.CameraCenter);
|
|
||||||
vdelta3 = Vector3.Distance(x.CameraLeftAxis, m_thisAgentUpdateArgs.CameraLeftAxis);
|
|
||||||
vdelta4 = Vector3.Distance(x.CameraUpAxis, m_thisAgentUpdateArgs.CameraUpAxis);
|
|
||||||
|
|
||||||
return CheckAgentMovementUpdateSignificance(x) || CheckAgentCameraUpdateSignificance(x);
|
return CheckAgentMovementUpdateSignificance(x) || CheckAgentCameraUpdateSignificance(x);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -5606,24 +5594,27 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
/// <param name='x'></param>
|
/// <param name='x'></param>
|
||||||
private bool CheckAgentMovementUpdateSignificance(AgentUpdatePacket.AgentDataBlock x)
|
private bool CheckAgentMovementUpdateSignificance(AgentUpdatePacket.AgentDataBlock x)
|
||||||
{
|
{
|
||||||
if (
|
float qdelta1 = 1 - (float)Math.Pow(Quaternion.Dot(x.BodyRotation, m_thisAgentUpdateArgs.BodyRotation), 2);
|
||||||
(qdelta1 > QDELTA) ||
|
//qdelta2 = 1 - (float)Math.Pow(Quaternion.Dot(x.HeadRotation, m_thisAgentUpdateArgs.HeadRotation), 2);
|
||||||
|
|
||||||
|
bool movementSignificant =
|
||||||
|
(qdelta1 > QDELTA) // significant if body rotation above threshold
|
||||||
// Ignoring head rotation altogether, because it's not being used for anything interesting up the stack
|
// Ignoring head rotation altogether, because it's not being used for anything interesting up the stack
|
||||||
//(qdelta2 > QDELTA * 10) ||
|
// || (qdelta2 > QDELTA * 10) // significant if head rotation above threshold
|
||||||
(x.ControlFlags != m_thisAgentUpdateArgs.ControlFlags) ||
|
|| (x.ControlFlags != m_thisAgentUpdateArgs.ControlFlags) // significant if control flags changed
|
||||||
(x.Far != m_thisAgentUpdateArgs.Far) ||
|
|| (x.ControlFlags != (byte)AgentManager.ControlFlags.NONE) // significant if user supplying any movement update commands
|
||||||
(x.Flags != m_thisAgentUpdateArgs.Flags) ||
|
|| (x.Far != m_thisAgentUpdateArgs.Far) // significant if far distance changed
|
||||||
(x.State != m_thisAgentUpdateArgs.State)
|
|| (x.Flags != m_thisAgentUpdateArgs.Flags) // significant if Flags changed
|
||||||
)
|
|| (x.State != m_thisAgentUpdateArgs.State) // significant if Stats changed
|
||||||
{
|
;
|
||||||
|
//if (movementSignificant)
|
||||||
|
//{
|
||||||
//m_log.DebugFormat("[LLCLIENTVIEW]: Bod {0} {1}",
|
//m_log.DebugFormat("[LLCLIENTVIEW]: Bod {0} {1}",
|
||||||
// qdelta1, qdelta2);
|
// qdelta1, qdelta2);
|
||||||
//m_log.DebugFormat("[LLCLIENTVIEW]: St {0} {1} {2} {3} (Thread {4})",
|
//m_log.DebugFormat("[LLCLIENTVIEW]: St {0} {1} {2} {3}",
|
||||||
// x.ControlFlags, x.Flags, x.Far, x.State, Thread.CurrentThread.Name);
|
// x.ControlFlags, x.Flags, x.Far, x.State);
|
||||||
return true;
|
//}
|
||||||
}
|
return movementSignificant;
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -5634,23 +5625,27 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
/// <param name='x'></param>
|
/// <param name='x'></param>
|
||||||
private bool CheckAgentCameraUpdateSignificance(AgentUpdatePacket.AgentDataBlock x)
|
private bool CheckAgentCameraUpdateSignificance(AgentUpdatePacket.AgentDataBlock x)
|
||||||
{
|
{
|
||||||
if (
|
float vdelta1 = Vector3.Distance(x.CameraAtAxis, m_thisAgentUpdateArgs.CameraAtAxis);
|
||||||
/* These 4 are the worst offenders!
|
float vdelta2 = Vector3.Distance(x.CameraCenter, m_thisAgentUpdateArgs.CameraCenter);
|
||||||
* With Singularity, there is a bug where sometimes the spam on these doesn't stop */
|
float vdelta3 = Vector3.Distance(x.CameraLeftAxis, m_thisAgentUpdateArgs.CameraLeftAxis);
|
||||||
|
float vdelta4 = Vector3.Distance(x.CameraUpAxis, m_thisAgentUpdateArgs.CameraUpAxis);
|
||||||
|
|
||||||
|
bool cameraSignificant =
|
||||||
(vdelta1 > VDELTA) ||
|
(vdelta1 > VDELTA) ||
|
||||||
(vdelta2 > VDELTA) ||
|
(vdelta2 > VDELTA) ||
|
||||||
(vdelta3 > VDELTA) ||
|
(vdelta3 > VDELTA) ||
|
||||||
(vdelta4 > VDELTA)
|
(vdelta4 > VDELTA)
|
||||||
)
|
;
|
||||||
{
|
|
||||||
|
//if (cameraSignificant)
|
||||||
|
//{
|
||||||
//m_log.DebugFormat("[LLCLIENTVIEW]: Cam1 {0} {1}",
|
//m_log.DebugFormat("[LLCLIENTVIEW]: Cam1 {0} {1}",
|
||||||
// x.CameraAtAxis, x.CameraCenter);
|
// x.CameraAtAxis, x.CameraCenter);
|
||||||
//m_log.DebugFormat("[LLCLIENTVIEW]: Cam2 {0} {1}",
|
//m_log.DebugFormat("[LLCLIENTVIEW]: Cam2 {0} {1}",
|
||||||
// x.CameraLeftAxis, x.CameraUpAxis);
|
// x.CameraLeftAxis, x.CameraUpAxis);
|
||||||
return true;
|
//}
|
||||||
}
|
|
||||||
|
|
||||||
return false;
|
return cameraSignificant;
|
||||||
}
|
}
|
||||||
|
|
||||||
private bool HandleAgentUpdate(IClientAPI sener, Packet packet)
|
private bool HandleAgentUpdate(IClientAPI sener, Packet packet)
|
||||||
|
|
|
@ -67,11 +67,24 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
{
|
{
|
||||||
m_udpServer.AddScene(scene);
|
m_udpServer.AddScene(scene);
|
||||||
|
|
||||||
|
StatsManager.RegisterStat(
|
||||||
|
new Stat(
|
||||||
|
"IncomingUDPReceivesCount",
|
||||||
|
"Number of UDP receives performed",
|
||||||
|
"Number of UDP receives performed",
|
||||||
|
"",
|
||||||
|
"clientstack",
|
||||||
|
scene.Name,
|
||||||
|
StatType.Pull,
|
||||||
|
MeasuresOfInterest.AverageChangeOverTime,
|
||||||
|
stat => stat.Value = m_udpServer.UdpReceives,
|
||||||
|
StatVerbosity.Debug));
|
||||||
|
|
||||||
StatsManager.RegisterStat(
|
StatsManager.RegisterStat(
|
||||||
new Stat(
|
new Stat(
|
||||||
"IncomingPacketsProcessedCount",
|
"IncomingPacketsProcessedCount",
|
||||||
"Number of inbound UDP packets processed",
|
"Number of inbound LL protocol packets processed",
|
||||||
"Number of inbound UDP packets processed",
|
"Number of inbound LL protocol packets processed",
|
||||||
"",
|
"",
|
||||||
"clientstack",
|
"clientstack",
|
||||||
scene.Name,
|
scene.Name,
|
||||||
|
@ -79,6 +92,34 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
MeasuresOfInterest.AverageChangeOverTime,
|
MeasuresOfInterest.AverageChangeOverTime,
|
||||||
stat => stat.Value = m_udpServer.IncomingPacketsProcessed,
|
stat => stat.Value = m_udpServer.IncomingPacketsProcessed,
|
||||||
StatVerbosity.Debug));
|
StatVerbosity.Debug));
|
||||||
|
|
||||||
|
StatsManager.RegisterStat(
|
||||||
|
new Stat(
|
||||||
|
"OutgoingUDPSendsCount",
|
||||||
|
"Number of UDP sends performed",
|
||||||
|
"Number of UDP sends performed",
|
||||||
|
"",
|
||||||
|
"clientstack",
|
||||||
|
scene.Name,
|
||||||
|
StatType.Pull,
|
||||||
|
MeasuresOfInterest.AverageChangeOverTime,
|
||||||
|
stat => stat.Value = m_udpServer.UdpSends,
|
||||||
|
StatVerbosity.Debug));
|
||||||
|
|
||||||
|
StatsManager.RegisterStat(
|
||||||
|
new Stat(
|
||||||
|
"AverageUDPProcessTime",
|
||||||
|
"Average number of milliseconds taken to process each incoming UDP packet in a sample.",
|
||||||
|
"This is for initial receive processing which is separate from the later client LL packet processing stage.",
|
||||||
|
"ms",
|
||||||
|
"clientstack",
|
||||||
|
scene.Name,
|
||||||
|
StatType.Pull,
|
||||||
|
MeasuresOfInterest.None,
|
||||||
|
stat => stat.Value = m_udpServer.AverageReceiveTicksForLastSamplePeriod / TimeSpan.TicksPerMillisecond,
|
||||||
|
// stat =>
|
||||||
|
// stat.Value = Math.Round(m_udpServer.AverageReceiveTicksForLastSamplePeriod / TimeSpan.TicksPerMillisecond, 7),
|
||||||
|
StatVerbosity.Debug));
|
||||||
}
|
}
|
||||||
|
|
||||||
public bool HandlesRegion(Location x)
|
public bool HandlesRegion(Location x)
|
||||||
|
@ -459,6 +500,19 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
m_scene = (Scene)scene;
|
m_scene = (Scene)scene;
|
||||||
m_location = new Location(m_scene.RegionInfo.RegionHandle);
|
m_location = new Location(m_scene.RegionInfo.RegionHandle);
|
||||||
|
|
||||||
|
StatsManager.RegisterStat(
|
||||||
|
new Stat(
|
||||||
|
"InboxPacketsCount",
|
||||||
|
"Number of LL protocol packets waiting for the second stage of processing after initial receive.",
|
||||||
|
"Number of LL protocol packets waiting for the second stage of processing after initial receive.",
|
||||||
|
"",
|
||||||
|
"clientstack",
|
||||||
|
scene.Name,
|
||||||
|
StatType.Pull,
|
||||||
|
MeasuresOfInterest.AverageChangeOverTime,
|
||||||
|
stat => stat.Value = packetInbox.Count,
|
||||||
|
StatVerbosity.Debug));
|
||||||
|
|
||||||
// XXX: These stats are also pool stats but we register them separately since they are currently not
|
// XXX: These stats are also pool stats but we register them separately since they are currently not
|
||||||
// turned on and off by EnablePools()/DisablePools()
|
// turned on and off by EnablePools()/DisablePools()
|
||||||
StatsManager.RegisterStat(
|
StatsManager.RegisterStat(
|
||||||
|
@ -828,7 +882,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
|
|
||||||
PacketPool.Instance.ReturnPacket(packet);
|
PacketPool.Instance.ReturnPacket(packet);
|
||||||
m_dataPresentEvent.Set();
|
m_dataPresentEvent.Set();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private AutoResetEvent m_dataPresentEvent = new AutoResetEvent(false);
|
private AutoResetEvent m_dataPresentEvent = new AutoResetEvent(false);
|
||||||
|
@ -1331,9 +1384,10 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
|
|
||||||
AgentUpdatePacket agentUpdate = (AgentUpdatePacket)packet;
|
AgentUpdatePacket agentUpdate = (AgentUpdatePacket)packet;
|
||||||
|
|
||||||
|
LLClientView llClient = client as LLClientView;
|
||||||
if (agentUpdate.AgentData.SessionID != client.SessionId
|
if (agentUpdate.AgentData.SessionID != client.SessionId
|
||||||
|| agentUpdate.AgentData.AgentID != client.AgentId
|
|| agentUpdate.AgentData.AgentID != client.AgentId
|
||||||
|| !((LLClientView)client).CheckAgentUpdateSignificance(agentUpdate.AgentData))
|
|| !(llClient == null || llClient.CheckAgentUpdateSignificance(agentUpdate.AgentData)) )
|
||||||
{
|
{
|
||||||
PacketPool.Instance.ReturnPacket(packet);
|
PacketPool.Instance.ReturnPacket(packet);
|
||||||
return;
|
return;
|
||||||
|
|
|
@ -77,6 +77,36 @@ namespace OpenMetaverse
|
||||||
/// <remarks>If IsRunningOut = false, then any request to send a packet is simply dropped.</remarks>
|
/// <remarks>If IsRunningOut = false, then any request to send a packet is simply dropped.</remarks>
|
||||||
public bool IsRunningOutbound { get; private set; }
|
public bool IsRunningOutbound { get; private set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Number of UDP receives.
|
||||||
|
/// </summary>
|
||||||
|
public int UdpReceives { get; private set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Number of UDP sends
|
||||||
|
/// </summary>
|
||||||
|
public int UdpSends { get; private set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Number of receives over which to establish a receive time average.
|
||||||
|
/// </summary>
|
||||||
|
private readonly static int s_receiveTimeSamples = 500;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Current number of samples taken to establish a receive time average.
|
||||||
|
/// </summary>
|
||||||
|
private int m_currentReceiveTimeSamples;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Cumulative receive time for the sample so far.
|
||||||
|
/// </summary>
|
||||||
|
private int m_receiveTicksInCurrentSamplePeriod;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The average time taken for each require receive in the last sample.
|
||||||
|
/// </summary>
|
||||||
|
public float AverageReceiveTicksForLastSamplePeriod { get; private set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Default constructor
|
/// Default constructor
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
@ -275,6 +305,8 @@ namespace OpenMetaverse
|
||||||
// to AsyncBeginReceive
|
// to AsyncBeginReceive
|
||||||
if (IsRunningInbound)
|
if (IsRunningInbound)
|
||||||
{
|
{
|
||||||
|
UdpReceives++;
|
||||||
|
|
||||||
// Asynchronous mode will start another receive before the
|
// Asynchronous mode will start another receive before the
|
||||||
// callback for this packet is even fired. Very parallel :-)
|
// callback for this packet is even fired. Very parallel :-)
|
||||||
if (m_asyncPacketHandling)
|
if (m_asyncPacketHandling)
|
||||||
|
@ -286,6 +318,8 @@ namespace OpenMetaverse
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
|
int startTick = Util.EnvironmentTickCount();
|
||||||
|
|
||||||
// get the length of data actually read from the socket, store it with the
|
// get the length of data actually read from the socket, store it with the
|
||||||
// buffer
|
// buffer
|
||||||
buffer.DataLength = m_udpSocket.EndReceiveFrom(iar, ref buffer.RemoteEndPoint);
|
buffer.DataLength = m_udpSocket.EndReceiveFrom(iar, ref buffer.RemoteEndPoint);
|
||||||
|
@ -293,6 +327,23 @@ namespace OpenMetaverse
|
||||||
// call the abstract method PacketReceived(), passing the buffer that
|
// call the abstract method PacketReceived(), passing the buffer that
|
||||||
// has just been filled from the socket read.
|
// has just been filled from the socket read.
|
||||||
PacketReceived(buffer);
|
PacketReceived(buffer);
|
||||||
|
|
||||||
|
// If more than one thread can be calling AsyncEndReceive() at once (e.g. if m_asyncPacketHandler)
|
||||||
|
// then a particular stat may be inaccurate due to a race condition. We won't worry about this
|
||||||
|
// since this should be rare and won't cause a runtime problem.
|
||||||
|
if (m_currentReceiveTimeSamples >= s_receiveTimeSamples)
|
||||||
|
{
|
||||||
|
AverageReceiveTicksForLastSamplePeriod
|
||||||
|
= (float)m_receiveTicksInCurrentSamplePeriod / s_receiveTimeSamples;
|
||||||
|
|
||||||
|
m_receiveTicksInCurrentSamplePeriod = 0;
|
||||||
|
m_currentReceiveTimeSamples = 0;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
m_receiveTicksInCurrentSamplePeriod += Util.EnvironmentTickCountSubtract(startTick);
|
||||||
|
m_currentReceiveTimeSamples++;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
catch (SocketException) { }
|
catch (SocketException) { }
|
||||||
catch (ObjectDisposedException) { }
|
catch (ObjectDisposedException) { }
|
||||||
|
@ -306,7 +357,6 @@ namespace OpenMetaverse
|
||||||
if (!m_asyncPacketHandling)
|
if (!m_asyncPacketHandling)
|
||||||
AsyncBeginReceive();
|
AsyncBeginReceive();
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -336,6 +386,8 @@ namespace OpenMetaverse
|
||||||
{
|
{
|
||||||
// UDPPacketBuffer buf = (UDPPacketBuffer)result.AsyncState;
|
// UDPPacketBuffer buf = (UDPPacketBuffer)result.AsyncState;
|
||||||
m_udpSocket.EndSendTo(result);
|
m_udpSocket.EndSendTo(result);
|
||||||
|
|
||||||
|
UdpSends++;
|
||||||
}
|
}
|
||||||
catch (SocketException) { }
|
catch (SocketException) { }
|
||||||
catch (ObjectDisposedException) { }
|
catch (ObjectDisposedException) { }
|
||||||
|
|
Loading…
Reference in New Issue