Added necessary locking to LandManagementModule. As it is used by several
threads concurrently, you'll get bad Heisenbugs without correct locking. This might fix Mantis#24130.6.1-post-fixes
parent
38b99e998e
commit
718425e7dc
|
@ -59,11 +59,11 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
private LandChannel landChannel;
|
private LandChannel landChannel;
|
||||||
private Scene m_scene;
|
private Scene m_scene;
|
||||||
|
|
||||||
private readonly int[,] landIDList = new int[64, 64];
|
private readonly int[,] m_landIDList = new int[64, 64];
|
||||||
private readonly Dictionary<int, ILandObject> landList = new Dictionary<int, ILandObject>();
|
private readonly Dictionary<int, ILandObject> m_landList = new Dictionary<int, ILandObject>();
|
||||||
|
|
||||||
private bool landPrimCountTainted;
|
private bool m_landPrimCountTainted;
|
||||||
private int lastLandLocalID = LandChannel.START_LAND_LOCAL_ID - 1;
|
private int m_lastLandLocalID = LandChannel.START_LAND_LOCAL_ID - 1;
|
||||||
|
|
||||||
private bool m_allowedForcefulBans = true;
|
private bool m_allowedForcefulBans = true;
|
||||||
|
|
||||||
|
@ -75,7 +75,7 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
public void Initialise(Scene scene, IConfigSource source)
|
public void Initialise(Scene scene, IConfigSource source)
|
||||||
{
|
{
|
||||||
m_scene = scene;
|
m_scene = scene;
|
||||||
landIDList.Initialize();
|
m_landIDList.Initialize();
|
||||||
landChannel = new LandChannel(scene, this);
|
landChannel = new LandChannel(scene, this);
|
||||||
|
|
||||||
parcelInfoCache = new Cache();
|
parcelInfoCache = new Cache();
|
||||||
|
@ -154,13 +154,18 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
AllowedForcefulBans = forceful;
|
AllowedForcefulBans = forceful;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void UpdateLandObject(int local_id, LandData newData)
|
public void UpdateLandObject(int local_id, LandData data)
|
||||||
{
|
|
||||||
if (landList.ContainsKey(local_id))
|
|
||||||
{
|
{
|
||||||
|
LandData newData = data.Copy();
|
||||||
newData.LocalID = local_id;
|
newData.LocalID = local_id;
|
||||||
landList[local_id].landData = newData.Copy();
|
|
||||||
m_scene.EventManager.TriggerLandObjectUpdated((uint)local_id, landList[local_id]);
|
lock (m_landList)
|
||||||
|
{
|
||||||
|
if (m_landList.ContainsKey(local_id))
|
||||||
|
{
|
||||||
|
m_landList[local_id].landData = newData;
|
||||||
|
m_scene.EventManager.TriggerLandObjectUpdated((uint)local_id, m_landList[local_id]);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -176,9 +181,12 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
public void ResetSimLandObjects()
|
public void ResetSimLandObjects()
|
||||||
{
|
{
|
||||||
//Remove all the land objects in the sim and add a blank, full sim land object set to public
|
//Remove all the land objects in the sim and add a blank, full sim land object set to public
|
||||||
landList.Clear();
|
lock (m_landList)
|
||||||
lastLandLocalID = LandChannel.START_LAND_LOCAL_ID - 1;
|
{
|
||||||
landIDList.Initialize();
|
m_landList.Clear();
|
||||||
|
m_lastLandLocalID = LandChannel.START_LAND_LOCAL_ID - 1;
|
||||||
|
m_landIDList.Initialize();
|
||||||
|
}
|
||||||
|
|
||||||
ILandObject fullSimParcel = new LandObject(UUID.Zero, false, m_scene);
|
ILandObject fullSimParcel = new LandObject(UUID.Zero, false, m_scene);
|
||||||
|
|
||||||
|
@ -193,7 +201,10 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
|
|
||||||
public List<ILandObject> AllParcels()
|
public List<ILandObject> AllParcels()
|
||||||
{
|
{
|
||||||
return new List<ILandObject>(landList.Values);
|
lock (m_landList)
|
||||||
|
{
|
||||||
|
return new List<ILandObject>(m_landList.Values);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<ILandObject> ParcelsNearPoint(Vector3 position)
|
public List<ILandObject> ParcelsNearPoint(Vector3 position)
|
||||||
|
@ -240,9 +251,14 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
{
|
{
|
||||||
if (m_scene.RegionInfo.RegionID == regionID)
|
if (m_scene.RegionInfo.RegionID == regionID)
|
||||||
{
|
{
|
||||||
if (landList[localLandID] != null)
|
ILandObject parcelAvatarIsEntering;
|
||||||
|
lock (m_landList)
|
||||||
|
{
|
||||||
|
parcelAvatarIsEntering = m_landList[localLandID];
|
||||||
|
}
|
||||||
|
|
||||||
|
if (parcelAvatarIsEntering != null)
|
||||||
{
|
{
|
||||||
ILandObject parcelAvatarIsEntering = landList[localLandID];
|
|
||||||
if (avatar.AbsolutePosition.Z < LandChannel.BAN_LINE_SAFETY_HIEGHT)
|
if (avatar.AbsolutePosition.Z < LandChannel.BAN_LINE_SAFETY_HIEGHT)
|
||||||
{
|
{
|
||||||
if (parcelAvatarIsEntering.isBannedFromLand(avatar.UUID))
|
if (parcelAvatarIsEntering.isBannedFromLand(avatar.UUID))
|
||||||
|
@ -279,12 +295,12 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
{
|
{
|
||||||
if (checkBan.isBannedFromLand(avatar.AgentId))
|
if (checkBan.isBannedFromLand(avatar.AgentId))
|
||||||
{
|
{
|
||||||
checkBan.sendLandProperties(-30000, false, (int)ParcelResult.Single, avatar);
|
checkBan.sendLandProperties((int)ParcelStatus.CollisionBanned, false, (int)ParcelResult.Single, avatar);
|
||||||
return; //Only send one
|
return; //Only send one
|
||||||
}
|
}
|
||||||
if (checkBan.isRestrictedFromLand(avatar.AgentId))
|
if (checkBan.isRestrictedFromLand(avatar.AgentId))
|
||||||
{
|
{
|
||||||
checkBan.sendLandProperties(-40000, false, (int)ParcelResult.Single, avatar);
|
checkBan.sendLandProperties((int)ParcelStatus.CollisionNotOnAccessList, false, (int)ParcelResult.Single, avatar);
|
||||||
return; //Only send one
|
return; //Only send one
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -376,9 +392,15 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
public void handleParcelAccessRequest(UUID agentID, UUID sessionID, uint flags, int sequenceID,
|
public void handleParcelAccessRequest(UUID agentID, UUID sessionID, uint flags, int sequenceID,
|
||||||
int landLocalID, IClientAPI remote_client)
|
int landLocalID, IClientAPI remote_client)
|
||||||
{
|
{
|
||||||
if (landList.ContainsKey(landLocalID))
|
ILandObject land;
|
||||||
|
lock (m_landList)
|
||||||
{
|
{
|
||||||
landList[landLocalID].sendAccessList(agentID, sessionID, flags, sequenceID, remote_client);
|
m_landList.TryGetValue(landLocalID, out land);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (land != null)
|
||||||
|
{
|
||||||
|
m_landList[landLocalID].sendAccessList(agentID, sessionID, flags, sequenceID, remote_client);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -386,16 +408,22 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
List<ParcelManager.ParcelAccessEntry> entries,
|
List<ParcelManager.ParcelAccessEntry> entries,
|
||||||
IClientAPI remote_client)
|
IClientAPI remote_client)
|
||||||
{
|
{
|
||||||
if (landList.ContainsKey(landLocalID))
|
ILandObject land;
|
||||||
|
lock (m_landList)
|
||||||
{
|
{
|
||||||
if (agentID == landList[landLocalID].landData.OwnerID)
|
m_landList.TryGetValue(landLocalID, out land);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (land != null)
|
||||||
{
|
{
|
||||||
landList[landLocalID].updateAccessList(flags, entries, remote_client);
|
if (agentID == land.landData.OwnerID)
|
||||||
|
{
|
||||||
|
land.updateAccessList(flags, entries, remote_client);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
Console.WriteLine("INVALID LOCAL LAND ID");
|
m_log.WarnFormat("[LAND]: Invalid local land ID {0}", landLocalID);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -412,11 +440,14 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
/// Adds a land object to the stored list and adds them to the landIDList to what they own
|
/// Adds a land object to the stored list and adds them to the landIDList to what they own
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="new_land">The land object being added</param>
|
/// <param name="new_land">The land object being added</param>
|
||||||
public ILandObject AddLandObject(ILandObject new_land)
|
public ILandObject AddLandObject(ILandObject land)
|
||||||
{
|
{
|
||||||
lastLandLocalID++;
|
ILandObject new_land = land.Copy();
|
||||||
new_land.landData.LocalID = lastLandLocalID;
|
|
||||||
landList.Add(lastLandLocalID, new_land.Copy());
|
lock (m_landList)
|
||||||
|
{
|
||||||
|
int newLandLocalID = ++m_lastLandLocalID;
|
||||||
|
new_land.landData.LocalID = newLandLocalID;
|
||||||
|
|
||||||
bool[,] landBitmap = new_land.getLandBitmap();
|
bool[,] landBitmap = new_land.getLandBitmap();
|
||||||
for (int x = 0; x < 64; x++)
|
for (int x = 0; x < 64; x++)
|
||||||
|
@ -425,11 +456,15 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
{
|
{
|
||||||
if (landBitmap[x, y])
|
if (landBitmap[x, y])
|
||||||
{
|
{
|
||||||
landIDList[x, y] = lastLandLocalID;
|
m_landIDList[x, y] = newLandLocalID;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
landList[lastLandLocalID].forceUpdateLandInfo();
|
|
||||||
|
m_landList.Add(newLandLocalID, new_land);
|
||||||
|
}
|
||||||
|
|
||||||
|
new_land.forceUpdateLandInfo();
|
||||||
m_scene.EventManager.TriggerLandObjectAdded(new_land);
|
m_scene.EventManager.TriggerLandObjectAdded(new_land);
|
||||||
return new_land;
|
return new_land;
|
||||||
}
|
}
|
||||||
|
@ -439,33 +474,41 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="local_id">Land.localID of the peice of land to remove.</param>
|
/// <param name="local_id">Land.localID of the peice of land to remove.</param>
|
||||||
public void removeLandObject(int local_id)
|
public void removeLandObject(int local_id)
|
||||||
|
{
|
||||||
|
lock (m_landList)
|
||||||
{
|
{
|
||||||
for (int x = 0; x < 64; x++)
|
for (int x = 0; x < 64; x++)
|
||||||
{
|
{
|
||||||
for (int y = 0; y < 64; y++)
|
for (int y = 0; y < 64; y++)
|
||||||
{
|
{
|
||||||
if (landIDList[x, y] == local_id)
|
if (m_landIDList[x, y] == local_id)
|
||||||
{
|
{
|
||||||
|
m_log.WarnFormat("[LAND]: Not removing land object {0}; still being used at {1}, {2}",
|
||||||
|
local_id, x, y);
|
||||||
return;
|
return;
|
||||||
//throw new Exception("Could not remove land object. Still being used at " + x + ", " + y);
|
//throw new Exception("Could not remove land object. Still being used at " + x + ", " + y);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
m_scene.EventManager.TriggerLandObjectRemoved(landList[local_id].landData.GlobalID);
|
m_scene.EventManager.TriggerLandObjectRemoved(m_landList[local_id].landData.GlobalID);
|
||||||
landList.Remove(local_id);
|
m_landList.Remove(local_id);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void performFinalLandJoin(ILandObject master, ILandObject slave)
|
private void performFinalLandJoin(ILandObject master, ILandObject slave)
|
||||||
{
|
{
|
||||||
bool[,] landBitmapSlave = slave.getLandBitmap();
|
bool[,] landBitmapSlave = slave.getLandBitmap();
|
||||||
|
lock (m_landList)
|
||||||
|
{
|
||||||
for (int x = 0; x < 64; x++)
|
for (int x = 0; x < 64; x++)
|
||||||
{
|
{
|
||||||
for (int y = 0; y < 64; y++)
|
for (int y = 0; y < 64; y++)
|
||||||
{
|
{
|
||||||
if (landBitmapSlave[x, y])
|
if (landBitmapSlave[x, y])
|
||||||
{
|
{
|
||||||
landIDList[x, y] = master.landData.LocalID;
|
m_landIDList[x, y] = master.landData.LocalID;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -476,11 +519,11 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
|
|
||||||
public ILandObject GetLandObject(int parcelLocalID)
|
public ILandObject GetLandObject(int parcelLocalID)
|
||||||
{
|
{
|
||||||
lock (landList)
|
lock (m_landList)
|
||||||
{
|
{
|
||||||
if (landList.ContainsKey(parcelLocalID))
|
if (m_landList.ContainsKey(parcelLocalID))
|
||||||
{
|
{
|
||||||
return landList[parcelLocalID];
|
return m_landList[parcelLocalID];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return null;
|
return null;
|
||||||
|
@ -511,7 +554,10 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
{
|
{
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
return landList[landIDList[x, y]];
|
lock (m_landList)
|
||||||
|
{
|
||||||
|
return m_landList[m_landIDList[x, y]];
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public ILandObject GetLandObject(int x, int y)
|
public ILandObject GetLandObject(int x, int y)
|
||||||
|
@ -522,7 +568,10 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
// they happen every time at border crossings
|
// they happen every time at border crossings
|
||||||
throw new Exception("Error: Parcel not found at point " + x + ", " + y);
|
throw new Exception("Error: Parcel not found at point " + x + ", " + y);
|
||||||
}
|
}
|
||||||
return landList[landIDList[x / 4, y / 4]];
|
lock (m_landIDList)
|
||||||
|
{
|
||||||
|
return m_landList[m_landIDList[x / 4, y / 4]];
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
@ -531,20 +580,23 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
|
|
||||||
public void ResetAllLandPrimCounts()
|
public void ResetAllLandPrimCounts()
|
||||||
{
|
{
|
||||||
foreach (LandObject p in landList.Values)
|
lock (m_landList)
|
||||||
|
{
|
||||||
|
foreach (LandObject p in m_landList.Values)
|
||||||
{
|
{
|
||||||
p.resetLandPrimCounts();
|
p.resetLandPrimCounts();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public void SetPrimsTainted()
|
public void SetPrimsTainted()
|
||||||
{
|
{
|
||||||
landPrimCountTainted = true;
|
m_landPrimCountTainted = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public bool IsLandPrimCountTainted()
|
public bool IsLandPrimCountTainted()
|
||||||
{
|
{
|
||||||
return landPrimCountTainted;
|
return m_landPrimCountTainted;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void AddPrimToLandPrimCounts(SceneObjectGroup obj)
|
public void AddPrimToLandPrimCounts(SceneObjectGroup obj)
|
||||||
|
@ -559,32 +611,46 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
|
|
||||||
public void RemovePrimFromLandPrimCounts(SceneObjectGroup obj)
|
public void RemovePrimFromLandPrimCounts(SceneObjectGroup obj)
|
||||||
{
|
{
|
||||||
foreach (LandObject p in landList.Values)
|
|
||||||
|
lock (m_landList)
|
||||||
|
{
|
||||||
|
foreach (LandObject p in m_landList.Values)
|
||||||
{
|
{
|
||||||
p.removePrimFromCount(obj);
|
p.removePrimFromCount(obj);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public void FinalizeLandPrimCountUpdate()
|
public void FinalizeLandPrimCountUpdate()
|
||||||
{
|
{
|
||||||
|
m_log.Debug("Called FinalizeLandPrimCountUpdate start");
|
||||||
//Get Simwide prim count for owner
|
//Get Simwide prim count for owner
|
||||||
Dictionary<UUID, List<LandObject>> landOwnersAndParcels = new Dictionary<UUID, List<LandObject>>();
|
Dictionary<UUID, List<LandObject>> landOwnersAndParcels = new Dictionary<UUID, List<LandObject>>();
|
||||||
foreach (LandObject p in landList.Values)
|
lock (m_landList)
|
||||||
{
|
{
|
||||||
|
m_log.DebugFormat("[LAND]: Got {0} parcels", m_landList.Count);
|
||||||
|
foreach (LandObject p in m_landList.Values)
|
||||||
|
{
|
||||||
|
m_log.DebugFormat("processing land {0}", p.GetHashCode());
|
||||||
if (!landOwnersAndParcels.ContainsKey(p.landData.OwnerID))
|
if (!landOwnersAndParcels.ContainsKey(p.landData.OwnerID))
|
||||||
{
|
{
|
||||||
|
m_log.DebugFormat("adding new owner {0} to landlist", p.landData.OwnerID);
|
||||||
List<LandObject> tempList = new List<LandObject>();
|
List<LandObject> tempList = new List<LandObject>();
|
||||||
tempList.Add(p);
|
tempList.Add(p);
|
||||||
landOwnersAndParcels.Add(p.landData.OwnerID, tempList);
|
landOwnersAndParcels.Add(p.landData.OwnerID, tempList);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
m_log.DebugFormat("adding to owner {0}", p.landData.OwnerID);
|
||||||
landOwnersAndParcels[p.landData.OwnerID].Add(p);
|
landOwnersAndParcels[p.landData.OwnerID].Add(p);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
m_log.DebugFormat("got {0} owners of land", landOwnersAndParcels.Count);
|
||||||
foreach (UUID owner in landOwnersAndParcels.Keys)
|
foreach (UUID owner in landOwnersAndParcels.Keys)
|
||||||
{
|
{
|
||||||
|
m_log.DebugFormat("processing owner {0}", owner);
|
||||||
int simArea = 0;
|
int simArea = 0;
|
||||||
int simPrims = 0;
|
int simPrims = 0;
|
||||||
foreach (LandObject p in landOwnersAndParcels[owner])
|
foreach (LandObject p in landOwnersAndParcels[owner])
|
||||||
|
@ -592,18 +658,23 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
simArea += p.landData.Area;
|
simArea += p.landData.Area;
|
||||||
simPrims += p.landData.OwnerPrims + p.landData.OtherPrims + p.landData.GroupPrims +
|
simPrims += p.landData.OwnerPrims + p.landData.OtherPrims + p.landData.GroupPrims +
|
||||||
p.landData.SelectedPrims;
|
p.landData.SelectedPrims;
|
||||||
|
m_log.DebugFormat("added {0} m² of land, total {1}", p.landData.Area, simArea);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
m_log.DebugFormat("setting total area of {0} to {1} for {2} parcels", owner, simArea, landOwnersAndParcels[owner].Count);
|
||||||
foreach (LandObject p in landOwnersAndParcels[owner])
|
foreach (LandObject p in landOwnersAndParcels[owner])
|
||||||
{
|
{
|
||||||
|
m_log.DebugFormat("... in land {0}", p.GetHashCode());
|
||||||
p.landData.SimwideArea = simArea;
|
p.landData.SimwideArea = simArea;
|
||||||
p.landData.SimwidePrims = simPrims;
|
p.landData.SimwidePrims = simPrims;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
m_log.Debug("Called FinalizeLandPrimCountUpdate end");
|
||||||
}
|
}
|
||||||
|
|
||||||
public void UpdateLandPrimCounts()
|
public void UpdateLandPrimCounts()
|
||||||
{
|
{
|
||||||
|
m_log.Debug("Called UpdateLandPrimCounts");
|
||||||
ResetAllLandPrimCounts();
|
ResetAllLandPrimCounts();
|
||||||
lock (m_scene.Entities)
|
lock (m_scene.Entities)
|
||||||
{
|
{
|
||||||
|
@ -619,15 +690,16 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
FinalizeLandPrimCountUpdate();
|
FinalizeLandPrimCountUpdate();
|
||||||
landPrimCountTainted = false;
|
m_landPrimCountTainted = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void PerformParcelPrimCountUpdate()
|
public void PerformParcelPrimCountUpdate()
|
||||||
{
|
{
|
||||||
|
m_log.Debug("Called PerformParcelPrimCountUpdate");
|
||||||
ResetAllLandPrimCounts();
|
ResetAllLandPrimCounts();
|
||||||
m_scene.EventManager.TriggerParcelPrimCountUpdate();
|
m_scene.EventManager.TriggerParcelPrimCountUpdate();
|
||||||
FinalizeLandPrimCountUpdate();
|
FinalizeLandPrimCountUpdate();
|
||||||
landPrimCountTainted = false;
|
m_landPrimCountTainted = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -684,9 +756,12 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
|
|
||||||
//Now, lets set the subdivision area of the original to false
|
//Now, lets set the subdivision area of the original to false
|
||||||
int startLandObjectIndex = startLandObject.landData.LocalID;
|
int startLandObjectIndex = startLandObject.landData.LocalID;
|
||||||
landList[startLandObjectIndex].setLandBitmap(
|
lock (m_landList)
|
||||||
|
{
|
||||||
|
m_landList[startLandObjectIndex].setLandBitmap(
|
||||||
newLand.modifyLandBitmapSquare(startLandObject.getLandBitmap(), start_x, start_y, end_x, end_y, false));
|
newLand.modifyLandBitmapSquare(startLandObject.getLandBitmap(), start_x, start_y, end_x, end_y, false));
|
||||||
landList[startLandObjectIndex].forceUpdateLandInfo();
|
m_landList[startLandObjectIndex].forceUpdateLandInfo();
|
||||||
|
}
|
||||||
|
|
||||||
SetPrimsTainted();
|
SetPrimsTainted();
|
||||||
|
|
||||||
|
@ -746,13 +821,16 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
lock (m_landList)
|
||||||
|
{
|
||||||
foreach (ILandObject slaveLandObject in selectedLandObjects)
|
foreach (ILandObject slaveLandObject in selectedLandObjects)
|
||||||
{
|
{
|
||||||
landList[masterLandObject.landData.LocalID].setLandBitmap(
|
m_landList[masterLandObject.landData.LocalID].setLandBitmap(
|
||||||
slaveLandObject.mergeLandBitmaps(masterLandObject.getLandBitmap(), slaveLandObject.getLandBitmap()));
|
slaveLandObject.mergeLandBitmaps(masterLandObject.getLandBitmap(), slaveLandObject.getLandBitmap()));
|
||||||
performFinalLandJoin(masterLandObject, slaveLandObject);
|
performFinalLandJoin(masterLandObject, slaveLandObject);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
SetPrimsTainted();
|
SetPrimsTainted();
|
||||||
|
|
||||||
masterLandObject.sendLandUpdateToAvatarsOverMe();
|
masterLandObject.sendLandUpdateToAvatarsOverMe();
|
||||||
|
@ -892,10 +970,13 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
|
|
||||||
public void handleParcelPropertiesUpdateRequest(LandUpdateArgs args, int localID, IClientAPI remote_client)
|
public void handleParcelPropertiesUpdateRequest(LandUpdateArgs args, int localID, IClientAPI remote_client)
|
||||||
{
|
{
|
||||||
if (landList.ContainsKey(localID))
|
ILandObject land;
|
||||||
|
lock (m_landList)
|
||||||
{
|
{
|
||||||
landList[localID].updateLandProperties(args, remote_client);
|
m_landList.TryGetValue(localID, out land);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (land != null) land.updateLandProperties(args, remote_client);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void handleParcelDivideRequest(int west, int south, int east, int north, IClientAPI remote_client)
|
public void handleParcelDivideRequest(int west, int south, int east, int north, IClientAPI remote_client)
|
||||||
|
@ -910,67 +991,88 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
|
|
||||||
public void handleParcelSelectObjectsRequest(int local_id, int request_type, IClientAPI remote_client)
|
public void handleParcelSelectObjectsRequest(int local_id, int request_type, IClientAPI remote_client)
|
||||||
{
|
{
|
||||||
landList[local_id].sendForceObjectSelect(local_id, request_type, remote_client);
|
m_landList[local_id].sendForceObjectSelect(local_id, request_type, remote_client);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void handleParcelObjectOwnersRequest(int local_id, IClientAPI remote_client)
|
public void handleParcelObjectOwnersRequest(int local_id, IClientAPI remote_client)
|
||||||
{
|
{
|
||||||
lock (landList)
|
ILandObject land;
|
||||||
|
lock (m_landList)
|
||||||
{
|
{
|
||||||
if (landList.ContainsKey(local_id))
|
m_landList.TryGetValue(local_id, out land);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (land != null)
|
||||||
{
|
{
|
||||||
landList[local_id].sendLandObjectOwners(remote_client);
|
m_landList[local_id].sendLandObjectOwners(remote_client);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
System.Console.WriteLine("[PARCEL]: Invalid land object passed for parcel object owner request");
|
m_log.WarnFormat("[PARCEL]: Invalid land object {0} passed for parcel object owner request", local_id);
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void handleParcelGodForceOwner(int local_id, UUID ownerID, IClientAPI remote_client)
|
public void handleParcelGodForceOwner(int local_id, UUID ownerID, IClientAPI remote_client)
|
||||||
{
|
{
|
||||||
if (landList.ContainsKey(local_id))
|
ILandObject land;
|
||||||
|
lock (m_landList)
|
||||||
|
{
|
||||||
|
m_landList.TryGetValue(local_id, out land);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (land != null)
|
||||||
{
|
{
|
||||||
if (m_scene.ExternalChecks.ExternalChecksCanBeGodLike(remote_client.AgentId))
|
if (m_scene.ExternalChecks.ExternalChecksCanBeGodLike(remote_client.AgentId))
|
||||||
{
|
{
|
||||||
landList[local_id].landData.OwnerID = ownerID;
|
land.landData.OwnerID = ownerID;
|
||||||
|
|
||||||
m_scene.Broadcast(SendParcelOverlay);
|
m_scene.Broadcast(SendParcelOverlay);
|
||||||
landList[local_id].sendLandUpdateToClient(remote_client);
|
land.sendLandUpdateToClient(remote_client);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void handleParcelAbandonRequest(int local_id, IClientAPI remote_client)
|
public void handleParcelAbandonRequest(int local_id, IClientAPI remote_client)
|
||||||
{
|
{
|
||||||
if (landList.ContainsKey(local_id))
|
ILandObject land;
|
||||||
|
lock (m_landList)
|
||||||
{
|
{
|
||||||
if (m_scene.ExternalChecks.ExternalChecksCanAbandonParcel(remote_client.AgentId, landList[local_id]))
|
m_landList.TryGetValue(local_id, out land);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (land != null)
|
||||||
|
{
|
||||||
|
if (m_scene.ExternalChecks.ExternalChecksCanAbandonParcel(remote_client.AgentId, land))
|
||||||
{
|
{
|
||||||
if (m_scene.RegionInfo.EstateSettings.EstateOwner != UUID.Zero)
|
if (m_scene.RegionInfo.EstateSettings.EstateOwner != UUID.Zero)
|
||||||
landList[local_id].landData.OwnerID = m_scene.RegionInfo.EstateSettings.EstateOwner;
|
land.landData.OwnerID = m_scene.RegionInfo.EstateSettings.EstateOwner;
|
||||||
else
|
else
|
||||||
landList[local_id].landData.OwnerID = m_scene.RegionInfo.MasterAvatarAssignedUUID;
|
land.landData.OwnerID = m_scene.RegionInfo.MasterAvatarAssignedUUID;
|
||||||
m_scene.Broadcast(SendParcelOverlay);
|
m_scene.Broadcast(SendParcelOverlay);
|
||||||
landList[local_id].sendLandUpdateToClient(remote_client);
|
land.sendLandUpdateToClient(remote_client);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void handleParcelReclaim(int local_id, IClientAPI remote_client)
|
public void handleParcelReclaim(int local_id, IClientAPI remote_client)
|
||||||
{
|
{
|
||||||
if (landList.ContainsKey(local_id))
|
ILandObject land;
|
||||||
|
lock (m_landList)
|
||||||
{
|
{
|
||||||
if (m_scene.ExternalChecks.ExternalChecksCanReclaimParcel(remote_client.AgentId, landList[local_id]))
|
m_landList.TryGetValue(local_id, out land);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (land != null)
|
||||||
|
{
|
||||||
|
if (m_scene.ExternalChecks.ExternalChecksCanReclaimParcel(remote_client.AgentId, land))
|
||||||
{
|
{
|
||||||
if (m_scene.RegionInfo.EstateSettings.EstateOwner != UUID.Zero)
|
if (m_scene.RegionInfo.EstateSettings.EstateOwner != UUID.Zero)
|
||||||
landList[local_id].landData.OwnerID = m_scene.RegionInfo.EstateSettings.EstateOwner;
|
land.landData.OwnerID = m_scene.RegionInfo.EstateSettings.EstateOwner;
|
||||||
else
|
else
|
||||||
landList[local_id].landData.OwnerID = m_scene.RegionInfo.MasterAvatarAssignedUUID;
|
land.landData.OwnerID = m_scene.RegionInfo.MasterAvatarAssignedUUID;
|
||||||
landList[local_id].landData.ClaimDate = Util.UnixTimeSinceEpoch();
|
land.landData.ClaimDate = Util.UnixTimeSinceEpoch();
|
||||||
m_scene.Broadcast(SendParcelOverlay);
|
m_scene.Broadcast(SendParcelOverlay);
|
||||||
landList[local_id].sendLandUpdateToClient(remote_client);
|
land.sendLandUpdateToClient(remote_client);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -984,13 +1086,15 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
{
|
{
|
||||||
if (e.economyValidated && e.landValidated)
|
if (e.economyValidated && e.landValidated)
|
||||||
{
|
{
|
||||||
lock (landList)
|
ILandObject land;
|
||||||
|
lock (m_landList)
|
||||||
{
|
{
|
||||||
if (landList.ContainsKey(e.parcelLocalID))
|
m_landList.TryGetValue(e.parcelLocalID, out land);
|
||||||
{
|
|
||||||
landList[e.parcelLocalID].updateLandSold(e.agentId, e.groupId, e.groupOwned, (uint)e.transactionID, e.parcelPrice, e.parcelArea);
|
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (land != null)
|
||||||
|
{
|
||||||
|
land.updateLandSold(e.agentId, e.groupId, e.groupOwned, (uint)e.transactionID, e.parcelPrice, e.parcelArea);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1004,13 +1108,11 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
if (e.landValidated == false)
|
if (e.landValidated == false)
|
||||||
{
|
{
|
||||||
ILandObject lob = null;
|
ILandObject lob = null;
|
||||||
lock (landList)
|
lock (m_landList)
|
||||||
{
|
{
|
||||||
if (landList.ContainsKey(e.parcelLocalID))
|
m_landList.TryGetValue(e.parcelLocalID, out lob);
|
||||||
{
|
|
||||||
lob = landList[e.parcelLocalID];
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (lob != null)
|
if (lob != null)
|
||||||
{
|
{
|
||||||
UUID AuthorizedID = lob.landData.AuthBuyerID;
|
UUID AuthorizedID = lob.landData.AuthBuyerID;
|
||||||
|
@ -1021,11 +1123,12 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
(uint)(Parcel.ParcelFlags.ForSale | Parcel.ParcelFlags.ForSaleObjects | Parcel.ParcelFlags.SellParcelObjects)) != 0);
|
(uint)(Parcel.ParcelFlags.ForSale | Parcel.ParcelFlags.ForSaleObjects | Parcel.ParcelFlags.SellParcelObjects)) != 0);
|
||||||
if ((AuthorizedID == UUID.Zero || AuthorizedID == e.agentId) && e.parcelPrice >= saleprice && landforsale)
|
if ((AuthorizedID == UUID.Zero || AuthorizedID == e.agentId) && e.parcelPrice >= saleprice && landforsale)
|
||||||
{
|
{
|
||||||
lock (e)
|
// TODO I don't think we have to lock it here, no?
|
||||||
{
|
//lock (e)
|
||||||
|
//{
|
||||||
e.parcelOwnerID = pOwnerID;
|
e.parcelOwnerID = pOwnerID;
|
||||||
e.landValidated = true;
|
e.landValidated = true;
|
||||||
}
|
//}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1037,20 +1140,8 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
{
|
{
|
||||||
for (int i = 0; i < data.Count; i++)
|
for (int i = 0; i < data.Count; i++)
|
||||||
{
|
{
|
||||||
//try
|
|
||||||
//{
|
|
||||||
IncomingLandObjectFromStorage(data[i]);
|
IncomingLandObjectFromStorage(data[i]);
|
||||||
//}
|
|
||||||
//catch (Exception ex)
|
|
||||||
//{
|
|
||||||
//m_log.Error("[LandManager]: IncomingLandObjectsFromStorage: Exception: " + ex.ToString());
|
|
||||||
//throw ex;
|
|
||||||
//}
|
|
||||||
}
|
}
|
||||||
//foreach (LandData parcel in data)
|
|
||||||
//{
|
|
||||||
// IncomingLandObjectFromStorage(parcel);
|
|
||||||
//}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void IncomingLandObjectFromStorage(LandData data)
|
public void IncomingLandObjectFromStorage(LandData data)
|
||||||
|
@ -1064,13 +1155,12 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
public void ReturnObjectsInParcel(int localID, uint returnType, UUID[] agentIDs, UUID[] taskIDs, IClientAPI remoteClient)
|
public void ReturnObjectsInParcel(int localID, uint returnType, UUID[] agentIDs, UUID[] taskIDs, IClientAPI remoteClient)
|
||||||
{
|
{
|
||||||
ILandObject selectedParcel = null;
|
ILandObject selectedParcel = null;
|
||||||
lock (landList)
|
lock (m_landList)
|
||||||
{
|
{
|
||||||
if (landList.ContainsKey(localID))
|
m_landList.TryGetValue(localID, out selectedParcel);
|
||||||
selectedParcel = landList[localID];
|
|
||||||
}
|
}
|
||||||
if (selectedParcel == null)
|
|
||||||
return;
|
if (selectedParcel == null) return;
|
||||||
|
|
||||||
if (returnType == 16) // parcel return
|
if (returnType == 16) // parcel return
|
||||||
{
|
{
|
||||||
|
@ -1087,11 +1177,14 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
|
|
||||||
public void setParcelObjectMaxOverride(overrideParcelMaxPrimCountDelegate overrideDel)
|
public void setParcelObjectMaxOverride(overrideParcelMaxPrimCountDelegate overrideDel)
|
||||||
{
|
{
|
||||||
foreach (LandObject obj in landList.Values)
|
lock (m_landList)
|
||||||
|
{
|
||||||
|
foreach (LandObject obj in m_landList.Values)
|
||||||
{
|
{
|
||||||
obj.setParcelObjectMaxOverride(overrideDel);
|
obj.setParcelObjectMaxOverride(overrideDel);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public void setSimulatorObjectMaxOverride(overrideSimulatorMaxPrimCountDelegate overrideDel)
|
public void setSimulatorObjectMaxOverride(overrideSimulatorMaxPrimCountDelegate overrideDel)
|
||||||
{
|
{
|
||||||
|
@ -1236,17 +1329,20 @@ namespace OpenSim.Region.Environment.Modules.World.Land
|
||||||
|
|
||||||
public void setParcelOtherCleanTime(IClientAPI remoteClient, int localID, int otherCleanTime)
|
public void setParcelOtherCleanTime(IClientAPI remoteClient, int localID, int otherCleanTime)
|
||||||
{
|
{
|
||||||
if (!landList.ContainsKey(localID))
|
ILandObject land;
|
||||||
|
lock (m_landList)
|
||||||
|
{
|
||||||
|
m_landList.TryGetValue(localID, out land);
|
||||||
|
}
|
||||||
|
|
||||||
|
if(land == null) return;
|
||||||
|
|
||||||
|
if (!m_scene.ExternalChecks.ExternalChecksCanEditParcel(remoteClient.AgentId, land))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
ILandObject landObject = landList[localID];
|
land.landData.OtherCleanTime = otherCleanTime;
|
||||||
|
|
||||||
if (!m_scene.ExternalChecks.ExternalChecksCanEditParcel(remoteClient.AgentId, landObject))
|
UpdateLandObject(localID, land.landData);
|
||||||
return;
|
|
||||||
|
|
||||||
landObject.landData.OtherCleanTime = otherCleanTime;
|
|
||||||
|
|
||||||
UpdateLandObject(localID, landObject.landData);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue