aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Framework/Scenes/Scene.cs
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Region/Framework/Scenes/Scene.cs')
-rw-r--r--OpenSim/Region/Framework/Scenes/Scene.cs504
1 files changed, 375 insertions, 129 deletions
diff --git a/OpenSim/Region/Framework/Scenes/Scene.cs b/OpenSim/Region/Framework/Scenes/Scene.cs
index bdf3d1d..1575e50 100644
--- a/OpenSim/Region/Framework/Scenes/Scene.cs
+++ b/OpenSim/Region/Framework/Scenes/Scene.cs
@@ -93,6 +93,7 @@ namespace OpenSim.Region.Framework.Scenes
93 // TODO: need to figure out how allow client agents but deny 93 // TODO: need to figure out how allow client agents but deny
94 // root agents when ACL denies access to root agent 94 // root agents when ACL denies access to root agent
95 public bool m_strictAccessControl = true; 95 public bool m_strictAccessControl = true;
96 public bool m_seeIntoBannedRegion = false;
96 public int MaxUndoCount = 5; 97 public int MaxUndoCount = 5;
97 // Using this for RegionReady module to prevent LoginsDisabled from changing under our feet; 98 // Using this for RegionReady module to prevent LoginsDisabled from changing under our feet;
98 public bool LoginLock = false; 99 public bool LoginLock = false;
@@ -114,6 +115,7 @@ namespace OpenSim.Region.Framework.Scenes
114 protected ModuleLoader m_moduleLoader; 115 protected ModuleLoader m_moduleLoader;
115 protected AgentCircuitManager m_authenticateHandler; 116 protected AgentCircuitManager m_authenticateHandler;
116 protected SceneCommunicationService m_sceneGridService; 117 protected SceneCommunicationService m_sceneGridService;
118 protected ISnmpModule m_snmpService = null;
117 119
118 protected ISimulationDataService m_SimulationDataService; 120 protected ISimulationDataService m_SimulationDataService;
119 protected IEstateDataService m_EstateDataService; 121 protected IEstateDataService m_EstateDataService;
@@ -170,7 +172,7 @@ namespace OpenSim.Region.Framework.Scenes
170 private int m_update_events = 1; 172 private int m_update_events = 1;
171 private int m_update_backup = 200; 173 private int m_update_backup = 200;
172 private int m_update_terrain = 50; 174 private int m_update_terrain = 50;
173// private int m_update_land = 1; 175 private int m_update_land = 10;
174 private int m_update_coarse_locations = 50; 176 private int m_update_coarse_locations = 50;
175 177
176 private int frameMS; 178 private int frameMS;
@@ -184,6 +186,7 @@ namespace OpenSim.Region.Framework.Scenes
184 private int landMS; 186 private int landMS;
185 private int lastCompletedFrame; 187 private int lastCompletedFrame;
186 188
189 public bool CombineRegions = false;
187 private bool m_physics_enabled = true; 190 private bool m_physics_enabled = true;
188 private bool m_scripts_enabled = true; 191 private bool m_scripts_enabled = true;
189 private string m_defaultScriptEngine; 192 private string m_defaultScriptEngine;
@@ -192,6 +195,8 @@ namespace OpenSim.Region.Framework.Scenes
192 private volatile bool shuttingdown; 195 private volatile bool shuttingdown;
193 196
194 private int m_lastUpdate; 197 private int m_lastUpdate;
198 private int m_lastIncoming;
199 private int m_lastOutgoing;
195 private bool m_firstHeartbeat = true; 200 private bool m_firstHeartbeat = true;
196 201
197 private object m_deleting_scene_object = new object(); 202 private object m_deleting_scene_object = new object();
@@ -244,6 +249,19 @@ namespace OpenSim.Region.Framework.Scenes
244 get { return m_sceneGridService; } 249 get { return m_sceneGridService; }
245 } 250 }
246 251
252 public ISnmpModule SnmpService
253 {
254 get
255 {
256 if (m_snmpService == null)
257 {
258 m_snmpService = RequestModuleInterface<ISnmpModule>();
259 }
260
261 return m_snmpService;
262 }
263 }
264
247 public ISimulationDataService SimulationDataService 265 public ISimulationDataService SimulationDataService
248 { 266 {
249 get 267 get
@@ -572,7 +590,10 @@ namespace OpenSim.Region.Framework.Scenes
572 m_regInfo = regInfo; 590 m_regInfo = regInfo;
573 m_regionHandle = m_regInfo.RegionHandle; 591 m_regionHandle = m_regInfo.RegionHandle;
574 m_regionName = m_regInfo.RegionName; 592 m_regionName = m_regInfo.RegionName;
593 m_datastore = m_regInfo.DataStore;
575 m_lastUpdate = Util.EnvironmentTickCount(); 594 m_lastUpdate = Util.EnvironmentTickCount();
595 m_lastIncoming = 0;
596 m_lastOutgoing = 0;
576 597
577 m_physicalPrim = physicalPrim; 598 m_physicalPrim = physicalPrim;
578 m_seeIntoRegionFromNeighbor = SeeIntoRegionFromNeighbor; 599 m_seeIntoRegionFromNeighbor = SeeIntoRegionFromNeighbor;
@@ -586,6 +607,8 @@ namespace OpenSim.Region.Framework.Scenes
586 #region Region Settings 607 #region Region Settings
587 608
588 // Load region settings 609 // Load region settings
610 m_regInfo.WindlightSettings = SimulationDataService.LoadRegionWindlightSettings(m_regInfo.RegionID);
611
589 m_regInfo.RegionSettings = simDataService.LoadRegionSettings(m_regInfo.RegionID); 612 m_regInfo.RegionSettings = simDataService.LoadRegionSettings(m_regInfo.RegionID);
590 if (estateDataService != null) 613 if (estateDataService != null)
591 m_regInfo.EstateSettings = estateDataService.LoadEstateSettings(m_regInfo.RegionID, false); 614 m_regInfo.EstateSettings = estateDataService.LoadEstateSettings(m_regInfo.RegionID, false);
@@ -663,9 +686,10 @@ namespace OpenSim.Region.Framework.Scenes
663 //Animation states 686 //Animation states
664 m_useFlySlow = startupConfig.GetBoolean("enableflyslow", false); 687 m_useFlySlow = startupConfig.GetBoolean("enableflyslow", false);
665 // TODO: Change default to true once the feature is supported 688 // TODO: Change default to true once the feature is supported
666 m_usePreJump = startupConfig.GetBoolean("enableprejump", false); 689 m_usePreJump = startupConfig.GetBoolean("enableprejump", true);
667
668 m_maxNonphys = startupConfig.GetFloat("NonPhysicalPrimMax", m_maxNonphys); 690 m_maxNonphys = startupConfig.GetFloat("NonPhysicalPrimMax", m_maxNonphys);
691
692 m_log.DebugFormat("[SCENE]: prejump is {0}", m_usePreJump ? "ON" : "OFF");
669 if (RegionInfo.NonphysPrimMax > 0) 693 if (RegionInfo.NonphysPrimMax > 0)
670 { 694 {
671 m_maxNonphys = RegionInfo.NonphysPrimMax; 695 m_maxNonphys = RegionInfo.NonphysPrimMax;
@@ -697,6 +721,7 @@ namespace OpenSim.Region.Framework.Scenes
697 m_persistAfter *= 10000000; 721 m_persistAfter *= 10000000;
698 722
699 m_defaultScriptEngine = startupConfig.GetString("DefaultScriptEngine", "XEngine"); 723 m_defaultScriptEngine = startupConfig.GetString("DefaultScriptEngine", "XEngine");
724 m_log.InfoFormat("[SCENE]: Default script engine {0}", m_defaultScriptEngine);
700 725
701 IConfig packetConfig = m_config.Configs["PacketPool"]; 726 IConfig packetConfig = m_config.Configs["PacketPool"];
702 if (packetConfig != null) 727 if (packetConfig != null)
@@ -706,6 +731,8 @@ namespace OpenSim.Region.Framework.Scenes
706 } 731 }
707 732
708 m_strictAccessControl = startupConfig.GetBoolean("StrictAccessControl", m_strictAccessControl); 733 m_strictAccessControl = startupConfig.GetBoolean("StrictAccessControl", m_strictAccessControl);
734 m_seeIntoBannedRegion = startupConfig.GetBoolean("SeeIntoBannedRegion", m_seeIntoBannedRegion);
735 CombineRegions = startupConfig.GetBoolean("CombineContiguousRegions", false);
709 736
710 m_generateMaptiles = startupConfig.GetBoolean("GenerateMaptiles", true); 737 m_generateMaptiles = startupConfig.GetBoolean("GenerateMaptiles", true);
711 if (m_generateMaptiles) 738 if (m_generateMaptiles)
@@ -730,9 +757,9 @@ namespace OpenSim.Region.Framework.Scenes
730 } 757 }
731 } 758 }
732 } 759 }
733 catch 760 catch (Exception e)
734 { 761 {
735 m_log.Warn("[SCENE]: Failed to load StartupConfig"); 762 m_log.Error("[SCENE]: Failed to load StartupConfig: " + e.ToString());
736 } 763 }
737 764
738 #endregion Region Config 765 #endregion Region Config
@@ -1107,7 +1134,9 @@ namespace OpenSim.Region.Framework.Scenes
1107 //m_heartbeatTimer.Elapsed += new ElapsedEventHandler(Heartbeat); 1134 //m_heartbeatTimer.Elapsed += new ElapsedEventHandler(Heartbeat);
1108 if (HeartbeatThread != null) 1135 if (HeartbeatThread != null)
1109 { 1136 {
1137 m_log.ErrorFormat("[SCENE]: Restarting heartbeat thread because it hasn't reported in in region {0}", RegionInfo.RegionName);
1110 HeartbeatThread.Abort(); 1138 HeartbeatThread.Abort();
1139 Watchdog.RemoveThread(HeartbeatThread.ManagedThreadId);
1111 HeartbeatThread = null; 1140 HeartbeatThread = null;
1112 } 1141 }
1113 m_lastUpdate = Util.EnvironmentTickCount(); 1142 m_lastUpdate = Util.EnvironmentTickCount();
@@ -1231,9 +1260,6 @@ namespace OpenSim.Region.Framework.Scenes
1231 { 1260 {
1232 while (!shuttingdown) 1261 while (!shuttingdown)
1233 Update(); 1262 Update();
1234
1235 m_lastUpdate = Util.EnvironmentTickCount();
1236 m_firstHeartbeat = false;
1237 } 1263 }
1238 catch (ThreadAbortException) 1264 catch (ThreadAbortException)
1239 { 1265 {
@@ -1339,12 +1365,12 @@ namespace OpenSim.Region.Framework.Scenes
1339 terrainMS = Util.EnvironmentTickCountSubtract(terMS); 1365 terrainMS = Util.EnvironmentTickCountSubtract(terMS);
1340 } 1366 }
1341 1367
1342 //if (Frame % m_update_land == 0) 1368 // if (Frame % m_update_land == 0)
1343 //{ 1369 // {
1344 // int ldMS = Util.EnvironmentTickCount(); 1370 // int ldMS = Util.EnvironmentTickCount();
1345 // UpdateLand(); 1371 // UpdateLand();
1346 // landMS = Util.EnvironmentTickCountSubtract(ldMS); 1372 // landMS = Util.EnvironmentTickCountSubtract(ldMS);
1347 //} 1373 // }
1348 1374
1349 frameMS = Util.EnvironmentTickCountSubtract(tmpFrameMS); 1375 frameMS = Util.EnvironmentTickCountSubtract(tmpFrameMS);
1350 otherMS = tempOnRezMS + eventMS + backupMS + terrainMS + landMS; 1376 otherMS = tempOnRezMS + eventMS + backupMS + terrainMS + landMS;
@@ -1426,12 +1452,16 @@ namespace OpenSim.Region.Framework.Scenes
1426 maintc = Util.EnvironmentTickCountSubtract(maintc); 1452 maintc = Util.EnvironmentTickCountSubtract(maintc);
1427 maintc = (int)(m_timespan * 1000) - maintc; 1453 maintc = (int)(m_timespan * 1000) - maintc;
1428 1454
1455
1456 m_lastUpdate = Util.EnvironmentTickCount();
1457 m_firstHeartbeat = false;
1458
1429 if (maintc > 0) 1459 if (maintc > 0)
1430 Thread.Sleep(maintc); 1460 Thread.Sleep(maintc);
1431 1461
1432 // Tell the watchdog that this thread is still alive 1462 // Tell the watchdog that this thread is still alive
1433 Watchdog.UpdateThread(); 1463 Watchdog.UpdateThread();
1434 } 1464 }
1435 1465
1436 public void AddGroupTarget(SceneObjectGroup grp) 1466 public void AddGroupTarget(SceneObjectGroup grp)
1437 { 1467 {
@@ -1447,9 +1477,9 @@ namespace OpenSim.Region.Framework.Scenes
1447 1477
1448 private void CheckAtTargets() 1478 private void CheckAtTargets()
1449 { 1479 {
1450 Dictionary<UUID, SceneObjectGroup>.ValueCollection objs; 1480 List<SceneObjectGroup> objs = new List<SceneObjectGroup>();
1451 lock (m_groupsWithTargets) 1481 lock (m_groupsWithTargets)
1452 objs = m_groupsWithTargets.Values; 1482 objs = new List<SceneObjectGroup>(m_groupsWithTargets.Values);
1453 1483
1454 foreach (SceneObjectGroup entry in objs) 1484 foreach (SceneObjectGroup entry in objs)
1455 entry.checkAtTargets(); 1485 entry.checkAtTargets();
@@ -1773,14 +1803,24 @@ namespace OpenSim.Region.Framework.Scenes
1773 /// <returns></returns> 1803 /// <returns></returns>
1774 public Vector3 GetNewRezLocation(Vector3 RayStart, Vector3 RayEnd, UUID RayTargetID, Quaternion rot, byte bypassRayCast, byte RayEndIsIntersection, bool frontFacesOnly, Vector3 scale, bool FaceCenter) 1804 public Vector3 GetNewRezLocation(Vector3 RayStart, Vector3 RayEnd, UUID RayTargetID, Quaternion rot, byte bypassRayCast, byte RayEndIsIntersection, bool frontFacesOnly, Vector3 scale, bool FaceCenter)
1775 { 1805 {
1806
1807 float wheight = (float)RegionInfo.RegionSettings.WaterHeight;
1808 Vector3 wpos = Vector3.Zero;
1809 // Check for water surface intersection from above
1810 if ( (RayStart.Z > wheight) && (RayEnd.Z < wheight) )
1811 {
1812 float ratio = (RayStart.Z - wheight) / (RayStart.Z - RayEnd.Z);
1813 wpos.X = RayStart.X - (ratio * (RayStart.X - RayEnd.X));
1814 wpos.Y = RayStart.Y - (ratio * (RayStart.Y - RayEnd.Y));
1815 wpos.Z = wheight;
1816 }
1817
1776 Vector3 pos = Vector3.Zero; 1818 Vector3 pos = Vector3.Zero;
1777 if (RayEndIsIntersection == (byte)1) 1819 if (RayEndIsIntersection == (byte)1)
1778 { 1820 {
1779 pos = RayEnd; 1821 pos = RayEnd;
1780 return pos;
1781 } 1822 }
1782 1823 else if (RayTargetID != UUID.Zero)
1783 if (RayTargetID != UUID.Zero)
1784 { 1824 {
1785 SceneObjectPart target = GetSceneObjectPart(RayTargetID); 1825 SceneObjectPart target = GetSceneObjectPart(RayTargetID);
1786 1826
@@ -1802,7 +1842,7 @@ namespace OpenSim.Region.Framework.Scenes
1802 EntityIntersection ei = target.TestIntersectionOBB(NewRay, Quaternion.Identity, frontFacesOnly, FaceCenter); 1842 EntityIntersection ei = target.TestIntersectionOBB(NewRay, Quaternion.Identity, frontFacesOnly, FaceCenter);
1803 1843
1804 // Un-comment out the following line to Get Raytrace results printed to the console. 1844 // Un-comment out the following line to Get Raytrace results printed to the console.
1805 // m_log.Info("[RAYTRACERESULTS]: Hit:" + ei.HitTF.ToString() + " Point: " + ei.ipoint.ToString() + " Normal: " + ei.normal.ToString()); 1845 // m_log.Info("[RAYTRACERESULTS]: Hit:" + ei.HitTF.ToString() + " Point: " + ei.ipoint.ToString() + " Normal: " + ei.normal.ToString());
1806 float ScaleOffset = 0.5f; 1846 float ScaleOffset = 0.5f;
1807 1847
1808 // If we hit something 1848 // If we hit something
@@ -1825,13 +1865,10 @@ namespace OpenSim.Region.Framework.Scenes
1825 //pos.Z -= 0.25F; 1865 //pos.Z -= 0.25F;
1826 1866
1827 } 1867 }
1828
1829 return pos;
1830 } 1868 }
1831 else 1869 else
1832 { 1870 {
1833 // We don't have a target here, so we're going to raytrace all the objects in the scene. 1871 // We don't have a target here, so we're going to raytrace all the objects in the scene.
1834
1835 EntityIntersection ei = m_sceneGraph.GetClosestIntersectingPrim(new Ray(AXOrigin, AXdirection), true, false); 1872 EntityIntersection ei = m_sceneGraph.GetClosestIntersectingPrim(new Ray(AXOrigin, AXdirection), true, false);
1836 1873
1837 // Un-comment the following line to print the raytrace results to the console. 1874 // Un-comment the following line to print the raytrace results to the console.
@@ -1840,13 +1877,12 @@ namespace OpenSim.Region.Framework.Scenes
1840 if (ei.HitTF) 1877 if (ei.HitTF)
1841 { 1878 {
1842 pos = new Vector3(ei.ipoint.X, ei.ipoint.Y, ei.ipoint.Z); 1879 pos = new Vector3(ei.ipoint.X, ei.ipoint.Y, ei.ipoint.Z);
1843 } else 1880 }
1881 else
1844 { 1882 {
1845 // fall back to our stupid functionality 1883 // fall back to our stupid functionality
1846 pos = RayEnd; 1884 pos = RayEnd;
1847 } 1885 }
1848
1849 return pos;
1850 } 1886 }
1851 } 1887 }
1852 else 1888 else
@@ -1857,8 +1893,12 @@ namespace OpenSim.Region.Framework.Scenes
1857 //increase height so its above the ground. 1893 //increase height so its above the ground.
1858 //should be getting the normal of the ground at the rez point and using that? 1894 //should be getting the normal of the ground at the rez point and using that?
1859 pos.Z += scale.Z / 2f; 1895 pos.Z += scale.Z / 2f;
1860 return pos; 1896// return pos;
1861 } 1897 }
1898
1899 // check against posible water intercept
1900 if (wpos.Z > pos.Z) pos = wpos;
1901 return pos;
1862 } 1902 }
1863 1903
1864 1904
@@ -1942,7 +1982,10 @@ namespace OpenSim.Region.Framework.Scenes
1942 public bool AddRestoredSceneObject( 1982 public bool AddRestoredSceneObject(
1943 SceneObjectGroup sceneObject, bool attachToBackup, bool alreadyPersisted, bool sendClientUpdates) 1983 SceneObjectGroup sceneObject, bool attachToBackup, bool alreadyPersisted, bool sendClientUpdates)
1944 { 1984 {
1945 return m_sceneGraph.AddRestoredSceneObject(sceneObject, attachToBackup, alreadyPersisted, sendClientUpdates); 1985 bool result = m_sceneGraph.AddRestoredSceneObject(sceneObject, attachToBackup, alreadyPersisted, sendClientUpdates);
1986 if (result)
1987 sceneObject.IsDeleted = false;
1988 return result;
1946 } 1989 }
1947 1990
1948 /// <summary> 1991 /// <summary>
@@ -2032,6 +2075,15 @@ namespace OpenSim.Region.Framework.Scenes
2032 /// </summary> 2075 /// </summary>
2033 public void DeleteAllSceneObjects() 2076 public void DeleteAllSceneObjects()
2034 { 2077 {
2078 DeleteAllSceneObjects(false);
2079 }
2080
2081 /// <summary>
2082 /// Delete every object from the scene. This does not include attachments worn by avatars.
2083 /// </summary>
2084 public void DeleteAllSceneObjects(bool exceptNoCopy)
2085 {
2086 List<SceneObjectGroup> toReturn = new List<SceneObjectGroup>();
2035 lock (Entities) 2087 lock (Entities)
2036 { 2088 {
2037 EntityBase[] entities = Entities.GetEntities(); 2089 EntityBase[] entities = Entities.GetEntities();
@@ -2040,11 +2092,24 @@ namespace OpenSim.Region.Framework.Scenes
2040 if (e is SceneObjectGroup) 2092 if (e is SceneObjectGroup)
2041 { 2093 {
2042 SceneObjectGroup sog = (SceneObjectGroup)e; 2094 SceneObjectGroup sog = (SceneObjectGroup)e;
2043 if (!sog.IsAttachment) 2095 if (sog != null && !sog.IsAttachment)
2044 DeleteSceneObject((SceneObjectGroup)e, false); 2096 {
2097 if (!exceptNoCopy || ((sog.GetEffectivePermissions() & (uint)PermissionMask.Copy) != 0))
2098 {
2099 DeleteSceneObject((SceneObjectGroup)e, false);
2100 }
2101 else
2102 {
2103 toReturn.Add((SceneObjectGroup)e);
2104 }
2105 }
2045 } 2106 }
2046 } 2107 }
2047 } 2108 }
2109 if (toReturn.Count > 0)
2110 {
2111 returnObjects(toReturn.ToArray(), UUID.Zero);
2112 }
2048 } 2113 }
2049 2114
2050 /// <summary> 2115 /// <summary>
@@ -2093,6 +2158,8 @@ namespace OpenSim.Region.Framework.Scenes
2093 } 2158 }
2094 2159
2095 group.DeleteGroupFromScene(silent); 2160 group.DeleteGroupFromScene(silent);
2161 if (!silent)
2162 SendKillObject(new List<uint>() { group.LocalId });
2096 2163
2097// m_log.DebugFormat("[SCENE]: Exit DeleteSceneObject() for {0} {1}", group.Name, group.UUID); 2164// m_log.DebugFormat("[SCENE]: Exit DeleteSceneObject() for {0} {1}", group.Name, group.UUID);
2098 } 2165 }
@@ -2445,10 +2512,17 @@ namespace OpenSim.Region.Framework.Scenes
2445 /// <returns>True if the SceneObjectGroup was added, False if it was not</returns> 2512 /// <returns>True if the SceneObjectGroup was added, False if it was not</returns>
2446 public bool AddSceneObject(SceneObjectGroup sceneObject) 2513 public bool AddSceneObject(SceneObjectGroup sceneObject)
2447 { 2514 {
2515 if (sceneObject.OwnerID == UUID.Zero)
2516 {
2517 m_log.ErrorFormat("[SCENE]: Owner ID for {0} was zero", sceneObject.UUID);
2518 return false;
2519 }
2520
2448 // If the user is banned, we won't let any of their objects 2521 // If the user is banned, we won't let any of their objects
2449 // enter. Period. 2522 // enter. Period.
2450 // 2523 //
2451 if (m_regInfo.EstateSettings.IsBanned(sceneObject.OwnerID)) 2524 int flags = GetUserFlags(sceneObject.OwnerID);
2525 if (m_regInfo.EstateSettings.IsBanned(sceneObject.OwnerID, flags))
2452 { 2526 {
2453 m_log.Info("[INTERREGION]: Denied prim crossing for " + 2527 m_log.Info("[INTERREGION]: Denied prim crossing for " +
2454 "banned avatar"); 2528 "banned avatar");
@@ -2492,15 +2566,28 @@ namespace OpenSim.Region.Framework.Scenes
2492 2566
2493 if (AttachmentsModule != null) 2567 if (AttachmentsModule != null)
2494 AttachmentsModule.AttachObject(sp.ControllingClient, grp, 0, false); 2568 AttachmentsModule.AttachObject(sp.ControllingClient, grp, 0, false);
2569
2570 m_log.DebugFormat("[SCENE]: Attachment {0} arrived and scene presence was found, attaching", sceneObject.UUID);
2495 } 2571 }
2496 else 2572 else
2497 { 2573 {
2574 m_log.DebugFormat("[SCENE]: Attachment {0} arrived and scene presence was not found, setting to temp", sceneObject.UUID);
2498 RootPrim.RemFlag(PrimFlags.TemporaryOnRez); 2575 RootPrim.RemFlag(PrimFlags.TemporaryOnRez);
2499 RootPrim.AddFlag(PrimFlags.TemporaryOnRez); 2576 RootPrim.AddFlag(PrimFlags.TemporaryOnRez);
2500 } 2577 }
2578 if (sceneObject.OwnerID == UUID.Zero)
2579 {
2580 m_log.ErrorFormat("[SCENE]: Owner ID for {0} was zero after attachment processing. BUG!", sceneObject.UUID);
2581 return false;
2582 }
2501 } 2583 }
2502 else 2584 else
2503 { 2585 {
2586 if (sceneObject.OwnerID == UUID.Zero)
2587 {
2588 m_log.ErrorFormat("[SCENE]: Owner ID for non-attachment {0} was zero", sceneObject.UUID);
2589 return false;
2590 }
2504 AddRestoredSceneObject(sceneObject, true, false); 2591 AddRestoredSceneObject(sceneObject, true, false);
2505 2592
2506 if (!Permissions.CanObjectEntry(sceneObject.UUID, 2593 if (!Permissions.CanObjectEntry(sceneObject.UUID,
@@ -2530,6 +2617,24 @@ namespace OpenSim.Region.Framework.Scenes
2530 return 2; // StateSource.PrimCrossing 2617 return 2; // StateSource.PrimCrossing
2531 } 2618 }
2532 2619
2620 public int GetUserFlags(UUID user)
2621 {
2622 //Unfortunately the SP approach means that the value is cached until region is restarted
2623 /*
2624 ScenePresence sp;
2625 if (TryGetScenePresence(user, out sp))
2626 {
2627 return sp.UserFlags;
2628 }
2629 else
2630 {
2631 */
2632 UserAccount uac = UserAccountService.GetUserAccount(RegionInfo.ScopeID, user);
2633 if (uac == null)
2634 return 0;
2635 return uac.UserFlags;
2636 //}
2637 }
2533 #endregion 2638 #endregion
2534 2639
2535 #region Add/Remove Avatar Methods 2640 #region Add/Remove Avatar Methods
@@ -2550,6 +2655,7 @@ namespace OpenSim.Region.Framework.Scenes
2550 (aCircuit.teleportFlags & (uint)Constants.TeleportFlags.ViaLogin) != 0; 2655 (aCircuit.teleportFlags & (uint)Constants.TeleportFlags.ViaLogin) != 0;
2551 2656
2552 CheckHeartbeat(); 2657 CheckHeartbeat();
2658 ScenePresence presence;
2553 2659
2554 if (GetScenePresence(client.AgentId) == null) // ensure there is no SP here 2660 if (GetScenePresence(client.AgentId) == null) // ensure there is no SP here
2555 { 2661 {
@@ -2573,7 +2679,7 @@ namespace OpenSim.Region.Framework.Scenes
2573 } 2679 }
2574 } 2680 }
2575 2681
2576 if (GetScenePresence(client.AgentId) != null) 2682 if (TryGetScenePresence(client.AgentId, out presence))
2577 { 2683 {
2578 m_LastLogin = Util.EnvironmentTickCount(); 2684 m_LastLogin = Util.EnvironmentTickCount();
2579 2685
@@ -2582,7 +2688,14 @@ namespace OpenSim.Region.Framework.Scenes
2582 2688
2583 EventManager.TriggerOnNewClient(client); 2689 EventManager.TriggerOnNewClient(client);
2584 if (vialogin) 2690 if (vialogin)
2691 {
2585 EventManager.TriggerOnClientLogin(client); 2692 EventManager.TriggerOnClientLogin(client);
2693
2694 // Send initial parcel data
2695 Vector3 pos = presence.AbsolutePosition;
2696 ILandObject land = LandChannel.GetLandObject(pos.X, pos.Y);
2697 land.SendLandUpdateToClient(presence.ControllingClient);
2698 }
2586 } 2699 }
2587 } 2700 }
2588 2701
@@ -2655,19 +2768,12 @@ namespace OpenSim.Region.Framework.Scenes
2655 // and the scene presence and the client, if they exist 2768 // and the scene presence and the client, if they exist
2656 try 2769 try
2657 { 2770 {
2658 // We need to wait for the client to make UDP contact first. 2771 ScenePresence sp = GetScenePresence(agentID);
2659 // It's the UDP contact that creates the scene presence 2772 PresenceService.LogoutAgent(sp.ControllingClient.SessionId);
2660 ScenePresence sp = WaitGetScenePresence(agentID); 2773
2661 if (sp != null) 2774 if (sp != null)
2662 {
2663 PresenceService.LogoutAgent(sp.ControllingClient.SessionId);
2664
2665 sp.ControllingClient.Close(); 2775 sp.ControllingClient.Close();
2666 } 2776
2667 else
2668 {
2669 m_log.WarnFormat("[SCENE]: Could not find scene presence for {0}", agentID);
2670 }
2671 // BANG! SLASH! 2777 // BANG! SLASH!
2672 m_authenticateHandler.RemoveCircuit(agentID); 2778 m_authenticateHandler.RemoveCircuit(agentID);
2673 2779
@@ -2767,6 +2873,7 @@ namespace OpenSim.Region.Framework.Scenes
2767 client.OnFetchInventory += HandleFetchInventory; 2873 client.OnFetchInventory += HandleFetchInventory;
2768 client.OnUpdateInventoryItem += UpdateInventoryItemAsset; 2874 client.OnUpdateInventoryItem += UpdateInventoryItemAsset;
2769 client.OnCopyInventoryItem += CopyInventoryItem; 2875 client.OnCopyInventoryItem += CopyInventoryItem;
2876 client.OnMoveItemsAndLeaveCopy += MoveInventoryItemsLeaveCopy;
2770 client.OnMoveInventoryItem += MoveInventoryItem; 2877 client.OnMoveInventoryItem += MoveInventoryItem;
2771 client.OnRemoveInventoryItem += RemoveInventoryItem; 2878 client.OnRemoveInventoryItem += RemoveInventoryItem;
2772 client.OnRemoveInventoryFolder += RemoveInventoryFolder; 2879 client.OnRemoveInventoryFolder += RemoveInventoryFolder;
@@ -2944,15 +3051,16 @@ namespace OpenSim.Region.Framework.Scenes
2944 /// </summary> 3051 /// </summary>
2945 /// <param name="agentId">The avatar's Unique ID</param> 3052 /// <param name="agentId">The avatar's Unique ID</param>
2946 /// <param name="client">The IClientAPI for the client</param> 3053 /// <param name="client">The IClientAPI for the client</param>
2947 public virtual void TeleportClientHome(UUID agentId, IClientAPI client) 3054 public virtual bool TeleportClientHome(UUID agentId, IClientAPI client)
2948 { 3055 {
2949 if (m_teleportModule != null) 3056 if (m_teleportModule != null)
2950 m_teleportModule.TeleportHome(agentId, client); 3057 return m_teleportModule.TeleportHome(agentId, client);
2951 else 3058 else
2952 { 3059 {
2953 m_log.DebugFormat("[SCENE]: Unable to teleport user home: no AgentTransferModule is active"); 3060 m_log.DebugFormat("[SCENE]: Unable to teleport user home: no AgentTransferModule is active");
2954 client.SendTeleportFailed("Unable to perform teleports on this simulator."); 3061 client.SendTeleportFailed("Unable to perform teleports on this simulator.");
2955 } 3062 }
3063 return false;
2956 } 3064 }
2957 3065
2958 /// <summary> 3066 /// <summary>
@@ -3051,6 +3159,16 @@ namespace OpenSim.Region.Framework.Scenes
3051 /// <param name="flags"></param> 3159 /// <param name="flags"></param>
3052 public virtual void SetHomeRezPoint(IClientAPI remoteClient, ulong regionHandle, Vector3 position, Vector3 lookAt, uint flags) 3160 public virtual void SetHomeRezPoint(IClientAPI remoteClient, ulong regionHandle, Vector3 position, Vector3 lookAt, uint flags)
3053 { 3161 {
3162 //Add half the avatar's height so that the user doesn't fall through prims
3163 ScenePresence presence;
3164 if (TryGetScenePresence(remoteClient.AgentId, out presence))
3165 {
3166 if (presence.Appearance != null)
3167 {
3168 position.Z = position.Z + (presence.Appearance.AvatarHeight / 2);
3169 }
3170 }
3171
3054 if (GridUserService != null && GridUserService.SetHome(remoteClient.AgentId.ToString(), RegionInfo.RegionID, position, lookAt)) 3172 if (GridUserService != null && GridUserService.SetHome(remoteClient.AgentId.ToString(), RegionInfo.RegionID, position, lookAt))
3055 // FUBAR ALERT: this needs to be "Home position set." so the viewer saves a home-screenshot. 3173 // FUBAR ALERT: this needs to be "Home position set." so the viewer saves a home-screenshot.
3056 m_dialogModule.SendAlertToUser(remoteClient, "Home position set."); 3174 m_dialogModule.SendAlertToUser(remoteClient, "Home position set.");
@@ -3127,7 +3245,9 @@ namespace OpenSim.Region.Framework.Scenes
3127 regions.Remove(RegionInfo.RegionHandle); 3245 regions.Remove(RegionInfo.RegionHandle);
3128 m_sceneGridService.SendCloseChildAgentConnections(agentID, regions); 3246 m_sceneGridService.SendCloseChildAgentConnections(agentID, regions);
3129 } 3247 }
3248 m_log.Debug("[Scene] Beginning ClientClosed");
3130 m_eventManager.TriggerClientClosed(agentID, this); 3249 m_eventManager.TriggerClientClosed(agentID, this);
3250 m_log.Debug("[Scene] Finished ClientClosed");
3131 } 3251 }
3132 catch (NullReferenceException) 3252 catch (NullReferenceException)
3133 { 3253 {
@@ -3135,7 +3255,12 @@ namespace OpenSim.Region.Framework.Scenes
3135 // Avatar is already disposed :/ 3255 // Avatar is already disposed :/
3136 } 3256 }
3137 3257
3258 m_log.Debug("[Scene] Beginning OnRemovePresence");
3138 m_eventManager.TriggerOnRemovePresence(agentID); 3259 m_eventManager.TriggerOnRemovePresence(agentID);
3260 m_log.Debug("[Scene] Finished OnRemovePresence");
3261
3262 if (avatar != null && (!avatar.IsChildAgent))
3263 avatar.SaveChangedAttachments();
3139 3264
3140 if (avatar != null && (!avatar.IsChildAgent)) 3265 if (avatar != null && (!avatar.IsChildAgent))
3141 avatar.SaveChangedAttachments(); 3266 avatar.SaveChangedAttachments();
@@ -3144,7 +3269,7 @@ namespace OpenSim.Region.Framework.Scenes
3144 delegate(IClientAPI client) 3269 delegate(IClientAPI client)
3145 { 3270 {
3146 //We can safely ignore null reference exceptions. It means the avatar is dead and cleaned up anyway 3271 //We can safely ignore null reference exceptions. It means the avatar is dead and cleaned up anyway
3147 try { client.SendKillObject(avatar.RegionHandle, avatar.LocalId); } 3272 try { client.SendKillObject(avatar.RegionHandle, new List<uint>() { avatar.LocalId}); }
3148 catch (NullReferenceException) { } 3273 catch (NullReferenceException) { }
3149 }); 3274 });
3150 3275
@@ -3155,8 +3280,11 @@ namespace OpenSim.Region.Framework.Scenes
3155 } 3280 }
3156 3281
3157 // Remove the avatar from the scene 3282 // Remove the avatar from the scene
3283 m_log.Debug("[Scene] Begin RemoveScenePresence");
3158 m_sceneGraph.RemoveScenePresence(agentID); 3284 m_sceneGraph.RemoveScenePresence(agentID);
3285 m_log.Debug("[Scene] Finished RemoveScenePresence. Removing the client manager");
3159 m_clientManager.Remove(agentID); 3286 m_clientManager.Remove(agentID);
3287 m_log.Debug("[Scene] Removed the client manager. Firing avatar.close");
3160 3288
3161 try 3289 try
3162 { 3290 {
@@ -3170,9 +3298,10 @@ namespace OpenSim.Region.Framework.Scenes
3170 { 3298 {
3171 m_log.Error("[SCENE] Scene.cs:RemoveClient exception: " + e.ToString()); 3299 m_log.Error("[SCENE] Scene.cs:RemoveClient exception: " + e.ToString());
3172 } 3300 }
3173 3301 m_log.Debug("[Scene] Done. Firing RemoveCircuit");
3174 m_authenticateHandler.RemoveCircuit(avatar.ControllingClient.CircuitCode); 3302 m_authenticateHandler.RemoveCircuit(avatar.ControllingClient.CircuitCode);
3175 CleanDroppedAttachments(); 3303 CleanDroppedAttachments();
3304 m_log.Debug("[Scene] The avatar has left the building");
3176 //m_log.InfoFormat("[SCENE] Memory pre GC {0}", System.GC.GetTotalMemory(false)); 3305 //m_log.InfoFormat("[SCENE] Memory pre GC {0}", System.GC.GetTotalMemory(false));
3177 //m_log.InfoFormat("[SCENE] Memory post GC {0}", System.GC.GetTotalMemory(true)); 3306 //m_log.InfoFormat("[SCENE] Memory post GC {0}", System.GC.GetTotalMemory(true));
3178 } 3307 }
@@ -3203,18 +3332,24 @@ namespace OpenSim.Region.Framework.Scenes
3203 3332
3204 #region Entities 3333 #region Entities
3205 3334
3206 public void SendKillObject(uint localID) 3335 public void SendKillObject(List<uint> localIDs)
3207 { 3336 {
3208 SceneObjectPart part = GetSceneObjectPart(localID); 3337 List<uint> deleteIDs = new List<uint>();
3209 if (part != null) // It is a prim 3338
3339 foreach (uint localID in localIDs)
3210 { 3340 {
3211 if (part.ParentGroup != null && !part.ParentGroup.IsDeleted) // Valid 3341 SceneObjectPart part = GetSceneObjectPart(localID);
3342 if (part != null) // It is a prim
3212 { 3343 {
3213 if (part.ParentGroup.RootPart != part) // Child part 3344 if (part.ParentGroup != null && !part.ParentGroup.IsDeleted) // Valid
3214 return; 3345 {
3346 if (part.ParentGroup.RootPart != part) // Child part
3347 continue;
3348 }
3215 } 3349 }
3350 deleteIDs.Add(localID);
3216 } 3351 }
3217 ForEachClient(delegate(IClientAPI client) { client.SendKillObject(m_regionHandle, localID); }); 3352 ForEachClient(delegate(IClientAPI client) { client.SendKillObject(m_regionHandle, deleteIDs); });
3218 } 3353 }
3219 3354
3220 #endregion 3355 #endregion
@@ -3232,7 +3367,6 @@ namespace OpenSim.Region.Framework.Scenes
3232 //m_sceneGridService.OnChildAgentUpdate += IncomingChildAgentDataUpdate; 3367 //m_sceneGridService.OnChildAgentUpdate += IncomingChildAgentDataUpdate;
3233 //m_sceneGridService.OnRemoveKnownRegionFromAvatar += HandleRemoveKnownRegionsFromAvatar; 3368 //m_sceneGridService.OnRemoveKnownRegionFromAvatar += HandleRemoveKnownRegionsFromAvatar;
3234 m_sceneGridService.OnLogOffUser += HandleLogOffUserFromGrid; 3369 m_sceneGridService.OnLogOffUser += HandleLogOffUserFromGrid;
3235 m_sceneGridService.KiPrimitive += SendKillObject;
3236 m_sceneGridService.OnGetLandData += GetLandData; 3370 m_sceneGridService.OnGetLandData += GetLandData;
3237 } 3371 }
3238 3372
@@ -3241,7 +3375,6 @@ namespace OpenSim.Region.Framework.Scenes
3241 /// </summary> 3375 /// </summary>
3242 public void UnRegisterRegionWithComms() 3376 public void UnRegisterRegionWithComms()
3243 { 3377 {
3244 m_sceneGridService.KiPrimitive -= SendKillObject;
3245 m_sceneGridService.OnLogOffUser -= HandleLogOffUserFromGrid; 3378 m_sceneGridService.OnLogOffUser -= HandleLogOffUserFromGrid;
3246 //m_sceneGridService.OnRemoveKnownRegionFromAvatar -= HandleRemoveKnownRegionsFromAvatar; 3379 //m_sceneGridService.OnRemoveKnownRegionFromAvatar -= HandleRemoveKnownRegionsFromAvatar;
3247 //m_sceneGridService.OnChildAgentUpdate -= IncomingChildAgentDataUpdate; 3380 //m_sceneGridService.OnChildAgentUpdate -= IncomingChildAgentDataUpdate;
@@ -3321,13 +3454,16 @@ namespace OpenSim.Region.Framework.Scenes
3321 sp = null; 3454 sp = null;
3322 } 3455 }
3323 3456
3324 ILandObject land = LandChannel.GetLandObject(agent.startpos.X, agent.startpos.Y);
3325 3457
3326 //On login test land permisions 3458 //On login test land permisions
3327 if (vialogin) 3459 if (vialogin)
3328 { 3460 {
3329 if (land != null && !TestLandRestrictions(agent, land, out reason)) 3461 IUserAccountCacheModule cache = RequestModuleInterface<IUserAccountCacheModule>();
3462 if (cache != null)
3463 cache.Remove(agent.firstname + " " + agent.lastname);
3464 if (!TestLandRestrictions(agent.AgentID, out reason, ref agent.startpos.X, ref agent.startpos.Y))
3330 { 3465 {
3466 m_log.DebugFormat("[CONNECTION BEGIN]: Denying access to {0} due to no land access", agent.AgentID.ToString());
3331 return false; 3467 return false;
3332 } 3468 }
3333 } 3469 }
@@ -3350,8 +3486,13 @@ namespace OpenSim.Region.Framework.Scenes
3350 3486
3351 try 3487 try
3352 { 3488 {
3353 if (!AuthorizeUser(agent, out reason)) 3489 // Always check estate if this is a login. Always
3354 return false; 3490 // check if banned regions are to be blacked out.
3491 if (vialogin || (!m_seeIntoBannedRegion))
3492 {
3493 if (!AuthorizeUser(agent.AgentID, out reason))
3494 return false;
3495 }
3355 } 3496 }
3356 catch (Exception e) 3497 catch (Exception e)
3357 { 3498 {
@@ -3454,6 +3595,8 @@ namespace OpenSim.Region.Framework.Scenes
3454 } 3595 }
3455 } 3596 }
3456 // Honor parcel landing type and position. 3597 // Honor parcel landing type and position.
3598 /*
3599 ILandObject land = LandChannel.GetLandObject(agent.startpos.X, agent.startpos.Y);
3457 if (land != null) 3600 if (land != null)
3458 { 3601 {
3459 if (land.LandData.LandingType == (byte)1 && land.LandData.UserLocation != Vector3.Zero) 3602 if (land.LandData.LandingType == (byte)1 && land.LandData.UserLocation != Vector3.Zero)
@@ -3461,26 +3604,34 @@ namespace OpenSim.Region.Framework.Scenes
3461 agent.startpos = land.LandData.UserLocation; 3604 agent.startpos = land.LandData.UserLocation;
3462 } 3605 }
3463 } 3606 }
3607 */// This is now handled properly in ScenePresence.MakeRootAgent
3464 } 3608 }
3465 3609
3466 return true; 3610 return true;
3467 } 3611 }
3468 3612
3469 private bool TestLandRestrictions(AgentCircuitData agent, ILandObject land, out string reason) 3613 private bool TestLandRestrictions(UUID agentID, out string reason, ref float posX, ref float posY)
3470 { 3614 {
3471 3615 reason = String.Empty;
3472 bool banned = land.IsBannedFromLand(agent.AgentID); 3616 if (Permissions.IsGod(agentID))
3473 bool restricted = land.IsRestrictedFromLand(agent.AgentID); 3617 return true;
3618
3619 ILandObject land = LandChannel.GetLandObject(posX, posY);
3620 if (land == null)
3621 return false;
3622
3623 bool banned = land.IsBannedFromLand(agentID);
3624 bool restricted = land.IsRestrictedFromLand(agentID);
3474 3625
3475 if (banned || restricted) 3626 if (banned || restricted)
3476 { 3627 {
3477 ILandObject nearestParcel = GetNearestAllowedParcel(agent.AgentID, agent.startpos.X, agent.startpos.Y); 3628 ILandObject nearestParcel = GetNearestAllowedParcel(agentID, posX, posY);
3478 if (nearestParcel != null) 3629 if (nearestParcel != null)
3479 { 3630 {
3480 //Move agent to nearest allowed 3631 //Move agent to nearest allowed
3481 Vector3 newPosition = GetParcelCenterAtGround(nearestParcel); 3632 Vector3 newPosition = GetParcelCenterAtGround(nearestParcel);
3482 agent.startpos.X = newPosition.X; 3633 posX = newPosition.X;
3483 agent.startpos.Y = newPosition.Y; 3634 posY = newPosition.Y;
3484 } 3635 }
3485 else 3636 else
3486 { 3637 {
@@ -3536,19 +3687,19 @@ namespace OpenSim.Region.Framework.Scenes
3536 /// <param name="reason">outputs the reason to this string</param> 3687 /// <param name="reason">outputs the reason to this string</param>
3537 /// <returns>True if the region accepts this agent. False if it does not. False will 3688 /// <returns>True if the region accepts this agent. False if it does not. False will
3538 /// also return a reason.</returns> 3689 /// also return a reason.</returns>
3539 protected virtual bool AuthorizeUser(AgentCircuitData agent, out string reason) 3690 protected virtual bool AuthorizeUser(UUID agentID, out string reason)
3540 { 3691 {
3541 reason = String.Empty; 3692 reason = String.Empty;
3542 3693
3543 if (!m_strictAccessControl) return true; 3694 if (!m_strictAccessControl) return true;
3544 if (Permissions.IsGod(agent.AgentID)) return true; 3695 if (Permissions.IsGod(agentID)) return true;
3545 3696
3546 if (AuthorizationService != null) 3697 if (AuthorizationService != null)
3547 { 3698 {
3548 if (!AuthorizationService.IsAuthorizedForRegion(agent.AgentID.ToString(), RegionInfo.RegionID.ToString(),out reason)) 3699 if (!AuthorizationService.IsAuthorizedForRegion(agentID.ToString(), RegionInfo.RegionID.ToString(),out reason))
3549 { 3700 {
3550 m_log.WarnFormat("[CONNECTION BEGIN]: Denied access to: {0} ({1} {2}) at {3} because the user does not have access to the region", 3701 m_log.WarnFormat("[CONNECTION BEGIN]: Denied access to: {0} at {1} because the user does not have access to the region",
3551 agent.AgentID, agent.firstname, agent.lastname, RegionInfo.RegionName); 3702 agentID, RegionInfo.RegionName);
3552 //reason = String.Format("You are not currently on the access list for {0}",RegionInfo.RegionName); 3703 //reason = String.Format("You are not currently on the access list for {0}",RegionInfo.RegionName);
3553 return false; 3704 return false;
3554 } 3705 }
@@ -3556,10 +3707,26 @@ namespace OpenSim.Region.Framework.Scenes
3556 3707
3557 if (m_regInfo.EstateSettings != null) 3708 if (m_regInfo.EstateSettings != null)
3558 { 3709 {
3559 if (m_regInfo.EstateSettings.IsBanned(agent.AgentID)) 3710 int flags = GetUserFlags(agentID);
3711 if (m_regInfo.EstateSettings.IsBanned(agentID, flags))
3560 { 3712 {
3561 m_log.WarnFormat("[CONNECTION BEGIN]: Denied access to: {0} ({1} {2}) at {3} because the user is on the banlist", 3713 //Add some more info to help users
3562 agent.AgentID, agent.firstname, agent.lastname, RegionInfo.RegionName); 3714 if (!m_regInfo.EstateSettings.IsBanned(agentID, 32))
3715 {
3716 m_log.WarnFormat("[CONNECTION BEGIN]: Denied access to: {0} at {1} because the region requires age verification",
3717 agentID, RegionInfo.RegionName);
3718 reason = String.Format("Denied access to region {0}: Region requires age verification", RegionInfo.RegionName);
3719 return false;
3720 }
3721 if (!m_regInfo.EstateSettings.IsBanned(agentID, 4))
3722 {
3723 m_log.WarnFormat("[CONNECTION BEGIN]: Denied access to: {0} {1} because the region requires payment info on file",
3724 agentID, RegionInfo.RegionName);
3725 reason = String.Format("Denied access to region {0}: Region requires payment info on file", RegionInfo.RegionName);
3726 return false;
3727 }
3728 m_log.WarnFormat("[CONNECTION BEGIN]: Denied access to: {0} at {3} because the user is on the banlist",
3729 agentID, RegionInfo.RegionName);
3563 reason = String.Format("Denied access to region {0}: You have been banned from that region.", 3730 reason = String.Format("Denied access to region {0}: You have been banned from that region.",
3564 RegionInfo.RegionName); 3731 RegionInfo.RegionName);
3565 return false; 3732 return false;
@@ -3576,7 +3743,7 @@ namespace OpenSim.Region.Framework.Scenes
3576 if (groupsModule != null) 3743 if (groupsModule != null)
3577 { 3744 {
3578 GroupMembershipData[] GroupMembership = 3745 GroupMembershipData[] GroupMembership =
3579 groupsModule.GetMembershipData(agent.AgentID); 3746 groupsModule.GetMembershipData(agentID);
3580 3747
3581 if (GroupMembership != null) 3748 if (GroupMembership != null)
3582 { 3749 {
@@ -3605,44 +3772,16 @@ namespace OpenSim.Region.Framework.Scenes
3605 m_log.ErrorFormat("[CONNECTION BEGIN]: EstateGroups is null!"); 3772 m_log.ErrorFormat("[CONNECTION BEGIN]: EstateGroups is null!");
3606 3773
3607 if (!m_regInfo.EstateSettings.PublicAccess && 3774 if (!m_regInfo.EstateSettings.PublicAccess &&
3608 !m_regInfo.EstateSettings.HasAccess(agent.AgentID) && 3775 !m_regInfo.EstateSettings.HasAccess(agentID) &&
3609 !groupAccess) 3776 !groupAccess)
3610 { 3777 {
3611 m_log.WarnFormat("[CONNECTION BEGIN]: Denied access to: {0} ({1} {2}) at {3} because the user does not have access to the estate", 3778 m_log.WarnFormat("[CONNECTION BEGIN]: Denied access to: {0} at {1} because the user does not have access to the estate",
3612 agent.AgentID, agent.firstname, agent.lastname, RegionInfo.RegionName); 3779 agentID, RegionInfo.RegionName);
3613 reason = String.Format("Denied access to private region {0}: You are not on the access list for that region.", 3780 reason = String.Format("Denied access to private region {0}: You are not on the access list for that region.",
3614 RegionInfo.RegionName); 3781 RegionInfo.RegionName);
3615 return false; 3782 return false;
3616 } 3783 }
3617 3784
3618 // TODO: estate/region settings are not properly hooked up
3619 // to ILandObject.isRestrictedFromLand()
3620 // if (null != LandChannel)
3621 // {
3622 // // region seems to have local Id of 1
3623 // ILandObject land = LandChannel.GetLandObject(1);
3624 // if (null != land)
3625 // {
3626 // if (land.isBannedFromLand(agent.AgentID))
3627 // {
3628 // m_log.WarnFormat("[CONNECTION BEGIN]: Denied access to: {0} ({1} {2}) at {3} because the user has been banned from land",
3629 // agent.AgentID, agent.firstname, agent.lastname, RegionInfo.RegionName);
3630 // reason = String.Format("Denied access to private region {0}: You are banned from that region.",
3631 // RegionInfo.RegionName);
3632 // return false;
3633 // }
3634
3635 // if (land.isRestrictedFromLand(agent.AgentID))
3636 // {
3637 // m_log.WarnFormat("[CONNECTION BEGIN]: Denied access to: {0} ({1} {2}) at {3} because the user does not have access to the region",
3638 // agent.AgentID, agent.firstname, agent.lastname, RegionInfo.RegionName);
3639 // reason = String.Format("Denied access to private region {0}: You are not on the access list for that region.",
3640 // RegionInfo.RegionName);
3641 // return false;
3642 // }
3643 // }
3644 // }
3645
3646 return true; 3785 return true;
3647 } 3786 }
3648 3787
@@ -3746,6 +3885,13 @@ namespace OpenSim.Region.Framework.Scenes
3746 3885
3747 // We have to wait until the viewer contacts this region after receiving EAC. 3886 // We have to wait until the viewer contacts this region after receiving EAC.
3748 // That calls AddNewClient, which finally creates the ScenePresence 3887 // That calls AddNewClient, which finally creates the ScenePresence
3888 int flags = GetUserFlags(cAgentData.AgentID);
3889 if (m_regInfo.EstateSettings.IsBanned(cAgentData.AgentID, flags))
3890 {
3891 m_log.DebugFormat("[SCENE]: Denying root agent entry to {0}: banned", cAgentData.AgentID);
3892 return false;
3893 }
3894
3749 ILandObject nearestParcel = GetNearestAllowedParcel(cAgentData.AgentID, Constants.RegionSize / 2, Constants.RegionSize / 2); 3895 ILandObject nearestParcel = GetNearestAllowedParcel(cAgentData.AgentID, Constants.RegionSize / 2, Constants.RegionSize / 2);
3750 if (nearestParcel == null) 3896 if (nearestParcel == null)
3751 { 3897 {
@@ -3761,7 +3907,6 @@ namespace OpenSim.Region.Framework.Scenes
3761 return false; 3907 return false;
3762 } 3908 }
3763 3909
3764
3765 ScenePresence childAgentUpdate = WaitGetScenePresence(cAgentData.AgentID); 3910 ScenePresence childAgentUpdate = WaitGetScenePresence(cAgentData.AgentID);
3766 3911
3767 if (childAgentUpdate != null) 3912 if (childAgentUpdate != null)
@@ -3828,12 +3973,22 @@ namespace OpenSim.Region.Framework.Scenes
3828 return false; 3973 return false;
3829 } 3974 }
3830 3975
3976 public bool IncomingCloseAgent(UUID agentID)
3977 {
3978 return IncomingCloseAgent(agentID, false);
3979 }
3980
3981 public bool IncomingCloseChildAgent(UUID agentID)
3982 {
3983 return IncomingCloseAgent(agentID, true);
3984 }
3985
3831 /// <summary> 3986 /// <summary>
3832 /// Tell a single agent to disconnect from the region. 3987 /// Tell a single agent to disconnect from the region.
3833 /// </summary> 3988 /// </summary>
3834 /// <param name="regionHandle"></param>
3835 /// <param name="agentID"></param> 3989 /// <param name="agentID"></param>
3836 public bool IncomingCloseAgent(UUID agentID) 3990 /// <param name="childOnly"></param>
3991 public bool IncomingCloseAgent(UUID agentID, bool childOnly)
3837 { 3992 {
3838 //m_log.DebugFormat("[SCENE]: Processing incoming close agent for {0}", agentID); 3993 //m_log.DebugFormat("[SCENE]: Processing incoming close agent for {0}", agentID);
3839 3994
@@ -3845,7 +4000,7 @@ namespace OpenSim.Region.Framework.Scenes
3845 { 4000 {
3846 m_sceneGraph.removeUserCount(false); 4001 m_sceneGraph.removeUserCount(false);
3847 } 4002 }
3848 else 4003 else if (!childOnly)
3849 { 4004 {
3850 m_sceneGraph.removeUserCount(true); 4005 m_sceneGraph.removeUserCount(true);
3851 } 4006 }
@@ -3861,9 +4016,12 @@ namespace OpenSim.Region.Framework.Scenes
3861 } 4016 }
3862 else 4017 else
3863 presence.ControllingClient.SendShutdownConnectionNotice(); 4018 presence.ControllingClient.SendShutdownConnectionNotice();
4019 presence.ControllingClient.Close(false);
4020 }
4021 else if (!childOnly)
4022 {
4023 presence.ControllingClient.Close(true);
3864 } 4024 }
3865
3866 presence.ControllingClient.Close();
3867 return true; 4025 return true;
3868 } 4026 }
3869 4027
@@ -4474,34 +4632,66 @@ namespace OpenSim.Region.Framework.Scenes
4474 SimulationDataService.RemoveObject(uuid, m_regInfo.RegionID); 4632 SimulationDataService.RemoveObject(uuid, m_regInfo.RegionID);
4475 } 4633 }
4476 4634
4477 public int GetHealth() 4635 public int GetHealth(out int flags, out string message)
4478 { 4636 {
4479 // Returns: 4637 // Returns:
4480 // 1 = sim is up and accepting http requests. The heartbeat has 4638 // 1 = sim is up and accepting http requests. The heartbeat has
4481 // stopped and the sim is probably locked up, but a remote 4639 // stopped and the sim is probably locked up, but a remote
4482 // admin restart may succeed 4640 // admin restart may succeed
4483 // 4641 //
4484 // 2 = Sim is up and the heartbeat is running. The sim is likely 4642 // 2 = Sim is up and the heartbeat is running. The sim is likely
4485 // usable for people within and logins _may_ work 4643 // usable for people within
4644 //
4645 // 3 = Sim is up and one packet thread is running. Sim is
4646 // unstable and will not accept new logins
4486 // 4647 //
4487 // 3 = We have seen a new user enter within the past 4 minutes 4648 // 4 = Sim is up and both packet threads are running. Sim is
4649 // likely usable
4650 //
4651 // 5 = We have seen a new user enter within the past 4 minutes
4488 // which can be seen as positive confirmation of sim health 4652 // which can be seen as positive confirmation of sim health
4489 // 4653 //
4654
4655 flags = 0;
4656 message = String.Empty;
4657
4658 CheckHeartbeat();
4659
4660 if (m_firstHeartbeat || (m_lastIncoming == 0 && m_lastOutgoing == 0))
4661 {
4662 // We're still starting
4663 // 0 means "in startup", it can't happen another way, since
4664 // to get here, we must be able to accept http connections
4665 return 0;
4666 }
4667
4490 int health=1; // Start at 1, means we're up 4668 int health=1; // Start at 1, means we're up
4491 4669
4492 if ((Util.EnvironmentTickCountSubtract(m_lastUpdate)) < 1000) 4670 if (Util.EnvironmentTickCountSubtract(m_lastUpdate) < 1000)
4671 {
4493 health+=1; 4672 health+=1;
4494 else 4673 flags |= 1;
4674 }
4675
4676 if (Util.EnvironmentTickCountSubtract(m_lastIncoming) < 1000)
4677 {
4678 health+=1;
4679 flags |= 2;
4680 }
4681
4682 if (Util.EnvironmentTickCountSubtract(m_lastOutgoing) < 1000)
4683 {
4684 health+=1;
4685 flags |= 4;
4686 }
4687
4688 if (flags != 7)
4495 return health; 4689 return health;
4496 4690
4497 // A login in the last 4 mins? We can't be doing too badly 4691 // A login in the last 4 mins? We can't be doing too badly
4498 // 4692 //
4499 if ((Util.EnvironmentTickCountSubtract(m_LastLogin)) < 240000) 4693 if (Util.EnvironmentTickCountSubtract(m_LastLogin) < 240000)
4500 health++; 4694 health++;
4501 else
4502 return health;
4503
4504 CheckHeartbeat();
4505 4695
4506 return health; 4696 return health;
4507 } 4697 }
@@ -4694,7 +4884,7 @@ namespace OpenSim.Region.Framework.Scenes
4694 if (m_firstHeartbeat) 4884 if (m_firstHeartbeat)
4695 return; 4885 return;
4696 4886
4697 if (Util.EnvironmentTickCountSubtract(m_lastUpdate) > 2000) 4887 if (Util.EnvironmentTickCountSubtract(m_lastUpdate) > 10000)
4698 StartTimer(); 4888 StartTimer();
4699 } 4889 }
4700 4890
@@ -5103,10 +5293,28 @@ namespace OpenSim.Region.Framework.Scenes
5103 }); 5293 });
5104 } 5294 }
5105 5295
5106 foreach (SceneObjectGroup grp in objectsToDelete) 5296 if (objectsToDelete.Count > 0)
5107 { 5297 {
5108 m_log.InfoFormat("[SCENE]: Deleting dropped attachment {0} of user {1}", grp.UUID, grp.OwnerID); 5298 m_log.DebugFormat("[SCENE]: Starting delete of {0} dropped attachments", objectsToDelete.Count);
5109 DeleteSceneObject(grp, true); 5299 foreach (SceneObjectGroup grp in objectsToDelete)
5300 {
5301 m_log.InfoFormat("[SCENE]: Deleting dropped attachment {0} of user {1}", grp.UUID, grp.OwnerID);
5302 DeleteSceneObject(grp, true);
5303 }
5304 m_log.Debug("[SCENE]: Finished dropped attachment deletion");
5305 }
5306 }
5307
5308 public void ThreadAlive(int threadCode)
5309 {
5310 switch(threadCode)
5311 {
5312 case 1: // Incoming
5313 m_lastIncoming = Util.EnvironmentTickCount();
5314 break;
5315 case 2: // Incoming
5316 m_lastOutgoing = Util.EnvironmentTickCount();
5317 break;
5110 } 5318 }
5111 } 5319 }
5112 5320
@@ -5118,6 +5326,14 @@ namespace OpenSim.Region.Framework.Scenes
5118 // child agent creation, thereby emulating the SL behavior. 5326 // child agent creation, thereby emulating the SL behavior.
5119 public bool QueryAccess(UUID agentID, Vector3 position, out string reason) 5327 public bool QueryAccess(UUID agentID, Vector3 position, out string reason)
5120 { 5328 {
5329 reason = "You are banned from the region";
5330
5331 if (Permissions.IsGod(agentID))
5332 {
5333 reason = String.Empty;
5334 return true;
5335 }
5336
5121 int num = m_sceneGraph.GetNumberOfScenePresences(); 5337 int num = m_sceneGraph.GetNumberOfScenePresences();
5122 5338
5123 if (num >= RegionInfo.RegionSettings.AgentLimit) 5339 if (num >= RegionInfo.RegionSettings.AgentLimit)
@@ -5129,6 +5345,36 @@ namespace OpenSim.Region.Framework.Scenes
5129 } 5345 }
5130 } 5346 }
5131 5347
5348 if (!AuthorizeUser(agentID, out reason))
5349 {
5350 // m_log.DebugFormat("[SCENE]: Denying access for {0}", agentID);
5351 return false;
5352 }
5353
5354 if (position == Vector3.Zero) // Teleport
5355 {
5356 float posX = 128.0f;
5357 float posY = 128.0f;
5358
5359 if (!TestLandRestrictions(agentID, out reason, ref posX, ref posY))
5360 {
5361 // m_log.DebugFormat("[SCENE]: Denying {0} because they are banned on all parcels", agentID);
5362 return false;
5363 }
5364 }
5365 else // Walking
5366 {
5367 ILandObject land = LandChannel.GetLandObject(position.X, position.Y);
5368 if (land == null)
5369 return false;
5370
5371 bool banned = land.IsBannedFromLand(agentID);
5372 bool restricted = land.IsRestrictedFromLand(agentID);
5373
5374 if (banned || restricted)
5375 return false;
5376 }
5377
5132 reason = String.Empty; 5378 reason = String.Empty;
5133 return true; 5379 return true;
5134 } 5380 }