summaryrefslogtreecommitdiff
path: root/indra/newview/llworld.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'indra/newview/llworld.cpp')
-rwxr-xr-x[-rw-r--r--]indra/newview/llworld.cpp497
1 files changed, 298 insertions, 199 deletions
diff --git a/indra/newview/llworld.cpp b/indra/newview/llworld.cpp
index 5c6fc2cf21..5d657f7eef 100644..100755
--- a/indra/newview/llworld.cpp
+++ b/indra/newview/llworld.cpp
@@ -2,31 +2,25 @@
* @file llworld.cpp
* @brief Initial test structure to organize viewer regions
*
- * $LicenseInfo:firstyear=2001&license=viewergpl$
- *
- * Copyright (c) 2001-2009, Linden Research, Inc.
- *
+ * $LicenseInfo:firstyear=2001&license=viewerlgpl$
* Second Life Viewer Source Code
- * The source code in this file ("Source Code") is provided by Linden Lab
- * to you under the terms of the GNU General Public License, version 2.0
- * ("GPL"), unless you have obtained a separate licensing agreement
- * ("Other License"), formally executed by you and Linden Lab. Terms of
- * the GPL can be found in doc/GPL-license.txt in this distribution, or
- * online at http://secondlifegrid.net/programs/open_source/licensing/gplv2
+ * Copyright (C) 2010, Linden Research, Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation;
+ * version 2.1 of the License only.
*
- * There are special exceptions to the terms and conditions of the GPL as
- * it is applied to this Source Code. View the full text of the exception
- * in the file doc/FLOSS-exception.txt in this software distribution, or
- * online at
- * http://secondlifegrid.net/programs/open_source/licensing/flossexception
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
*
- * By copying, modifying or distributing this software, you acknowledge
- * that you have read and understood your obligations described above,
- * and agree to abide by those obligations.
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
- * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
- * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
- * COMPLETENESS OR PERFORMANCE.
+ * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
* $/LicenseInfo$
*/
@@ -45,6 +39,7 @@
#include "llhttpnode.h"
#include "llregionhandle.h"
#include "llsurface.h"
+#include "lltrans.h"
#include "llviewercamera.h"
#include "llviewertexture.h"
#include "llviewertexturelist.h"
@@ -55,10 +50,17 @@
#include "llviewerstats.h"
#include "llvlcomposition.h"
#include "llvoavatar.h"
+#include "llvocache.h"
#include "llvowater.h"
#include "message.h"
#include "pipeline.h"
#include "llappviewer.h" // for do_disconnect()
+#include "llscenemonitor.h"
+#include <deque>
+#include <queue>
+#include <map>
+#include <cstring>
+
//
// Globals
@@ -68,7 +70,6 @@ U32 gAgentPauseSerialNum = 0;
//
// Constants
//
-const S32 MAX_NUMBER_OF_CLOUDS = 750;
const S32 WORLD_PATCH_SIZE = 16;
extern LLColor4U MAX_WATER_COLOR;
@@ -97,11 +98,6 @@ LLWorld::LLWorld() :
mEdgeWaterObjects[i] = NULL;
}
- if (gNoRender)
- {
- return;
- }
-
LLPointer<LLImageRaw> raw = new LLImageRaw(1,1,4);
U8 *default_texture = raw->getData();
*(default_texture++) = MAX_WATER_COLOR.mV[0];
@@ -113,26 +109,40 @@ LLWorld::LLWorld() :
gGL.getTexUnit(0)->bind(mDefaultWaterTexturep);
mDefaultWaterTexturep->setAddressMode(LLTexUnit::TAM_CLAMP);
+ LLViewerRegion::sVOCacheCullingEnabled = gSavedSettings.getBOOL("RequestFullRegionCache") && gSavedSettings.getBOOL("ObjectCacheEnabled");
}
void LLWorld::destroyClass()
{
+ mHoleWaterObjects.clear();
gObjectList.destroy();
for(region_list_t::iterator region_it = mRegionList.begin(); region_it != mRegionList.end(); )
{
LLViewerRegion* region_to_delete = *region_it++;
removeRegion(region_to_delete->getHost());
}
+
LLViewerPartSim::getInstance()->destroyClass();
+
+ mDefaultWaterTexturep = NULL ;
+ for (S32 i = 0; i < 8; i++)
+ {
+ mEdgeWaterObjects[i] = NULL;
+ }
+
+ //make all visible drawbles invisible.
+ LLDrawable::incrementVisible();
+
+ LLSceneMonitor::deleteSingleton();
}
LLViewerRegion* LLWorld::addRegion(const U64 &region_handle, const LLHost &host)
{
- LLMemType mt(LLMemType::MTYPE_REGIONS);
-
+ LL_INFOS() << "Add region with handle: " << region_handle << " on host " << host << LL_ENDL;
LLViewerRegion *regionp = getRegionFromHandle(region_handle);
+ std::string seedUrl;
if (regionp)
{
LLHost old_host = regionp->getHost();
@@ -140,31 +150,40 @@ LLViewerRegion* LLWorld::addRegion(const U64 &region_handle, const LLHost &host)
if (host == old_host && regionp->isAlive())
{
// This is a duplicate for the same host and it's alive, don't bother.
+ LL_INFOS() << "Region already exists and is alive, using existing region" << LL_ENDL;
return regionp;
}
if (host != old_host)
{
- llwarns << "LLWorld::addRegion exists, but old host " << old_host
- << " does not match new host " << host << llendl;
+ LL_WARNS() << "LLWorld::addRegion exists, but old host " << old_host
+ << " does not match new host " << host
+ << ", removing old region and creating new" << LL_ENDL;
}
if (!regionp->isAlive())
{
- llwarns << "LLWorld::addRegion exists, but isn't alive" << llendl;
+ LL_WARNS() << "LLWorld::addRegion exists, but isn't alive. Removing old region and creating new" << LL_ENDL;
}
+ // Save capabilities seed URL
+ seedUrl = regionp->getCapability("Seed");
+
// Kill the old host, and then we can continue on and add the new host. We have to kill even if the host
// matches, because all the agent state for the new camera is completely different.
removeRegion(old_host);
}
+ else
+ {
+ LL_INFOS() << "Region does not exist, creating new one" << LL_ENDL;
+ }
U32 iindex = 0;
U32 jindex = 0;
from_region_handle(region_handle, &iindex, &jindex);
S32 x = (S32)(iindex/mWidth);
S32 y = (S32)(jindex/mWidth);
- llinfos << "Adding new region (" << x << ":" << y << ")" << llendl;
- llinfos << "Host: " << host << llendl;
+ LL_INFOS() << "Adding new region (" << x << ":" << y << ")"
+ << " on host: " << host << LL_ENDL;
LLVector3d origin_global;
@@ -177,12 +196,13 @@ LLViewerRegion* LLWorld::addRegion(const U64 &region_handle, const LLHost &host)
getRegionWidthInMeters() );
if (!regionp)
{
- llerrs << "Unable to create new region!" << llendl;
+ LL_ERRS() << "Unable to create new region!" << LL_ENDL;
}
- regionp->mCloudLayer.create(regionp);
- regionp->mCloudLayer.setWidth((F32)mWidth);
- regionp->mCloudLayer.setWindPointer(&regionp->mWind);
+ if ( !seedUrl.empty() )
+ {
+ regionp->setCapability("Seed", seedUrl);
+ }
mRegionList.push_back(regionp);
mActiveRegionList.push_back(regionp);
@@ -214,7 +234,7 @@ LLViewerRegion* LLWorld::addRegion(const U64 &region_handle, const LLHost &host)
neighborp = getRegionFromHandle(adj_handle);
if (neighborp)
{
- //llinfos << "Connecting " << region_x << ":" << region_y << " -> " << adj_x << ":" << adj_y << llendl;
+ //LL_INFOS() << "Connecting " << region_x << ":" << region_y << " -> " << adj_x << ":" << adj_y << LL_ENDL;
regionp->connectNeighbor(neighborp, dir);
}
}
@@ -232,7 +252,7 @@ void LLWorld::removeRegion(const LLHost &host)
LLViewerRegion *regionp = getRegion(host);
if (!regionp)
{
- llwarns << "Trying to remove region that doesn't exist!" << llendl;
+ LL_WARNS() << "Trying to remove region that doesn't exist!" << LL_ENDL;
return;
}
@@ -242,36 +262,44 @@ void LLWorld::removeRegion(const LLHost &host)
iter != mRegionList.end(); ++iter)
{
LLViewerRegion* reg = *iter;
- llwarns << "RegionDump: " << reg->getName()
+ LL_WARNS() << "RegionDump: " << reg->getName()
<< " " << reg->getHost()
<< " " << reg->getOriginGlobal()
- << llendl;
+ << LL_ENDL;
}
- llwarns << "Agent position global " << gAgent.getPositionGlobal()
+ LL_WARNS() << "Agent position global " << gAgent.getPositionGlobal()
<< " agent " << gAgent.getPositionAgent()
- << llendl;
+ << LL_ENDL;
- llwarns << "Regions visited " << gAgent.getRegionsVisited() << llendl;
+ LL_WARNS() << "Regions visited " << gAgent.getRegionsVisited() << LL_ENDL;
- llwarns << "gFrameTimeSeconds " << gFrameTimeSeconds << llendl;
+ LL_WARNS() << "gFrameTimeSeconds " << gFrameTimeSeconds << LL_ENDL;
- llwarns << "Disabling region " << regionp->getName() << " that agent is in!" << llendl;
- LLAppViewer::instance()->forceDisconnect("You have been disconnected from the region you were in.");
+ LL_WARNS() << "Disabling region " << regionp->getName() << " that agent is in!" << LL_ENDL;
+ LLAppViewer::instance()->forceDisconnect(LLTrans::getString("YouHaveBeenDisconnected"));
+
+ regionp->saveObjectCache() ; //force to save objects here in case that the object cache is about to be destroyed.
return;
}
from_region_handle(regionp->getHandle(), &x, &y);
- llinfos << "Removing region " << x << ":" << y << llendl;
+ LL_INFOS() << "Removing region " << x << ":" << y << LL_ENDL;
mRegionList.remove(regionp);
mActiveRegionList.remove(regionp);
mCulledRegionList.remove(regionp);
mVisibleRegionList.remove(regionp);
-
+
+ mRegionRemovedSignal(regionp);
+
delete regionp;
updateWaterObjects();
+
+ //double check all objects of this region are removed.
+ gObjectList.clearAllMapObjectsInRegion(regionp) ;
+ //llassert_always(!gObjectList.hasMapObjectInRegion(regionp)) ;
}
@@ -392,6 +420,19 @@ LLViewerRegion* LLWorld::getRegionFromHandle(const U64 &handle)
return NULL;
}
+LLViewerRegion* LLWorld::getRegionFromID(const LLUUID& region_id)
+{
+ for (region_list_t::iterator iter = mRegionList.begin();
+ iter != mRegionList.end(); ++iter)
+ {
+ LLViewerRegion* regionp = *iter;
+ if (regionp->getRegionID() == region_id)
+ {
+ return regionp;
+ }
+ }
+ return NULL;
+}
void LLWorld::updateAgentOffset(const LLVector3d &offset_global)
{
@@ -422,14 +463,15 @@ BOOL LLWorld::positionRegionValidGlobal(const LLVector3d &pos_global)
// Allow objects to go up to their radius underground.
-F32 LLWorld::getMinAllowedZ(LLViewerObject* object)
+F32 LLWorld::getMinAllowedZ(LLViewerObject* object, const LLVector3d &global_pos)
{
- F32 land_height = resolveLandHeightGlobal(object->getPositionGlobal());
+ F32 land_height = resolveLandHeightGlobal(global_pos);
F32 radius = 0.5f * object->getScale().length();
return land_height - radius;
}
+
LLViewerRegion* LLWorld::resolveRegionGlobal(LLVector3 &pos_region, const LLVector3d &pos_global)
{
LLViewerRegion *regionp = getRegionFromPosGlobal(pos_global);
@@ -577,22 +619,23 @@ void LLWorld::updateVisibilities()
{
F32 cur_far_clip = LLViewerCamera::getInstance()->getFar();
- LLViewerCamera::getInstance()->setFar(mLandFarClip);
-
- F32 diagonal_squared = F_SQRT2 * F_SQRT2 * mWidth * mWidth;
- // Go through the culled list and check for visible regions
+ // Go through the culled list and check for visible regions (region is visible if land is visible)
for (region_list_t::iterator iter = mCulledRegionList.begin();
iter != mCulledRegionList.end(); )
{
region_list_t::iterator curiter = iter++;
LLViewerRegion* regionp = *curiter;
- F32 height = regionp->getLand().getMaxZ() - regionp->getLand().getMinZ();
- F32 radius = 0.5f*fsqrtf(height * height + diagonal_squared);
- if (!regionp->getLand().hasZData()
- || LLViewerCamera::getInstance()->sphereInFrustum(regionp->getCenterAgent(), radius))
+
+ LLSpatialPartition* part = regionp->getSpatialPartition(LLViewerRegion::PARTITION_TERRAIN);
+ if (part)
{
- mCulledRegionList.erase(curiter);
- mVisibleRegionList.push_back(regionp);
+ LLSpatialGroup* group = (LLSpatialGroup*) part->mOctree->getListener(0);
+ const LLVector4a* bounds = group->getBounds();
+ if (LLViewerCamera::getInstance()->AABBInFrustum(bounds[0], bounds[1]))
+ {
+ mCulledRegionList.erase(curiter);
+ mVisibleRegionList.push_back(regionp);
+ }
}
}
@@ -607,20 +650,21 @@ void LLWorld::updateVisibilities()
continue;
}
- F32 height = regionp->getLand().getMaxZ() - regionp->getLand().getMinZ();
- F32 radius = 0.5f*fsqrtf(height * height + diagonal_squared);
- if (LLViewerCamera::getInstance()->sphereInFrustum(regionp->getCenterAgent(), radius))
+ LLSpatialPartition* part = regionp->getSpatialPartition(LLViewerRegion::PARTITION_TERRAIN);
+ if (part)
{
- regionp->calculateCameraDistance();
- if (!gNoRender)
+ LLSpatialGroup* group = (LLSpatialGroup*) part->mOctree->getListener(0);
+ const LLVector4a* bounds = group->getBounds();
+ if (LLViewerCamera::getInstance()->AABBInFrustum(bounds[0], bounds[1]))
{
+ regionp->calculateCameraDistance();
regionp->getLand().updatePatchVisibilities(gAgent);
}
- }
- else
- {
- mVisibleRegionList.erase(curiter);
- mCulledRegionList.push_back(regionp);
+ else
+ {
+ mVisibleRegionList.erase(curiter);
+ mCulledRegionList.push_back(regionp);
+ }
}
}
@@ -630,87 +674,82 @@ void LLWorld::updateVisibilities()
LLViewerCamera::getInstance()->setFar(cur_far_clip);
}
+static LLTrace::SampleStatHandle<> sNumActiveCachedObjects("numactivecachedobjects", "Number of objects loaded from cache");
+
void LLWorld::updateRegions(F32 max_update_time)
{
- LLMemType mt_ur(LLMemType::MTYPE_IDLE_UPDATE_REGIONS);
LLTimer update_timer;
- BOOL did_one = FALSE;
+ mNumOfActiveCachedObjects = 0;
- // Perform idle time updates for the regions (and associated surfaces)
- for (region_list_t::iterator iter = mRegionList.begin();
- iter != mRegionList.end(); ++iter)
+ if(LLViewerCamera::getInstance()->isChanged())
{
- LLViewerRegion* regionp = *iter;
- F32 max_time = max_update_time - update_timer.getElapsedTimeF32();
- if (did_one && max_time <= 0.f)
- break;
- max_time = llmin(max_time, max_update_time*.1f);
- did_one |= regionp->idleUpdate(max_update_time);
+ LLViewerRegion::sLastCameraUpdated = LLViewerOctreeEntryData::getCurrentFrame() + 1;
}
-}
-
-void LLWorld::updateParticles()
-{
- LLViewerPartSim::getInstance()->updateSimulation();
-}
-
-void LLWorld::updateClouds(const F32 dt)
-{
- if (gSavedSettings.getBOOL("FreezeTime") ||
- !gSavedSettings.getBOOL("SkyUseClassicClouds"))
+ LLViewerRegion::calcNewObjectCreationThrottle();
+ if(LLViewerRegion::isNewObjectCreationThrottleDisabled())
{
- // don't move clouds in snapshot mode
- return;
+ max_update_time = llmax(max_update_time, 1.0f); //seconds, loosen the time throttle.
+ }
+
+ F32 max_time = llmin((F32)(max_update_time - update_timer.getElapsedTimeF32()), max_update_time * 0.25f);
+ //update the self avatar region
+ LLViewerRegion* self_regionp = gAgent.getRegion();
+ if(self_regionp)
+ {
+ self_regionp->idleUpdate(max_time);
}
- if (mActiveRegionList.size())
+
+ //sort regions by its mLastUpdate
+ //smaller mLastUpdate first to make sure every region has chance to get updated.
+ LLViewerRegion::region_priority_list_t region_list;
+ for (region_list_t::iterator iter = mRegionList.begin();
+ iter != mRegionList.end(); ++iter)
{
- // Update all the cloud puff positions, and timer based stuff
- // such as death decay
- for (region_list_t::iterator iter = mActiveRegionList.begin();
- iter != mActiveRegionList.end(); ++iter)
+ LLViewerRegion* regionp = *iter;
+ if(regionp != self_regionp)
{
- LLViewerRegion* regionp = *iter;
- regionp->mCloudLayer.updatePuffs(dt);
+ region_list.insert(regionp);
}
+ mNumOfActiveCachedObjects += regionp->getNumOfActiveCachedObjects();
+ }
- // Reshuffle who owns which puffs
- for (region_list_t::iterator iter = mActiveRegionList.begin();
- iter != mActiveRegionList.end(); ++iter)
+ // Perform idle time updates for the regions (and associated surfaces)
+ for (LLViewerRegion::region_priority_list_t::iterator iter = region_list.begin();
+ iter != region_list.end(); ++iter)
+ {
+ if(max_time > 0.f)
{
- LLViewerRegion* regionp = *iter;
- regionp->mCloudLayer.updatePuffOwnership();
+ max_time = llmin((F32)(max_update_time - update_timer.getElapsedTimeF32()), max_update_time * 0.25f);
}
- // Add new puffs
- for (region_list_t::iterator iter = mActiveRegionList.begin();
- iter != mActiveRegionList.end(); ++iter)
+ if(max_time > 0.f)
{
- LLViewerRegion* regionp = *iter;
- regionp->mCloudLayer.updatePuffCount();
+ (*iter)->idleUpdate(max_time);
}
+ else
+ {
+ //perform some necessary but very light updates.
+ (*iter)->lightIdleUpdate();
+ }
}
-}
-LLCloudGroup* LLWorld::findCloudGroup(const LLCloudPuff &puff)
+ sample(sNumActiveCachedObjects, mNumOfActiveCachedObjects);
+ }
+
+void LLWorld::clearAllVisibleObjects()
{
- if (mActiveRegionList.size())
+ for (region_list_t::iterator iter = mRegionList.begin();
+ iter != mRegionList.end(); ++iter)
{
- // Update all the cloud puff positions, and timer based stuff
- // such as death decay
- for (region_list_t::iterator iter = mActiveRegionList.begin();
- iter != mActiveRegionList.end(); ++iter)
- {
- LLViewerRegion* regionp = *iter;
- LLCloudGroup *groupp = regionp->mCloudLayer.findCloudGroup(puff);
- if (groupp)
- {
- return groupp;
- }
- }
+ //clear all cached visible objects.
+ (*iter)->clearCachedVisibleObjects();
}
- return NULL;
}
+void LLWorld::updateParticles()
+{
+ LLViewerPartSim::getInstance()->updateSimulation();
+}
void LLWorld::renderPropertyLines()
{
@@ -729,7 +768,7 @@ void LLWorld::renderPropertyLines()
void LLWorld::updateNetStats()
{
- F32 bits = 0.f;
+ F64Bits bits;
U32 packets = 0;
for (region_list_t::iterator iter = mActiveRegionList.begin();
@@ -737,29 +776,31 @@ void LLWorld::updateNetStats()
{
LLViewerRegion* regionp = *iter;
regionp->updateNetStats();
- bits += regionp->mBitStat.getCurrent();
- packets += llfloor( regionp->mPacketsStat.getCurrent() );
+ bits += regionp->mBitsReceived;
+ packets += llfloor( regionp->mPacketsReceived );
+ regionp->mBitsReceived = (F32Bits)0.f;
+ regionp->mPacketsReceived = 0.f;
}
S32 packets_in = gMessageSystem->mPacketsIn - mLastPacketsIn;
S32 packets_out = gMessageSystem->mPacketsOut - mLastPacketsOut;
S32 packets_lost = gMessageSystem->mDroppedPackets - mLastPacketsLost;
- S32 actual_in_bits = gMessageSystem->mPacketRing.getAndResetActualInBits();
- S32 actual_out_bits = gMessageSystem->mPacketRing.getAndResetActualOutBits();
- LLViewerStats::getInstance()->mActualInKBitStat.addValue(actual_in_bits/1024.f);
- LLViewerStats::getInstance()->mActualOutKBitStat.addValue(actual_out_bits/1024.f);
- LLViewerStats::getInstance()->mKBitStat.addValue(bits/1024.f);
- LLViewerStats::getInstance()->mPacketsInStat.addValue(packets_in);
- LLViewerStats::getInstance()->mPacketsOutStat.addValue(packets_out);
- LLViewerStats::getInstance()->mPacketsLostStat.addValue(gMessageSystem->mDroppedPackets);
- if (packets_in)
- {
- LLViewerStats::getInstance()->mPacketsLostPercentStat.addValue(100.f*((F32)packets_lost/(F32)packets_in));
- }
- else
+ F64Bits actual_in_bits(gMessageSystem->mPacketRing.getAndResetActualInBits());
+ F64Bits actual_out_bits(gMessageSystem->mPacketRing.getAndResetActualOutBits());
+
+ add(LLStatViewer::MESSAGE_SYSTEM_DATA_IN, actual_in_bits);
+ add(LLStatViewer::MESSAGE_SYSTEM_DATA_OUT, actual_out_bits);
+ add(LLStatViewer::ACTIVE_MESSAGE_DATA_RECEIVED, bits);
+ add(LLStatViewer::PACKETS_IN, packets_in);
+ add(LLStatViewer::PACKETS_OUT, packets_out);
+ add(LLStatViewer::PACKETS_LOST, packets_lost);
+
+ F32 total_packets_in = LLViewerStats::instance().getRecording().getSum(LLStatViewer::PACKETS_IN);
+ if (total_packets_in > 0)
{
- LLViewerStats::getInstance()->mPacketsLostPercentStat.addValue(0.f);
+ F32 total_packets_lost = LLViewerStats::instance().getRecording().getSum(LLStatViewer::PACKETS_LOST);
+ sample(LLStatViewer::PACKETS_LOST_PERCENT, LLUnits::Ratio::fromValue((F32)total_packets_lost/(F32)total_packets_in));
}
mLastPacketsIn = gMessageSystem->mPacketsIn;
@@ -770,8 +811,8 @@ void LLWorld::updateNetStats()
void LLWorld::printPacketsLost()
{
- llinfos << "Simulators:" << llendl;
- llinfos << "----------" << llendl;
+ LL_INFOS() << "Simulators:" << LL_ENDL;
+ LL_INFOS() << "----------" << LL_ENDL;
LLCircuitData *cdp = NULL;
for (region_list_t::iterator iter = mActiveRegionList.begin();
@@ -783,8 +824,8 @@ void LLWorld::printPacketsLost()
{
LLVector3d range = regionp->getCenterGlobal() - gAgent.getPositionGlobal();
- llinfos << regionp->getHost() << ", range: " << range.length()
- << " packets lost: " << cdp->getPacketsLost() << llendl;
+ LL_INFOS() << regionp->getHost() << ", range: " << range.length()
+ << " packets lost: " << cdp->getPacketsLost() << LL_ENDL;
}
}
}
@@ -805,9 +846,32 @@ F32 LLWorld::getLandFarClip() const
void LLWorld::setLandFarClip(const F32 far_clip)
{
+ static S32 const rwidth = (S32)REGION_WIDTH_U32;
+ S32 const n1 = (llceil(mLandFarClip) - 1) / rwidth;
+ S32 const n2 = (llceil(far_clip) - 1) / rwidth;
+ bool need_water_objects_update = n1 != n2;
+
mLandFarClip = far_clip;
+
+ if (need_water_objects_update)
+ {
+ updateWaterObjects();
+ }
}
+// Some region that we're connected to, but not the one we're in, gave us
+// a (possibly) new water height. Update it in our local copy.
+void LLWorld::waterHeightRegionInfo(std::string const& sim_name, F32 water_height)
+{
+ for (region_list_t::iterator iter = mRegionList.begin(); iter != mRegionList.end(); ++iter)
+ {
+ if ((*iter)->getName() == sim_name)
+ {
+ (*iter)->setWaterHeight(water_height);
+ break;
+ }
+ }
+}
void LLWorld::updateWaterObjects()
{
@@ -817,7 +881,7 @@ void LLWorld::updateWaterObjects()
}
if (mRegionList.empty())
{
- llwarns << "No regions!" << llendl;
+ LL_WARNS() << "No regions!" << LL_ENDL;
return;
}
@@ -841,14 +905,11 @@ void LLWorld::updateWaterObjects()
max_x = (S32)region_x + range;
max_y = (S32)region_y + range;
- F32 height = 0.f;
-
for (region_list_t::iterator iter = mRegionList.begin();
iter != mRegionList.end(); ++iter)
{
LLViewerRegion* regionp = *iter;
LLVOWater* waterp = regionp->getLand().getWaterObj();
- height += regionp->getWaterHeight();
if (waterp)
{
gObjectList.updateActive(waterp);
@@ -863,6 +924,9 @@ void LLWorld::updateWaterObjects()
}
mHoleWaterObjects.clear();
+ // Use the water height of the region we're on for areas where there is no region
+ F32 water_height = gAgent.getRegion()->getWaterHeight();
+
// Now, get a list of the holes
S32 x, y;
for (x = min_x; x <= max_x; x += rwidth)
@@ -871,12 +935,12 @@ void LLWorld::updateWaterObjects()
{
U64 region_handle = to_region_handle(x, y);
if (!getRegionFromHandle(region_handle))
- {
+ { // No region at that area, so make water
LLVOWater* waterp = (LLVOWater *)gObjectList.createObjectViewer(LLViewerObject::LL_VO_WATER, gAgent.getRegion());
waterp->setUseTexture(FALSE);
waterp->setPositionGlobal(LLVector3d(x + rwidth/2,
y + rwidth/2,
- 256.f+DEFAULT_WATER_HEIGHT));
+ 256.f + water_height));
waterp->setScale(LLVector3((F32)rwidth, (F32)rwidth, 512.f));
gPipeline.createObject(waterp);
mHoleWaterObjects.push_back(waterp);
@@ -916,15 +980,15 @@ void LLWorld::updateWaterObjects()
}
// Resize and reshape the water objects
- const S32 water_center_x = center_x + llround((wx + dim[0]) * 0.5f * gDirAxes[dir][0]);
- const S32 water_center_y = center_y + llround((wy + dim[1]) * 0.5f * gDirAxes[dir][1]);
+ const S32 water_center_x = center_x + ll_round((wx + dim[0]) * 0.5f * gDirAxes[dir][0]);
+ const S32 water_center_y = center_y + ll_round((wy + dim[1]) * 0.5f * gDirAxes[dir][1]);
LLVOWater* waterp = mEdgeWaterObjects[dir];
if (!waterp || waterp->isDead())
{
// The edge water objects can be dead because they're attached to the region that the
// agent was in when they were originally created.
- mEdgeWaterObjects[dir] = (LLVOWater *)gObjectList.createObjectViewer(LLViewerObject::LL_VO_WATER,
+ mEdgeWaterObjects[dir] = (LLVOWater *)gObjectList.createObjectViewer(LLViewerObject::LL_VO_VOID_WATER,
gAgent.getRegion());
waterp = mEdgeWaterObjects[dir];
waterp->setUseTexture(FALSE);
@@ -933,8 +997,7 @@ void LLWorld::updateWaterObjects()
}
waterp->setRegion(gAgent.getRegion());
- LLVector3d water_pos(water_center_x, water_center_y,
- DEFAULT_WATER_HEIGHT+256.f);
+ LLVector3d water_pos(water_center_x, water_center_y, 256.f + water_height) ;
LLVector3 water_scale((F32) dim[0], (F32) dim[1], 512.f);
//stretch out to horizon
@@ -951,6 +1014,7 @@ void LLWorld::updateWaterObjects()
}
}
+
void LLWorld::shiftRegions(const LLVector3& offset)
{
for (region_list_t::const_iterator i = getRegionList().begin(); i != getRegionList().end(); ++i)
@@ -967,12 +1031,12 @@ LLViewerTexture* LLWorld::getDefaultWaterTexture()
return mDefaultWaterTexturep;
}
-void LLWorld::setSpaceTimeUSec(const U64 space_time_usec)
+void LLWorld::setSpaceTimeUSec(const U64MicrosecondsImplicit space_time_usec)
{
mSpaceTimeUSec = space_time_usec;
}
-U64 LLWorld::getSpaceTimeUSec() const
+U64MicrosecondsImplicit LLWorld::getSpaceTimeUSec() const
{
return mSpaceTimeUSec;
}
@@ -1012,7 +1076,7 @@ void LLWorld::disconnectRegions()
continue;
}
- llinfos << "Sending AgentQuitCopy to: " << regionp->getHost() << llendl;
+ LL_INFOS() << "Sending AgentQuitCopy to: " << regionp->getHost() << LL_ENDL;
msg->newMessageFast(_PREHASH_AgentQuitCopy);
msg->nextBlockFast(_PREHASH_AgentData);
msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
@@ -1023,9 +1087,11 @@ void LLWorld::disconnectRegions()
}
}
+static LLTrace::BlockTimerStatHandle FTM_ENABLE_SIMULATOR("Enable Sim");
void process_enable_simulator(LLMessageSystem *msg, void **user_data)
{
+ LL_RECORD_BLOCK_TIME(FTM_ENABLE_SIMULATOR);
// enable the appropriate circuit for this simulator and
// add its values into the gSimulator structure
U64 handle;
@@ -1044,7 +1110,7 @@ void process_enable_simulator(LLMessageSystem *msg, void **user_data)
LLWorld::getInstance()->addRegion(handle, sim);
// give the simulator a message it can use to get ip and port
- llinfos << "simulator_enable() Enabling " << sim << " with code " << msg->getOurCircuitCode() << llendl;
+ LL_INFOS() << "simulator_enable() Enabling " << sim << " with code " << msg->getOurCircuitCode() << LL_ENDL;
msg->newMessageFast(_PREHASH_UseCircuitCode);
msg->nextBlockFast(_PREHASH_CircuitCode);
msg->addU32Fast(_PREHASH_Code, msg->getOurCircuitCode());
@@ -1072,7 +1138,7 @@ public:
!input["body"].has("sim-ip-and-port") ||
!input["body"].has("seed-capability"))
{
- llwarns << "invalid parameters" << llendl;
+ LL_WARNS() << "invalid parameters" << LL_ENDL;
return;
}
@@ -1081,10 +1147,12 @@ public:
LLViewerRegion* regionp = LLWorld::getInstance()->getRegion(sim);
if (!regionp)
{
- llwarns << "Got EstablishAgentCommunication for unknown region "
- << sim << llendl;
+ LL_WARNS() << "Got EstablishAgentCommunication for unknown region "
+ << sim << LL_ENDL;
return;
}
+ LL_DEBUGS("CrossingCaps") << "Calling setSeedCapability from LLEstablishAgentCommunication::post. Seed cap == "
+ << input["body"]["seed-capability"] << LL_ENDL;
regionp->setSeedCapability(input["body"]["seed-capability"]);
}
};
@@ -1095,7 +1163,7 @@ void process_disable_simulator(LLMessageSystem *mesgsys, void **user_data)
{
LLHost host = mesgsys->getSender();
- //llinfos << "Disabling simulator with message from " << host << llendl;
+ //LL_INFOS() << "Disabling simulator with message from " << host << LL_ENDL;
LLWorld::getInstance()->removeRegion(host);
mesgsys->disableCircuit(host);
@@ -1108,8 +1176,8 @@ void process_region_handshake(LLMessageSystem* msg, void** user_data)
LLViewerRegion* regionp = LLWorld::getInstance()->getRegion(host);
if (!regionp)
{
- llwarns << "Got region handshake for unknown region "
- << host << llendl;
+ LL_WARNS() << "Got region handshake for unknown region "
+ << host << LL_ENDL;
return;
}
@@ -1147,6 +1215,7 @@ void send_agent_pause()
}
gObjectList.mWasPaused = TRUE;
+ LLViewerStats::instance().getRecording().stop();
}
@@ -1176,36 +1245,27 @@ void send_agent_resume()
gMessageSystem->sendReliable(regionp->getHost());
}
- // Reset the FPS counter to avoid an invalid fps
- LLViewerStats::getInstance()->mFPSStat.start();
+ // Resume data collection to ignore invalid rates
+ LLViewerStats::instance().getRecording().resume();
LLAppViewer::instance()->resumeMainloopTimeout();
}
static LLVector3d unpackLocalToGlobalPosition(U32 compact_local, const LLVector3d& region_origin)
{
- LLVector3d pos_global;
- LLVector3 pos_local;
- U8 bits;
-
- bits = compact_local & 0xFF;
- pos_local.mV[VZ] = F32(bits) * 4.f;
- compact_local >>= 8;
+ LLVector3d pos_local;
- bits = compact_local & 0xFF;
- pos_local.mV[VY] = (F32)bits;
- compact_local >>= 8;
+ pos_local.mdV[VZ] = (compact_local & 0xFFU) * 4;
+ pos_local.mdV[VY] = (compact_local >> 8) & 0xFFU;
+ pos_local.mdV[VX] = (compact_local >> 16) & 0xFFU;
- bits = compact_local & 0xFF;
- pos_local.mV[VX] = (F32)bits;
-
- pos_global.setVec( pos_local );
- pos_global += region_origin;
- return pos_global;
+ return region_origin + pos_local;
}
-void LLWorld::getAvatars(std::vector<LLUUID>* avatar_ids, std::vector<LLVector3d>* positions, const LLVector3d& relative_to, F32 radius) const
+void LLWorld::getAvatars(uuid_vec_t* avatar_ids, std::vector<LLVector3d>* positions, const LLVector3d& relative_to, F32 radius) const
{
+ F32 radius_squared = radius * radius;
+
if(avatar_ids != NULL)
{
avatar_ids->clear();
@@ -1214,30 +1274,69 @@ void LLWorld::getAvatars(std::vector<LLUUID>* avatar_ids, std::vector<LLVector3d
{
positions->clear();
}
+ // get the list of avatars from the character list first, so distances are correct
+ // when agent is above 1020m and other avatars are nearby
+ for (std::vector<LLCharacter*>::iterator iter = LLCharacter::sInstances.begin();
+ iter != LLCharacter::sInstances.end(); ++iter)
+ {
+ LLVOAvatar* pVOAvatar = (LLVOAvatar*) *iter;
+
+ if (!pVOAvatar->isDead() && !pVOAvatar->mIsDummy)
+ {
+ LLVector3d pos_global = pVOAvatar->getPositionGlobal();
+ LLUUID uuid = pVOAvatar->getID();
+
+ if (!uuid.isNull()
+ && dist_vec_squared(pos_global, relative_to) <= radius_squared)
+ {
+ if(positions != NULL)
+ {
+ positions->push_back(pos_global);
+ }
+ if(avatar_ids !=NULL)
+ {
+ avatar_ids->push_back(uuid);
+ }
+ }
+ }
+ }
+ // region avatars added for situations where radius is greater than RenderFarClip
for (LLWorld::region_list_t::const_iterator iter = LLWorld::getInstance()->getRegionList().begin();
iter != LLWorld::getInstance()->getRegionList().end(); ++iter)
{
LLViewerRegion* regionp = *iter;
const LLVector3d& origin_global = regionp->getOriginGlobal();
- S32 count = regionp->mMapAvatars.count();
+ S32 count = regionp->mMapAvatars.size();
for (S32 i = 0; i < count; i++)
{
- LLVector3d pos_global = unpackLocalToGlobalPosition(regionp->mMapAvatars.get(i), origin_global);
- if(dist_vec(pos_global, relative_to) <= radius)
+ LLVector3d pos_global = unpackLocalToGlobalPosition(regionp->mMapAvatars.at(i), origin_global);
+ if(dist_vec_squared(pos_global, relative_to) <= radius_squared)
{
- if(positions != NULL)
+ LLUUID uuid = regionp->mMapAvatarIDs.at(i);
+ // if this avatar doesn't already exist in the list, add it
+ if(uuid.notNull() && avatar_ids != NULL && std::find(avatar_ids->begin(), avatar_ids->end(), uuid) == avatar_ids->end())
{
- positions->push_back(pos_global);
- }
- if(avatar_ids != NULL)
- {
- avatar_ids->push_back(regionp->mMapAvatarIDs.get(i));
+ if (positions != NULL)
+ {
+ positions->push_back(pos_global);
+ }
+ avatar_ids->push_back(uuid);
}
}
}
}
}
+bool LLWorld::isRegionListed(const LLViewerRegion* region) const
+{
+ region_list_t::const_iterator it = find(mRegionList.begin(), mRegionList.end(), region);
+ return it != mRegionList.end();
+}
+
+boost::signals2::connection LLWorld::setRegionRemovedCallback(const region_remove_signal_t::slot_type& cb)
+{
+ return mRegionRemovedSignal.connect(cb);
+}
LLHTTPRegistration<LLEstablishAgentCommunication>
gHTTPRegistrationEstablishAgentCommunication(