aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Framework/Scenes/Scene.cs
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--OpenSim/Region/Framework/Scenes/Scene.cs263
1 files changed, 206 insertions, 57 deletions
diff --git a/OpenSim/Region/Framework/Scenes/Scene.cs b/OpenSim/Region/Framework/Scenes/Scene.cs
index 7c3875d..aeca7df 100644
--- a/OpenSim/Region/Framework/Scenes/Scene.cs
+++ b/OpenSim/Region/Framework/Scenes/Scene.cs
@@ -36,6 +36,7 @@ using System.Timers;
36using System.Xml; 36using System.Xml;
37using Nini.Config; 37using Nini.Config;
38using OpenMetaverse; 38using OpenMetaverse;
39using OpenMetaverse.Packets;
39using OpenMetaverse.Imaging; 40using OpenMetaverse.Imaging;
40using OpenSim.Framework; 41using OpenSim.Framework;
41using OpenSim.Services.Interfaces; 42using OpenSim.Services.Interfaces;
@@ -87,8 +88,18 @@ namespace OpenSim.Region.Framework.Scenes
87 protected List<RegionInfo> m_regionRestartNotifyList = new List<RegionInfo>(); 88 protected List<RegionInfo> m_regionRestartNotifyList = new List<RegionInfo>();
88 protected List<RegionInfo> m_neighbours = new List<RegionInfo>(); 89 protected List<RegionInfo> m_neighbours = new List<RegionInfo>();
89 90
90 public volatile bool BordersLocked = false; 91 private volatile int m_bordersLocked = 0;
91 92 public bool BordersLocked
93 {
94 get { return m_bordersLocked == 1; }
95 set
96 {
97 if (value == true)
98 m_bordersLocked = 1;
99 else
100 m_bordersLocked = 0;
101 }
102 }
92 public List<Border> NorthBorders = new List<Border>(); 103 public List<Border> NorthBorders = new List<Border>();
93 public List<Border> EastBorders = new List<Border>(); 104 public List<Border> EastBorders = new List<Border>();
94 public List<Border> SouthBorders = new List<Border>(); 105 public List<Border> SouthBorders = new List<Border>();
@@ -135,6 +146,11 @@ namespace OpenSim.Region.Framework.Scenes
135 protected SceneCommunicationService m_sceneGridService; 146 protected SceneCommunicationService m_sceneGridService;
136 public bool loginsdisabled = true; 147 public bool loginsdisabled = true;
137 148
149 public new float TimeDilation
150 {
151 get { return m_sceneGraph.PhysicsScene.TimeDilation; }
152 }
153
138 public SceneCommunicationService SceneGridService 154 public SceneCommunicationService SceneGridService
139 { 155 {
140 get { return m_sceneGridService; } 156 get { return m_sceneGridService; }
@@ -252,7 +268,7 @@ namespace OpenSim.Region.Framework.Scenes
252 // Central Update Loop 268 // Central Update Loop
253 269
254 protected int m_fps = 10; 270 protected int m_fps = 10;
255 protected int m_frame; 271 protected uint m_frame;
256 protected float m_timespan = 0.089f; 272 protected float m_timespan = 0.089f;
257 protected DateTime m_lastupdate = DateTime.UtcNow; 273 protected DateTime m_lastupdate = DateTime.UtcNow;
258 274
@@ -269,6 +285,23 @@ namespace OpenSim.Region.Framework.Scenes
269 private int physicsMS2; 285 private int physicsMS2;
270 private int physicsMS; 286 private int physicsMS;
271 private int otherMS; 287 private int otherMS;
288 private int tempOnRezMS;
289 private int eventMS;
290 private int backupMS;
291 private int terrainMS;
292 private int landMS;
293 private int lastCompletedFrame;
294
295 public int MonitorFrameTime { get { return frameMS; } }
296 public int MonitorPhysicsUpdateTime { get { return physicsMS; } }
297 public int MonitorPhysicsSyncTime { get { return physicsMS2; } }
298 public int MonitorOtherTime { get { return otherMS; } }
299 public int MonitorTempOnRezTime { get { return tempOnRezMS; } }
300 public int MonitorEventTime { get { return eventMS; } } // This may need to be divided into each event?
301 public int MonitorBackupTime { get { return backupMS; } }
302 public int MonitorTerrainTime { get { return terrainMS; } }
303 public int MonitorLandTime { get { return landMS; } }
304 public int MonitorLastFrameTick { get { return lastCompletedFrame; } }
272 305
273 private bool m_physics_enabled = true; 306 private bool m_physics_enabled = true;
274 private bool m_scripts_enabled = true; 307 private bool m_scripts_enabled = true;
@@ -375,6 +408,73 @@ namespace OpenSim.Region.Framework.Scenes
375 408
376 #endregion 409 #endregion
377 410
411 #region BinaryStats
412
413 public class StatLogger
414 {
415 public DateTime StartTime;
416 public string Path;
417 public System.IO.BinaryWriter Log;
418 }
419 static StatLogger m_statLog = null;
420 static TimeSpan m_statLogPeriod = TimeSpan.FromSeconds(300);
421 static string m_statsDir = String.Empty;
422 static Object m_statLockObject = new Object();
423 private void LogSimStats(SimStats stats)
424 {
425 SimStatsPacket pack = new SimStatsPacket();
426 pack.Region = new SimStatsPacket.RegionBlock();
427 pack.Region.RegionX = stats.RegionX;
428 pack.Region.RegionY = stats.RegionY;
429 pack.Region.RegionFlags = stats.RegionFlags;
430 pack.Region.ObjectCapacity = stats.ObjectCapacity;
431 //pack.Region = //stats.RegionBlock;
432 pack.Stat = stats.StatsBlock;
433 pack.Header.Reliable = false;
434
435 // note that we are inside the reporter lock when called
436 DateTime now = DateTime.Now;
437
438 // hide some time information into the packet
439 pack.Header.Sequence = (uint)now.Ticks;
440
441 lock (m_statLockObject) // m_statLog is shared so make sure there is only executer here
442 {
443 try
444 {
445 if (m_statLog == null || now > m_statLog.StartTime + m_statLogPeriod)
446 {
447 // First log file or time has expired, start writing to a new log file
448 if (m_statLog != null && m_statLog.Log != null)
449 {
450 m_statLog.Log.Close();
451 }
452 m_statLog = new StatLogger();
453 m_statLog.StartTime = now;
454 m_statLog.Path = (m_statsDir.Length > 0 ? m_statsDir + System.IO.Path.DirectorySeparatorChar.ToString() : "")
455 + String.Format("stats-{0}.log", now.ToString("yyyyMMddHHmmss"));
456 m_statLog.Log = new BinaryWriter(File.Open(m_statLog.Path, FileMode.Append, FileAccess.Write));
457 }
458
459 // Write the serialized data to disk
460 if (m_statLog != null && m_statLog.Log != null)
461 m_statLog.Log.Write(pack.ToBytes());
462 }
463 catch (Exception ex)
464 {
465 m_log.Error("statistics gathering failed: " + ex.Message, ex);
466 if (m_statLog != null && m_statLog.Log != null)
467 {
468 m_statLog.Log.Close();
469 }
470 m_statLog = null;
471 }
472 }
473 return;
474 }
475
476 #endregion
477
378 #region Constructors 478 #region Constructors
379 479
380 public Scene(RegionInfo regInfo, AgentCircuitManager authen, 480 public Scene(RegionInfo regInfo, AgentCircuitManager authen,
@@ -560,6 +660,38 @@ namespace OpenSim.Region.Framework.Scenes
560 } 660 }
561 661
562 m_log.Info("[SCENE]: Using the " + m_update_prioritization_scheme + " prioritization scheme"); 662 m_log.Info("[SCENE]: Using the " + m_update_prioritization_scheme + " prioritization scheme");
663
664 #region BinaryStats
665
666 try
667 {
668 IConfig statConfig = m_config.Configs["Statistics.Binary"];
669 if (statConfig.Contains("enabled") && statConfig.GetBoolean("enabled"))
670 {
671 if (statConfig.Contains("collect_region_stats"))
672 {
673 if (statConfig.GetBoolean("collect_region_stats"))
674 {
675 // if enabled, add us to the event. If not enabled, I won't get called
676 StatsReporter.OnSendStatsResult += LogSimStats;
677 }
678 }
679 if (statConfig.Contains("region_stats_period_seconds"))
680 {
681 m_statLogPeriod = TimeSpan.FromSeconds(statConfig.GetInt("region_stats_period_seconds"));
682 }
683 if (statConfig.Contains("stats_dir"))
684 {
685 m_statsDir = statConfig.GetString("stats_dir");
686 }
687 }
688 }
689 catch
690 {
691 // if it doesn't work, we don't collect anything
692 }
693
694 #endregion BinaryStats
563 } 695 }
564 catch 696 catch
565 { 697 {
@@ -1013,36 +1145,25 @@ namespace OpenSim.Region.Framework.Scenes
1013 /// </summary> 1145 /// </summary>
1014 public override void Update() 1146 public override void Update()
1015 { 1147 {
1016 int maintc = 0; 1148 float physicsFPS;
1149 int maintc;
1150
1017 while (!shuttingdown) 1151 while (!shuttingdown)
1018 { 1152 {
1019//#if DEBUG
1020// int w = 0, io = 0;
1021// ThreadPool.GetAvailableThreads(out w, out io);
1022// if ((w < 10) || (io < 10))
1023// m_log.DebugFormat("[WARNING]: ThreadPool reaching exhaustion. workers = {0}; io = {1}", w, io);
1024//#endif
1025 maintc = Environment.TickCount;
1026
1027 TimeSpan SinceLastFrame = DateTime.UtcNow - m_lastupdate; 1153 TimeSpan SinceLastFrame = DateTime.UtcNow - m_lastupdate;
1028 float physicsFPS = 0; 1154 physicsFPS = 0f;
1029 1155
1030 frameMS = Environment.TickCount; 1156 maintc = otherMS = Environment.TickCount;
1157 int tmpFrameMS = maintc;
1158
1159 // Increment the frame counter
1160 ++m_frame;
1031 1161
1032 try 1162 try
1033 { 1163 {
1034 // Increment the frame counter
1035 m_frame++;
1036
1037 // Loop it
1038 if (m_frame == Int32.MaxValue)
1039 m_frame = 0;
1040
1041 otherMS = Environment.TickCount;
1042
1043 // Check if any objects have reached their targets 1164 // Check if any objects have reached their targets
1044 CheckAtTargets(); 1165 CheckAtTargets();
1045 1166
1046 // Update SceneObjectGroups that have scheduled themselves for updates 1167 // Update SceneObjectGroups that have scheduled themselves for updates
1047 // Objects queue their updates onto all scene presences 1168 // Objects queue their updates onto all scene presences
1048 if (m_frame % m_update_objects == 0) 1169 if (m_frame % m_update_objects == 0)
@@ -1053,62 +1174,92 @@ namespace OpenSim.Region.Framework.Scenes
1053 if (m_frame % m_update_presences == 0) 1174 if (m_frame % m_update_presences == 0)
1054 m_sceneGraph.UpdatePresences(); 1175 m_sceneGraph.UpdatePresences();
1055 1176
1056 physicsMS2 = Environment.TickCount; 1177 int TempPhysicsMS2 = Environment.TickCount;
1057 if ((m_frame % m_update_physics == 0) && m_physics_enabled) 1178 if ((m_frame % m_update_physics == 0) && m_physics_enabled)
1058 m_sceneGraph.UpdatePreparePhysics(); 1179 m_sceneGraph.UpdatePreparePhysics();
1059 physicsMS2 = Environment.TickCount - physicsMS2; 1180 TempPhysicsMS2 = Environment.TickCount - TempPhysicsMS2;
1181 physicsMS2 = TempPhysicsMS2;
1060 1182
1061 if (m_frame % m_update_entitymovement == 0) 1183 if (m_frame % m_update_entitymovement == 0)
1062 m_sceneGraph.UpdateScenePresenceMovement(); 1184 m_sceneGraph.UpdateScenePresenceMovement();
1063 1185
1064 physicsMS = Environment.TickCount; 1186 int TempPhysicsMS = Environment.TickCount;
1065 if ((m_frame % m_update_physics == 0) && m_physics_enabled) 1187 if (m_frame % m_update_physics == 0)
1066 physicsFPS = m_sceneGraph.UpdatePhysics( 1188 {
1067 Math.Max(SinceLastFrame.TotalSeconds, m_timespan) 1189 if (m_physics_enabled)
1068 ); 1190 physicsFPS = m_sceneGraph.UpdatePhysics(Math.Max(SinceLastFrame.TotalSeconds, m_timespan));
1069 if (m_frame % m_update_physics == 0 && SynchronizeScene != null) 1191 if (SynchronizeScene != null)
1070 SynchronizeScene(this); 1192 SynchronizeScene(this);
1071 1193 }
1072 physicsMS = Environment.TickCount - physicsMS; 1194 TempPhysicsMS = Environment.TickCount - TempPhysicsMS;
1073 physicsMS += physicsMS2; 1195 physicsMS = TempPhysicsMS;
1074 1196
1075 // Delete temp-on-rez stuff 1197 // Delete temp-on-rez stuff
1076 if (m_frame % m_update_backup == 0) 1198 if (m_frame % m_update_backup == 0)
1199 {
1200 int tozMS = Environment.TickCount;
1077 CleanTempObjects(); 1201 CleanTempObjects();
1202 tozMS -= Environment.TickCount;
1203 tempOnRezMS = tozMS;
1204 }
1078 1205
1079 if (RegionStatus != RegionStatus.SlaveScene) 1206 if (RegionStatus != RegionStatus.SlaveScene)
1080 { 1207 {
1081 if (m_frame % m_update_events == 0) 1208 if (m_frame % m_update_events == 0)
1209 {
1210 int evMS = Environment.TickCount;
1082 UpdateEvents(); 1211 UpdateEvents();
1212 evMS -= Environment.TickCount;
1213 eventMS = evMS;
1214 }
1083 1215
1084 if (m_frame % m_update_backup == 0) 1216 if (m_frame % m_update_backup == 0)
1217 {
1218 int backMS = Environment.TickCount;
1085 UpdateStorageBackup(); 1219 UpdateStorageBackup();
1220 backMS -= Environment.TickCount;
1221 backupMS = backMS;
1222 }
1086 1223
1087 if (m_frame % m_update_terrain == 0) 1224 if (m_frame % m_update_terrain == 0)
1225 {
1226 int terMS = Environment.TickCount;
1088 UpdateTerrain(); 1227 UpdateTerrain();
1228 terMS -= Environment.TickCount;
1229 terrainMS = terMS;
1230 }
1089 1231
1090 if (m_frame % m_update_land == 0) 1232 if (m_frame % m_update_land == 0)
1233 {
1234 int ldMS = Environment.TickCount;
1091 UpdateLand(); 1235 UpdateLand();
1236 ldMS -= Environment.TickCount;
1237 landMS = ldMS;
1238 }
1239
1240 int tickCount = Environment.TickCount;
1241 otherMS = tickCount - otherMS;
1242 tmpFrameMS -= tickCount;
1243 frameMS = tmpFrameMS;
1244 lastCompletedFrame = tickCount;
1092 1245
1093 otherMS = Environment.TickCount - otherMS;
1094 // if (m_frame%m_update_avatars == 0) 1246 // if (m_frame%m_update_avatars == 0)
1095 // UpdateInWorldTime(); 1247 // UpdateInWorldTime();
1096 StatsReporter.AddPhysicsFPS(physicsFPS); 1248 StatsReporter.AddPhysicsFPS(physicsFPS);
1097 StatsReporter.AddTimeDilation(m_timedilation); 1249 StatsReporter.AddTimeDilation(TimeDilation);
1098 StatsReporter.AddFPS(1); 1250 StatsReporter.AddFPS(1);
1099 StatsReporter.AddInPackets(0);
1100 StatsReporter.SetRootAgents(m_sceneGraph.GetRootAgentCount()); 1251 StatsReporter.SetRootAgents(m_sceneGraph.GetRootAgentCount());
1101 StatsReporter.SetChildAgents(m_sceneGraph.GetChildAgentCount()); 1252 StatsReporter.SetChildAgents(m_sceneGraph.GetChildAgentCount());
1102 StatsReporter.SetObjects(m_sceneGraph.GetTotalObjectsCount()); 1253 StatsReporter.SetObjects(m_sceneGraph.GetTotalObjectsCount());
1103 StatsReporter.SetActiveObjects(m_sceneGraph.GetActiveObjectsCount()); 1254 StatsReporter.SetActiveObjects(m_sceneGraph.GetActiveObjectsCount());
1104 frameMS = Environment.TickCount - frameMS;
1105 StatsReporter.addFrameMS(frameMS); 1255 StatsReporter.addFrameMS(frameMS);
1106 StatsReporter.addPhysicsMS(physicsMS); 1256 StatsReporter.addPhysicsMS(physicsMS + physicsMS2);
1107 StatsReporter.addOtherMS(otherMS); 1257 StatsReporter.addOtherMS(otherMS);
1108 StatsReporter.SetActiveScripts(m_sceneGraph.GetActiveScriptsCount()); 1258 StatsReporter.SetActiveScripts(m_sceneGraph.GetActiveScriptsCount());
1109 StatsReporter.addScriptLines(m_sceneGraph.GetScriptLPS()); 1259 StatsReporter.addScriptLines(m_sceneGraph.GetScriptLPS());
1110 } 1260 }
1111 if (loginsdisabled && (m_frame > 20)) 1261
1262 if (loginsdisabled && m_frame > 20)
1112 { 1263 {
1113 // In 99.9% of cases it is a bad idea to manually force garbage collection. However, 1264 // In 99.9% of cases it is a bad idea to manually force garbage collection. However,
1114 // this is a rare case where we know we have just went through a long cycle of heap 1265 // this is a rare case where we know we have just went through a long cycle of heap
@@ -1141,18 +1292,6 @@ namespace OpenSim.Region.Framework.Scenes
1141 } 1292 }
1142 finally 1293 finally
1143 { 1294 {
1144 //updateLock.ReleaseMutex();
1145 // Get actual time dilation
1146 float tmpval = (m_timespan / (float)SinceLastFrame.TotalSeconds);
1147
1148 // If actual time dilation is greater then one, we're catching up, so subtract
1149 // the amount that's greater then 1 from the time dilation
1150 if (tmpval > 1.0)
1151 {
1152 tmpval = tmpval - (tmpval - 1.0f);
1153 }
1154 m_timedilation = tmpval;
1155
1156 m_lastupdate = DateTime.UtcNow; 1295 m_lastupdate = DateTime.UtcNow;
1157 } 1296 }
1158 maintc = Environment.TickCount - maintc; 1297 maintc = Environment.TickCount - maintc;
@@ -1183,9 +1322,9 @@ namespace OpenSim.Region.Framework.Scenes
1183 { 1322 {
1184 lock (m_groupsWithTargets) 1323 lock (m_groupsWithTargets)
1185 { 1324 {
1186 foreach (KeyValuePair<UUID, SceneObjectGroup> kvp in m_groupsWithTargets) 1325 foreach (SceneObjectGroup entry in m_groupsWithTargets.Values)
1187 { 1326 {
1188 kvp.Value.checkAtTargets(); 1327 entry.checkAtTargets();
1189 } 1328 }
1190 } 1329 }
1191 } 1330 }
@@ -4244,6 +4383,16 @@ namespace OpenSim.Region.Framework.Scenes
4244 return m_sceneGraph.GetSceneObjectPart(fullID); 4383 return m_sceneGraph.GetSceneObjectPart(fullID);
4245 } 4384 }
4246 4385
4386 /// <summary>
4387 /// Get a scene object group that contains the prim with the given local id
4388 /// </summary>
4389 /// <param name="localID"></param>
4390 /// <returns>null if no scene object group containing that prim is found</returns>
4391 public SceneObjectGroup GetGroupByPrim(uint localID)
4392 {
4393 return m_sceneGraph.GetGroupByPrim(localID);
4394 }
4395
4247 public bool TryGetAvatar(UUID avatarId, out ScenePresence avatar) 4396 public bool TryGetAvatar(UUID avatarId, out ScenePresence avatar)
4248 { 4397 {
4249 return m_sceneGraph.TryGetAvatar(avatarId, out avatar); 4398 return m_sceneGraph.TryGetAvatar(avatarId, out avatar);
@@ -4606,7 +4755,7 @@ namespace OpenSim.Region.Framework.Scenes
4606 SceneObjectPart trackedBody = GetSceneObjectPart(joint.TrackedBodyName); // FIXME: causes a sequential lookup 4755 SceneObjectPart trackedBody = GetSceneObjectPart(joint.TrackedBodyName); // FIXME: causes a sequential lookup
4607 if (trackedBody == null) return; // the actor may have been deleted but the joint still lingers around a few frames waiting for deletion. during this time, trackedBody is NULL to prevent further motion of the joint proxy. 4756 if (trackedBody == null) return; // the actor may have been deleted but the joint still lingers around a few frames waiting for deletion. during this time, trackedBody is NULL to prevent further motion of the joint proxy.
4608 jointProxyObject.Velocity = trackedBody.Velocity; 4757 jointProxyObject.Velocity = trackedBody.Velocity;
4609 jointProxyObject.RotationalVelocity = trackedBody.RotationalVelocity; 4758 jointProxyObject.AngularVelocity = trackedBody.AngularVelocity;
4610 switch (joint.Type) 4759 switch (joint.Type)
4611 { 4760 {
4612 case PhysicsJointType.Ball: 4761 case PhysicsJointType.Ball: