diff --git a/indra/llrender/llvertexbuffer.cpp b/indra/llrender/llvertexbuffer.cpp index 4d354a59b..bc4c201d9 100644 --- a/indra/llrender/llvertexbuffer.cpp +++ b/indra/llrender/llvertexbuffer.cpp @@ -39,10 +39,8 @@ #include "llmemory.h" #include "llfasttimer.h" -#if LL_DARWIN -#define LL_VBO_POOLING 1 -#else -#endif +#define LL_VBO_POOLING 0 + //Next Highest Power Of Two //helper function, returns first number > v that is a power of 2, or v if v is already a power of 2 U32 nhpo2(U32 v) @@ -70,7 +68,6 @@ U32 wpo2(U32 i) const U32 LL_VBO_BLOCK_SIZE = 2048; -const U32 LL_VBO_POOL_MAX_SEED_SIZE = 256*1024; U32 vbo_block_size(U32 size) { //what block size will fit size? @@ -83,7 +80,6 @@ U32 vbo_block_index(U32 size) return vbo_block_size(size)/LL_VBO_BLOCK_SIZE; } -const U32 LL_VBO_POOL_SEED_COUNT = vbo_block_index(LL_VBO_POOL_MAX_SEED_SIZE); //============================================================================ @@ -96,11 +92,6 @@ LLVBOPool LLVertexBuffer::sDynamicIBOPool(GL_DYNAMIC_DRAW_ARB, GL_ELEMENT_ARRAY_ U32 LLVBOPool::sBytesPooled = 0; U32 LLVBOPool::sIndexBytesPooled = 0; -U32 LLVBOPool::sCurGLName = 1; - -std::list LLVertexBuffer::sAvailableVAOName; -U32 LLVertexBuffer::sCurVAOName = 1; - U32 LLVertexBuffer::sAllocatedIndexBytes = 0; U32 LLVertexBuffer::sIndexCount = 0; @@ -126,54 +117,14 @@ bool LLVertexBuffer::sUseVAO = false; bool LLVertexBuffer::sPreferStreamDraw = false; -U32 LLVBOPool::genBuffer() -{ - U32 ret = 0; - - if (mGLNamePool.empty()) - { - ret = sCurGLName++; - } - else - { - ret = mGLNamePool.front(); - mGLNamePool.pop_front(); - } - - return ret; -} - -void LLVBOPool::deleteBuffer(U32 name) -{ - if (gGLManager.mInited) - { - LLVertexBuffer::unbind(); - - glBindBufferARB(mType, name); - glBufferDataARB(mType, 0, NULL, mUsage); - - llassert(std::find(mGLNamePool.begin(), mGLNamePool.end(), name) == mGLNamePool.end()); - - mGLNamePool.push_back(name); - - glBindBufferARB(mType, 0); - } -} - - -LLVBOPool::LLVBOPool(U32 vboUsage, U32 vboType) -: mUsage(vboUsage), mType(vboType) -{ - mMissCount.resize(LL_VBO_POOL_SEED_COUNT); - std::fill(mMissCount.begin(), mMissCount.end(), 0); -} - -volatile U8* LLVBOPool::allocate(U32& name, U32 size, bool for_seed) +volatile U8* LLVBOPool::allocate(U32& name, U32 size) { llassert(vbo_block_size(size) == size); volatile U8* ret = NULL; +#if LL_VBO_POOLING + U32 i = vbo_block_index(size); if (mFreeList.size() <= i) @@ -181,31 +132,25 @@ volatile U8* LLVBOPool::allocate(U32& name, U32 size, bool for_seed) mFreeList.resize(i+1); } - if (mFreeList[i].empty() || for_seed) + if (mFreeList[i].empty()) { //make a new buffer - name = genBuffer(); - + glGenBuffersARB(1, &name); glBindBufferARB(mType, name); - if (!for_seed && i < LL_VBO_POOL_SEED_COUNT) - { //record this miss - mMissCount[i]++; - } - if (mType == GL_ARRAY_BUFFER_ARB) { LLVertexBuffer::sAllocatedBytes += size; } else - { - LLVertexBuffer::sAllocatedIndexBytes += size; - } + { + LLVertexBuffer::sAllocatedIndexBytes += size; + } - if (LLVertexBuffer::sDisableVBOMapping || mUsage != GL_DYNAMIC_DRAW_ARB) - { - glBufferDataARB(mType, size, 0, mUsage); - ret = (U8*) ll_aligned_malloc_16(size); + if (LLVertexBuffer::sDisableVBOMapping || mUsage != GL_DYNAMIC_DRAW_ARB) + { + glBufferDataARB(mType, size, 0, mUsage); + ret = (U8*) ll_aligned_malloc_16(size); } else { //always use a true hint of static draw when allocating non-client-backed buffers @@ -213,25 +158,6 @@ volatile U8* LLVBOPool::allocate(U32& name, U32 size, bool for_seed) } glBindBufferARB(mType, 0); - - if (for_seed) - { //put into pool for future use - llassert(mFreeList.size() > i); - - Record rec; - rec.mGLName = name; - rec.mClientData = ret; - - if (mType == GL_ARRAY_BUFFER_ARB) - { - sBytesPooled += size; - } - else - { - sIndexBytesPooled += size; - } - mFreeList[i].push_back(rec); - } } else { @@ -249,6 +175,33 @@ volatile U8* LLVBOPool::allocate(U32& name, U32 size, bool for_seed) mFreeList[i].pop_front(); } +#else //no pooling + + glGenBuffersARB(1, &name); + glBindBufferARB(mType, name); + + if (mType == GL_ARRAY_BUFFER_ARB) + { + LLVertexBuffer::sAllocatedBytes += size; + } + else + { + LLVertexBuffer::sAllocatedIndexBytes += size; + } + + if (LLVertexBuffer::sDisableVBOMapping || mUsage != GL_DYNAMIC_DRAW_ARB) + { + glBufferDataARB(mType, size, 0, mUsage); + ret = (U8*) ll_aligned_malloc_16(size); + } + else + { //always use a true hint of static draw when allocating non-client-backed buffers + glBufferDataARB(mType, size, 0, GL_STATIC_DRAW_ARB); + } + + glBindBufferARB(mType, 0); + +#endif return ret; } @@ -257,7 +210,34 @@ void LLVBOPool::release(U32 name, volatile U8* buffer, U32 size) { llassert(vbo_block_size(size) == size); - deleteBuffer(name); +#if LL_VBO_POOLING + + U32 i = vbo_block_index(size); + + llassert(mFreeList.size() > i); + + Record rec; + rec.mGLName = name; + rec.mClientData = buffer; + + if (buffer == NULL) + { + glDeleteBuffersARB(1, &rec.mGLName); + } + else + { + if (mType == GL_ARRAY_BUFFER_ARB) + { + sBytesPooled += size; + } + else + { + sIndexBytesPooled += size; + } + mFreeList[i].push_back(rec); + } +#else //no pooling + glDeleteBuffersARB(1, &name); ll_aligned_free_16((U8*) buffer); if (mType == GL_ARRAY_BUFFER_ARB) @@ -268,36 +248,12 @@ void LLVBOPool::release(U32 name, volatile U8* buffer, U32 size) { LLVertexBuffer::sAllocatedIndexBytes -= size; } +#endif } -void LLVBOPool::seedPool() -{ - U32 dummy_name = 0; - - if (mFreeList.size() < LL_VBO_POOL_SEED_COUNT) - { - mFreeList.resize(LL_VBO_POOL_SEED_COUNT); - } - - for (U32 i = 0; i < LL_VBO_POOL_SEED_COUNT; i++) - { - if (mMissCount[i] > mFreeList[i].size()) - { - U32 size = i*LL_VBO_BLOCK_SIZE; - - S32 count = mMissCount[i] - mFreeList[i].size(); - for (S32 j = 0; j < count; ++j) - { - allocate(dummy_name, size, true); - } - } - } -} - - void LLVBOPool::cleanup() { - U32 size = LL_VBO_BLOCK_SIZE; + U32 size = 1; for (U32 i = 0; i < mFreeList.size(); ++i) { @@ -307,8 +263,8 @@ void LLVBOPool::cleanup() { Record& r = l.front(); - deleteBuffer(r.mGLName); - + glDeleteBuffersARB(1, &r.mGLName); + if (r.mClientData) { ll_aligned_free_16((void*) r.mClientData); @@ -328,11 +284,8 @@ void LLVBOPool::cleanup() } } - size += LL_VBO_BLOCK_SIZE; + size *= 2; } - - //reset miss counts - std::fill(mMissCount.begin(), mMissCount.end(), 0); } @@ -366,41 +319,6 @@ U32 LLVertexBuffer::sGLMode[LLRender::NUM_MODES] = GL_LINE_LOOP, }; -//static -U32 LLVertexBuffer::getVAOName() -{ - U32 ret = 0; - - if (!sAvailableVAOName.empty()) - { - ret = sAvailableVAOName.front(); - sAvailableVAOName.pop_front(); - } - else - { -#ifdef GL_ARB_vertex_array_object - glGenVertexArrays(1, &ret); -#endif - } - - return ret; -} - -//static -void LLVertexBuffer::releaseVAOName(U32 name) -{ - sAvailableVAOName.push_back(name); -} - - -//static -void LLVertexBuffer::seedPools() -{ - sStreamVBOPool.seedPool(); - sDynamicVBOPool.seedPool(); - sStreamIBOPool.seedPool(); - sDynamicIBOPool.seedPool(); -} //static void LLVertexBuffer::setupClientArrays(U32 data_mask) @@ -1010,7 +928,7 @@ LLVertexBuffer::~LLVertexBuffer() if (mGLArray) { #if GL_ARB_vertex_array_object - releaseVAOName(mGLArray); + glDeleteVertexArrays(1, &mGLArray); #endif } @@ -1295,7 +1213,7 @@ void LLVertexBuffer::allocateBuffer(S32 nverts, S32 nindices, bool create) if (gGLManager.mHasVertexArrayObject && useVBOs() && (LLRender::sGLCoreProfile || sUseVAO)) { #if GL_ARB_vertex_array_object - mGLArray = getVAOName(); + glGenVertexArrays(1, &mGLArray); #endif setupVertexArray(); } @@ -2165,16 +2083,6 @@ void LLVertexBuffer::flush() } } -// bind for transform feedback (quick 'n dirty) -void LLVertexBuffer::bindForFeedback(U32 channel, U32 type, U32 index, U32 count) -{ -#ifdef GL_TRANSFORM_FEEDBACK_BUFFER - U32 offset = mOffsets[type] + sTypeSize[type]*index; - U32 size= (sTypeSize[type]*count); - glBindBufferRange(GL_TRANSFORM_FEEDBACK_BUFFER, channel, mGLBuffer, offset, size); -#endif -} - // Set for rendering void LLVertexBuffer::setBuffer(U32 data_mask) { diff --git a/indra/llrender/llvertexbuffer.h b/indra/llrender/llvertexbuffer.h index 14438a95e..469acfcef 100644 --- a/indra/llrender/llvertexbuffer.h +++ b/indra/llrender/llvertexbuffer.h @@ -56,29 +56,24 @@ class LLVBOPool public: static U32 sBytesPooled; static U32 sIndexBytesPooled; - - static U32 sCurGLName; - LLVBOPool(U32 vboUsage, U32 vboType); - + LLVBOPool(U32 vboUsage, U32 vboType) + : mUsage(vboUsage) + , mType(vboType) + {} + const U32 mUsage; const U32 mType; //size MUST be a power of 2 - volatile U8* allocate(U32& name, U32 size, bool for_seed = false); + volatile U8* allocate(U32& name, U32 size); //size MUST be the size provided to allocate that returned the given name void release(U32 name, volatile U8* buffer, U32 size); - //batch allocate buffers to be provided to the application on demand - void seedPool(); - //destroy all records in mFreeList void cleanup(); - U32 genBuffer(); - void deleteBuffer(U32 name); - class Record { public: @@ -86,13 +81,11 @@ public: volatile U8* mClientData; }; - std::list mGLNamePool; - typedef std::list record_list_t; std::vector mFreeList; - std::vector mMissCount; }; + //============================================================================ // base class class LLPrivateMemoryPool; @@ -126,22 +119,13 @@ public: static LLVBOPool sStreamIBOPool; static LLVBOPool sDynamicIBOPool; - static std::list sAvailableVAOName; - static U32 sCurVAOName; - static bool sUseStreamDraw; static bool sUseVAO; static bool sPreferStreamDraw; - static void seedPools(); - - static U32 getVAOName(); - static void releaseVAOName(U32 name); - static void initClass(bool use_vbo, bool no_vbo_mapping); static void cleanupClass(); static void setupClientArrays(U32 data_mask); - static void pushPositions(U32 mode, const LLVector4a* pos, U32 count); static void drawArrays(U32 mode, const std::vector& pos, const std::vector& norm); static void drawElements(U32 mode, const LLVector4a* pos, const LLVector2* tc, S32 num_indices, const U16* indicesp); @@ -218,6 +202,7 @@ protected: void destroyGLIndices(); void updateNumVerts(S32 nverts); void updateNumIndices(S32 nindices); + bool useVBOs() const; void unmapBuffer(); public: @@ -227,8 +212,6 @@ public: volatile U8* mapVertexBuffer(S32 type, S32 index, S32 count, bool map_range); volatile U8* mapIndexBuffer(S32 index, S32 count, bool map_range); - void bindForFeedback(U32 channel, U32 type, U32 index, U32 count); - // set for rendering virtual void setBuffer(U32 data_mask); // calls setupVertexBuffer() if data_mask is not 0 void flush(); //flush pending data to GL memory @@ -251,14 +234,12 @@ public: bool getNormalStrider(LLStrider& strider, S32 index=0, S32 count = -1, bool map_range = false); bool getBinormalStrider(LLStrider& strider, S32 index=0, S32 count = -1, bool map_range = false); bool getColorStrider(LLStrider& strider, S32 index=0, S32 count = -1, bool map_range = false); - bool getTextureIndexStrider(LLStrider& strider, S32 index=0, S32 count = -1, bool map_range = false); bool getEmissiveStrider(LLStrider& strider, S32 index=0, S32 count = -1, bool map_range = false); bool getWeightStrider(LLStrider& strider, S32 index=0, S32 count = -1, bool map_range = false); bool getWeight4Strider(LLStrider& strider, S32 index=0, S32 count = -1, bool map_range = false); bool getClothWeightStrider(LLStrider& strider, S32 index=0, S32 count = -1, bool map_range = false); - bool useVBOs() const; bool isEmpty() const { return mEmpty; } bool isLocked() const { return mVertexLocked || mIndexLocked; } S32 getNumVerts() const { return mNumVerts; } diff --git a/indra/llui/llui.cpp b/indra/llui/llui.cpp index 4dbffde3a..bf5fc316d 100644 --- a/indra/llui/llui.cpp +++ b/indra/llui/llui.cpp @@ -809,7 +809,11 @@ void gl_stippled_line_3d( const LLVector3& start, const LLVector3& end, const LL gGL.flush(); glLineWidth(2.5f); - glLineStipple(2, 0x3333 << shift); + if (!LLGLSLShader::sNoFixedFunction) + { + glLineStipple(2, 0x3333 << shift); + } + gGL.begin(LLRender::LINES); { diff --git a/indra/newview/llface.cpp b/indra/newview/llface.cpp index 6a299deda..e52bb5959 100644 --- a/indra/newview/llface.cpp +++ b/indra/newview/llface.cpp @@ -1367,7 +1367,7 @@ BOOL LLFace::getGeometryVolume(const LLVolume& volume, static LLCachedControl use_transform_feedback("RenderUseTransformFeedback", false); -#ifdef GL_TRANSFORM_FEEDBACK_BUFFER +#if 0//#ifdef GL_TRANSFORM_FEEDBACK_BUFFER if (use_transform_feedback && gTransformPositionProgram.mProgramObject && //transform shaders are loaded mVertexBuffer->useVBOs() && //target buffer is in VRAM diff --git a/indra/newview/llselectmgr.cpp b/indra/newview/llselectmgr.cpp index 8cad1d048..223b6cf80 100644 --- a/indra/newview/llselectmgr.cpp +++ b/indra/newview/llselectmgr.cpp @@ -5651,7 +5651,7 @@ void LLSelectNode::renderOneWireframe(const LLColor4& color) if (shader) { - gHighlightProgram.bind(); + gDebugProgram.bind(); } gGL.matrixMode(LLRender::MM_MODELVIEW); diff --git a/indra/newview/llviewermessage.cpp b/indra/newview/llviewermessage.cpp index f4cad90e6..00ec70cd1 100644 --- a/indra/newview/llviewermessage.cpp +++ b/indra/newview/llviewermessage.cpp @@ -4754,8 +4754,6 @@ void process_kill_object(LLMessageSystem *mesgsys, void **user_data) LL_DEBUGS("Messaging") << "Kill message for local " << local_id << LL_ENDL; } - LLSelectMgr::getInstance()->removeObjectFromSelections(id); - // ...don't kill the avatar if (!(id == gAgentID)) { @@ -4785,6 +4783,12 @@ void process_kill_object(LLMessageSystem *mesgsys, void **user_data) gObjectList.mNumUnknownKills++; } } + + // We should remove the object from selection after it is marked dead by gObjectList to make LLToolGrab, + // which is using the object, release the mouse capture correctly when the object dies. + // See LLToolGrab::handleHoverActive() and LLToolGrab::handleHoverNonPhysical(). + LLSelectMgr::getInstance()->removeObjectFromSelections(id); + } } diff --git a/indra/newview/llviewerwindow.cpp b/indra/newview/llviewerwindow.cpp index 273b69da1..833d6412d 100644 --- a/indra/newview/llviewerwindow.cpp +++ b/indra/newview/llviewerwindow.cpp @@ -4907,6 +4907,8 @@ void LLViewerWindow::restoreGL(const std::string& progress_message) void LLViewerWindow::initFonts(F32 zoom_factor) { + if(gGLManager.mIsDisabled) + return; LLFontGL::destroyAllGL(); // Initialize with possibly different zoom factor LLFontGL::initClass( gSavedSettings.getF32("FontScreenDPI"), diff --git a/indra/newview/llvopartgroup.cpp b/indra/newview/llvopartgroup.cpp index c5ceee40c..434c8ca64 100644 --- a/indra/newview/llvopartgroup.cpp +++ b/indra/newview/llvopartgroup.cpp @@ -62,28 +62,6 @@ S32* LLVOPartGroup::sVBSlotCursor = NULL; //static void LLVOPartGroup::restoreGL() { - //Just iterate over all particle faces and mark their vbo index as 'uninitialized' since sVBSlotFree & sVBSlotCursor will be clobbered. - for (int i=0; imDrawable) - { - if (obj->mDrawable->getRenderType() == LLPipeline::RENDER_TYPE_PARTICLES || - obj->mDrawable->getRenderType() == LLPipeline::RENDER_TYPE_HUD_PARTICLES -#if ENABLE_CLASSIC_CLOUDS - || obj->mDrawable->getRenderType() == LLPipeline::RENDER_TYPE_CLASSIC_CLOUDS -#endif - ) - { - for (S32 j = 0; j < obj->mDrawable->getNumFaces(); ++j) - { - LLFace* facep = obj->mDrawable->getFace(j); - if(facep) - facep->setIndicesIndex(0xFFFFFFFF); - } - } - } - } for (S32 i = 0; i < LL_MAX_PARTICLE_COUNT; ++i) { sVBSlotFree[i] = i; @@ -142,6 +120,32 @@ void LLVOPartGroup::restoreGL() //static void LLVOPartGroup::destroyGL() { + //Just iterate over all particle faces and mark their vbo index as 'uninitialized' since sVBSlotFree & sVBSlotCursor will be clobbered. + for (int i=0; imDrawable) + { + if (obj->mDrawable->getRenderType() == LLPipeline::RENDER_TYPE_PARTICLES || + obj->mDrawable->getRenderType() == LLPipeline::RENDER_TYPE_HUD_PARTICLES +#if ENABLE_CLASSIC_CLOUDS + || obj->mDrawable->getRenderType() == LLPipeline::RENDER_TYPE_CLASSIC_CLOUDS +#endif + ) + { + for (S32 j = 0; j < obj->mDrawable->getNumFaces(); ++j) + { + LLFace* facep = obj->mDrawable->getFace(j); + if(facep) + facep->setIndicesIndex(0xFFFFFFFF); + } + } + } + } + for (S32 i = 0; i < LL_MAX_PARTICLE_COUNT; ++i) + { + sVBSlotFree[i] = i; + } sVB = NULL; } diff --git a/indra/newview/pipeline.cpp b/indra/newview/pipeline.cpp index 8b11475ed..bd2424294 100644 --- a/indra/newview/pipeline.cpp +++ b/indra/newview/pipeline.cpp @@ -457,9 +457,11 @@ void LLPipeline::init() { mCubeVB = ll_create_cube_vb(LLVertexBuffer::MAP_VERTEX, GL_STATIC_DRAW_ARB); } - - mDeferredVB = new LLVertexBuffer(DEFERRED_VB_MASK, 0); - mDeferredVB->allocateBuffer(8, 0, true); + if(mDeferredVB.isNull()) + { + mDeferredVB = new LLVertexBuffer(DEFERRED_VB_MASK, 0); + mDeferredVB->allocateBuffer(8, 0, true); + } setLightingDetail(-1); gSavedSettings.getControl("RenderAutoMaskAlphaDeferred")->getCommitSignal()->connect(boost::bind(&LLPipeline::refreshCachedSettings)); gSavedSettings.getControl("RenderAutoMaskAlphaNonDeferred")->getCommitSignal()->connect(boost::bind(&LLPipeline::refreshCachedSettings)); @@ -468,7 +470,7 @@ void LLPipeline::init() //gSavedSettings.getControl("RenderDelayVBUpdate")->getCommitSignal()->connect(boost::bind(&LLPipeline::refreshCachedSettings)); gSavedSettings.getControl("UseOcclusion")->getCommitSignal()->connect(boost::bind(&LLPipeline::refreshCachedSettings)); gSavedSettings.getControl("VertexShaderEnable")->getCommitSignal()->connect(boost::bind(&LLPipeline::refreshCachedSettings)); - + gSavedSettings.getControl("RenderFSAASamples")->getCommitSignal()->connect(boost::bind(&LLPipeline::refreshCachedSettings)); } LLPipeline::~LLPipeline() @@ -2330,10 +2332,10 @@ void LLPipeline::updateGL() LLGLUpdate::sGLQ.pop_front(); } - { //seed VBO Pools + /*{ //seed VBO Pools LLFastTimer t(FTM_SEED_VBO_POOLS); LLVertexBuffer::seedPools(); - } + }*/ } void LLPipeline::rebuildPriorityGroups() @@ -6102,6 +6104,7 @@ void LLPipeline::doResetVertexBuffers() mResetVertexBuffers = false; mCubeVB = NULL; + mDeferredVB = NULL; for (LLWorld::region_list_t::const_iterator iter = LLWorld::getInstance()->getRegionList().begin(); iter != LLWorld::getInstance()->getRegionList().end(); ++iter) @@ -7241,6 +7244,11 @@ void LLPipeline::renderDeferredLighting() glh::matrix4f mat = glh_copy_matrix(gGLModelView); + if(mDeferredVB.isNull()) + { + mDeferredVB = new LLVertexBuffer(DEFERRED_VB_MASK, 0); + mDeferredVB->allocateBuffer(8, 0, true); + } LLStrider vert; mDeferredVB->getVertexStrider(vert); LLStrider tc0;