diff --git a/README.md b/README.md index e78a22fd54..a60954a276 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,8 @@ -![Firestorm Viewer Logo](doc/firestorm_256.png) +Logo of Firestorm viewer -**[Firestorm](https://www.firestormviewer.org/) is a free client for 3D virtual worlds such as Second Life and various OpenSim worlds where users can create, connect and chat with others from around the world.** This repository contains the official source code for the Firestorm viewer. +**[Firestorm](https://www.firestormviewer.org) is a free client for 3D virtual worlds such as Second Life and various OpenSim worlds where users can create, connect and chat with others from around the world.** + +This repository contains the official source code for the Firestorm viewer. ## Open Source @@ -12,7 +14,7 @@ Pre-built versions of the viewer releases for Windows, Mac and Linux can be down ## Build Instructions -Build instructions for each operating system can be found using the links below and in the official [wiki](https://wiki.firestormviewer.org/). +Build instructions for each operating system can be found using the links below and in the official [wiki](https://wiki.firestormviewer.org). - [Windows](doc/building_windows.md) - [Mac](doc/building_macos.md) diff --git a/indra/llimage/llimagefilter.cpp b/indra/llimage/llimagefilter.cpp index 1703e30dbe..da3519e3ab 100644 --- a/indra/llimage/llimagefilter.cpp +++ b/indra/llimage/llimagefilter.cpp @@ -88,7 +88,7 @@ void LLImageFilter::executeFilter(LLPointer raw_image) { mImage = raw_image; - LLImageDataLock lock(mImage); + LLImageDataSharedLock lock(mImage); // FIRE-34564 Bugsplat SHARED vs EXCLUSIVE lock conflict //std::cout << "Filter : size = " << mFilterData.size() << std::endl; for (S32 i = 0; i < mFilterData.size(); ++i) diff --git a/indra/newview/CMakeLists.txt b/indra/newview/CMakeLists.txt index ca52fa1203..58619e6191 100644 --- a/indra/newview/CMakeLists.txt +++ b/indra/newview/CMakeLists.txt @@ -2256,6 +2256,7 @@ if (WINDOWS) "--fmodstudio=${USE_FMODSTUDIO}" "--openal=${USE_OPENAL}" "--tracy=${USE_TRACY}" + "--avx2=${USE_AVX2_OPTIMIZATION}" --build=${CMAKE_CURRENT_BINARY_DIR} --buildtype=$ "--channel=${VIEWER_CHANNEL}" @@ -2319,6 +2320,7 @@ if (WINDOWS) "--fmodstudio=${USE_FMODSTUDIO}" "--openal=${USE_OPENAL}" "--tracy=${USE_TRACY}" + "--avx2=${USE_AVX2_OPTIMIZATION}" --build=${CMAKE_CURRENT_BINARY_DIR} --buildtype=$ "--channel=${VIEWER_CHANNEL}" @@ -2504,6 +2506,7 @@ if (LINUX) "--fmodstudio=${USE_FMODSTUDIO}" "--openal=${USE_OPENAL}" "--tracy=${USE_TRACY}" + "--avx2=${USE_AVX2_OPTIMIZATION}" --build=${CMAKE_CURRENT_BINARY_DIR} --buildtype=${CMAKE_BUILD_TYPE} "--channel=${VIEWER_CHANNEL}" @@ -2531,6 +2534,7 @@ if (LINUX) "--fmodstudio=${USE_FMODSTUDIO}" "--openal=${USE_OPENAL}" "--tracy=${USE_TRACY}" + "--avx2=${USE_AVX2_OPTIMIZATION}" --build=${CMAKE_CURRENT_BINARY_DIR} --buildtype=${CMAKE_BUILD_TYPE} "--channel=${VIEWER_CHANNEL}" @@ -2626,6 +2630,7 @@ if (DARWIN) "--fmodstudio=${USE_FMODSTUDIO}" "--openal=${USE_OPENAL}" "--tracy=${USE_TRACY}" + "--avx2=${USE_AVX2_OPTIMIZATION}" --build=${CMAKE_CURRENT_BINARY_DIR} --buildtype=$ --bundleid=${MACOSX_BUNDLE_GUI_IDENTIFIER} @@ -2663,6 +2668,7 @@ if (DARWIN) "--fmodstudio=${USE_FMODSTUDIO}" "--openal=${USE_OPENAL}" "--tracy=${USE_TRACY}" + "--avx2=${USE_AVX2_OPTIMIZATION}" --build=${CMAKE_CURRENT_BINARY_DIR} --buildtype=${CMAKE_BUILD_TYPE} "--channel=${VIEWER_CHANNEL}" diff --git a/indra/newview/fs_viewer_manifest.py b/indra/newview/fs_viewer_manifest.py index d6666d0fef..8093f9d3f6 100644 --- a/indra/newview/fs_viewer_manifest.py +++ b/indra/newview/fs_viewer_manifest.py @@ -4,18 +4,25 @@ import tarfile class FSViewerManifest: def fs_installer_basename(self): + if self.fs_is_avx2(): + opt_string = "AVX2" + else: + opt_string = "LEGACY" substitution_strings = { 'version' : '.'.join(self.args['version']), 'version_short' : '.'.join(self.args['version'][:-1]), 'version_dashes' : '-'.join(self.args['version']), 'app_name':self.app_name(), + 'optimized': opt_string, 'app_name_oneword':self.app_name_oneword() } - return "Phoenix-%(app_name)s-%(version_dashes)s" % substitution_strings + return "Phoenix-%(app_name)s_%(optimized)s-%(version_dashes)s" % substitution_strings def fs_is_opensim(self): return self.args['viewer_flavor'] == 'oss' #Havok would be hvk + def fs_is_avx2(self): + return self.args['avx2'] == 'ON' def fs_splice_grid_substitution_strings( self, subst_strings ): ret = subst_strings diff --git a/indra/newview/installers/windows/installer_template.nsi b/indra/newview/installers/windows/installer_template.nsi index bb62d35b1d..e0c515917b 100644 --- a/indra/newview/installers/windows/installer_template.nsi +++ b/indra/newview/installers/windows/installer_template.nsi @@ -32,7 +32,7 @@ SetCompressor /solid lzma # Compress whole installer as one block SetDatablockOptimize off # Only saves us 0.1%, not worth it XPStyle on # Add an XP manifest to the installer RequestExecutionLevel admin # For when we write to Program Files -Unicode true # Enable unicode support +Unicode true # Enable unicode support ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; Project flags @@ -181,6 +181,42 @@ Function dirPre FunctionEnd +; Add the AVX2 check functions +Function CheckCPUFlagsAVX2 + Push $1 + System::Call 'kernel32::IsProcessorFeaturePresent(i 40) i .r1' ; 40 is PF_AVX2_INSTRUCTIONS_AVAILABLE + IntCmp $1 1 OK_AVX2 + ; AVX2 not supported + MessageBox MB_OK $(MissingAVX2) + Quit + + OK_AVX2: + Pop $1 + Return +FunctionEnd + +Function CheckCPUFlagsAVX2_Prompt + Push $1 + System::Call 'kernel32::IsProcessorFeaturePresent(i 40) i .r1' ; 40 is PF_AVX2_INSTRUCTIONS_AVAILABLE + IntCmp $1 1 OK_AVX2 Not_AVX2 + + OK_AVX2: + MessageBox MB_YESNO $(AVX2Available) IDYES DownloadAVX2 IDNO ContinueInstall + DownloadAVX2: + ExecShell open 'https://www.firestormviewer.org/early-access-beta-downloads/' + Quit + ContinueInstall: + Goto End + + Not_AVX2: + ; CPU does not support AVX2, continue installation + Goto End + + End: + Pop $1 + Return +FunctionEnd + # Optional start menu entry ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; Post-directory page callback @@ -224,6 +260,12 @@ ${If} $0 != "" ${EndIf} Call CheckCPUFlags # Make sure we have SSE2 support +${If} ${ISAVX2} == 1 + Call CheckCPUFlagsAVX2 +${Else} + Call CheckCPUFlagsAVX2_Prompt +${EndIf} + Call CheckWindowsVersion # Don't install On unsupported systems Push $0 ${GetParameters} $COMMANDLINE # Get our command line diff --git a/indra/newview/installers/windows/lang_de.nsi b/indra/newview/installers/windows/lang_de.nsi index 164f165f50..a11e4d505a 100755 --- a/indra/newview/installers/windows/lang_de.nsi +++ b/indra/newview/installers/windows/lang_de.nsi @@ -57,6 +57,8 @@ LangString CheckAdministratorUnInstMB ${LANG_GERMAN} 'Sie besitzen ungenügende ; checkcpuflags LangString MissingSSE2 ${LANG_GERMAN} "Dieser PC besitzt möglicherweise keinen Prozessor mit SSE2-Unterstützung, die für die Ausführung von Firestorm ${VERSION_LONG} benötigt wird. Trotzdem installieren?" +LangString MissingAVX2 ${LANG_GERMAN} "Ihre CPU unterstützt keine AVX2-Anweisungen. Bitte laden Sie die Version für ältere CPUs von https://www.firestormviewer.org/early-access-beta-downloads-legacy-cpus/ herunter." +LangString AVX2Available ${LANG_GERMAN} "Ihre CPU unterstützt AVX2-Anweisungen. Sie können die für AVX2 optimierte Version für eine bessere Leistung unter https://www.firestormviewer.org/early-access-beta-downloads/ herunterladen. Möchten Sie sie jetzt herunterladen?" ; closesecondlife function (install) LangString CloseSecondLifeInstDP ${LANG_GERMAN} "Warten auf die Beendigung von Firestorm ..." diff --git a/indra/newview/installers/windows/lang_en-us.nsi b/indra/newview/installers/windows/lang_en-us.nsi index c301aa0e4e..69cde24d32 100644 Binary files a/indra/newview/installers/windows/lang_en-us.nsi and b/indra/newview/installers/windows/lang_en-us.nsi differ diff --git a/indra/newview/installers/windows/lang_es.nsi b/indra/newview/installers/windows/lang_es.nsi index 37897d5981..cf36e45285 100755 Binary files a/indra/newview/installers/windows/lang_es.nsi and b/indra/newview/installers/windows/lang_es.nsi differ diff --git a/indra/newview/installers/windows/lang_fr.nsi b/indra/newview/installers/windows/lang_fr.nsi index fc263d1eab..5312e31426 100755 Binary files a/indra/newview/installers/windows/lang_fr.nsi and b/indra/newview/installers/windows/lang_fr.nsi differ diff --git a/indra/newview/installers/windows/lang_it.nsi b/indra/newview/installers/windows/lang_it.nsi index 34e3bdcebd..d7447ed46b 100755 Binary files a/indra/newview/installers/windows/lang_it.nsi and b/indra/newview/installers/windows/lang_it.nsi differ diff --git a/indra/newview/installers/windows/lang_ja.nsi b/indra/newview/installers/windows/lang_ja.nsi index 8322d86f81..b0d8958984 100755 Binary files a/indra/newview/installers/windows/lang_ja.nsi and b/indra/newview/installers/windows/lang_ja.nsi differ diff --git a/indra/newview/installers/windows/lang_pl.nsi b/indra/newview/installers/windows/lang_pl.nsi index 2a8ea7ef1d..3356eed567 100644 Binary files a/indra/newview/installers/windows/lang_pl.nsi and b/indra/newview/installers/windows/lang_pl.nsi differ diff --git a/indra/newview/installers/windows/lang_ru.nsi b/indra/newview/installers/windows/lang_ru.nsi index 3f75a5b580..c7bb70ad02 100755 Binary files a/indra/newview/installers/windows/lang_ru.nsi and b/indra/newview/installers/windows/lang_ru.nsi differ diff --git a/indra/newview/llpanelgroupbulk.cpp b/indra/newview/llpanelgroupbulk.cpp index 433db74cda..8032e207cd 100644 --- a/indra/newview/llpanelgroupbulk.cpp +++ b/indra/newview/llpanelgroupbulk.cpp @@ -56,6 +56,7 @@ LLPanelGroupBulkImpl::LLPanelGroupBulkImpl(const LLUUID& group_id) : mGroupID(group_id), mBulkAgentList(NULL), mOKButton(NULL), + mAddButton(nullptr), mRemoveButton(NULL), mGroupName(NULL), mLoadingText(), @@ -79,29 +80,18 @@ LLPanelGroupBulkImpl::~LLPanelGroupBulkImpl() } } -// static -void LLPanelGroupBulkImpl::callbackClickAdd(void* userdata) +void LLPanelGroupBulkImpl::callbackClickAdd(LLPanelGroupBulk* panelp) { - if (LLPanelGroupBulk* panelp = (LLPanelGroupBulk*)userdata) - { - // Right now this is hard coded with some knowledge that it is part - // of a floater since the avatar picker needs to be added as a dependent - // floater to the parent floater. - // Soon the avatar picker will be embedded into this panel - // instead of being it's own separate floater. But that is next week. - // This will do for now. -jwolk May 10, 2006 - LLView* button = panelp->findChild("add_button"); - LLFloater* root_floater = gFloaterView->getParentFloater(panelp); - LLFloaterAvatarPicker* picker = LLFloaterAvatarPicker::show( - [&](const uuid_vec_t& agent_ids, const std::vector&) - { - panelp->mImplementation->addUsers(agent_ids); - }, true, false, false, root_floater->getName(), button); - if (picker) + LLFloater* root_floater = gFloaterView->getParentFloater(panelp); + LLFloaterAvatarPicker* picker = LLFloaterAvatarPicker::show( + [this](const uuid_vec_t& agent_ids, const std::vector&) { - root_floater->addDependentFloater(picker); - LLGroupMgr::getInstance()->sendCapGroupMembersRequest(panelp->mImplementation->mGroupID); - } + addUsers(agent_ids); + }, true, false, false, root_floater->getName(), mAddButton); + if (picker) + { + root_floater->addDependentFloater(picker); + LLGroupMgr::getInstance()->sendCapGroupMembersRequest(mGroupID); } } diff --git a/indra/newview/llpanelgroupbulkban.cpp b/indra/newview/llpanelgroupbulkban.cpp index 3c764887a6..1d3edad0f3 100644 --- a/indra/newview/llpanelgroupbulkban.cpp +++ b/indra/newview/llpanelgroupbulkban.cpp @@ -68,35 +68,26 @@ bool LLPanelGroupBulkBan::postBuild() mImplementation->mBulkAgentList->setCommitCallback(LLPanelGroupBulkImpl::callbackSelect, mImplementation); } - LLButton* button = getChild("add_button", recurse); - if ( button ) + mImplementation->mAddButton = getChild("add_button", recurse); + // default to opening avatarpicker automatically + mImplementation->mAddButton->setClickedCallback( + [this](LLUICtrl* ctrl, const LLSD& param) { - // default to opening avatarpicker automatically - // (*impl::callbackClickAdd)((void*)this); - button->setClickedCallback(LLPanelGroupBulkImpl::callbackClickAdd, this); - } + mImplementation->callbackClickAdd(this); + }); mImplementation->mRemoveButton = getChild("remove_button", recurse); - if ( mImplementation->mRemoveButton ) - { - mImplementation->mRemoveButton->setClickedCallback(LLPanelGroupBulkImpl::callbackClickRemove, mImplementation); - mImplementation->mRemoveButton->setEnabled(false); - } + mImplementation->mRemoveButton->setClickedCallback(LLPanelGroupBulkImpl::callbackClickRemove, mImplementation); + mImplementation->mRemoveButton->setEnabled(false); mImplementation->mOKButton = getChild("ban_button", recurse); - if ( mImplementation->mOKButton ) - { - mImplementation->mOKButton->setClickedCallback(LLPanelGroupBulkBan::callbackClickSubmit, this); - mImplementation->mOKButton->setEnabled(false); - } + mImplementation->mOKButton->setClickedCallback(LLPanelGroupBulkBan::callbackClickSubmit, this); + mImplementation->mOKButton->setEnabled(false); - button = getChild("cancel_button", recurse); - if ( button ) - { - button->setClickedCallback(LLPanelGroupBulkImpl::callbackClickCancel, mImplementation); - } + LLButton* button = getChild("cancel_button", recurse); + button->setClickedCallback(LLPanelGroupBulkImpl::callbackClickCancel, mImplementation); mImplementation->mTooManySelected = getString("ban_selection_too_large"); mImplementation->mBanNotPermitted = getString("ban_not_permitted"); diff --git a/indra/newview/llpanelgroupbulkimpl.h b/indra/newview/llpanelgroupbulkimpl.h index 5a479f8117..5515bd6d9a 100644 --- a/indra/newview/llpanelgroupbulkimpl.h +++ b/indra/newview/llpanelgroupbulkimpl.h @@ -44,7 +44,7 @@ public: LLPanelGroupBulkImpl(const LLUUID& group_id); ~LLPanelGroupBulkImpl(); - static void callbackClickAdd(void* userdata); + void callbackClickAdd(LLPanelGroupBulk* panelp); static void callbackClickRemove(void* userdata); static void callbackClickCancel(void* userdata); @@ -70,6 +70,7 @@ public: LLNameListCtrl* mBulkAgentList; LLButton* mOKButton; + LLButton* mAddButton; LLButton* mRemoveButton; LLTextBox* mGroupName; diff --git a/indra/newview/llviewerpartsim.cpp b/indra/newview/llviewerpartsim.cpp index 028c82c1ce..eccbb5722c 100644 --- a/indra/newview/llviewerpartsim.cpp +++ b/indra/newview/llviewerpartsim.cpp @@ -47,8 +47,8 @@ const F32 PART_SIM_BOX_SIDE = 16.f; //static S32 LLViewerPartSim::sMaxParticleCount = 0; -S32 LLViewerPartSim::sParticleCount = 0; -S32 LLViewerPartSim::sParticleCount2 = 0; +std::atomic LLViewerPartSim::sParticleCount{0}; // FIRE-34600 - bugsplat AVX2 particle count mismatch +std::atomic LLViewerPartSim::sParticleCount2{0}; // FIRE-34600 - bugsplat AVX2 particle count mismatch // This controls how greedy individual particle burst sources are allowed to be, and adapts according to how near the particle-count limit we are. F32 LLViewerPartSim::sParticleAdaptiveRate = 0.0625f; F32 LLViewerPartSim::sParticleBurstRate = 0.5f; @@ -82,7 +82,7 @@ LLViewerPart::LLViewerPart() : mPartSourcep = NULL; mParent = NULL; mChild = NULL; - ++LLViewerPartSim::sParticleCount2 ; + LLViewerPartSim::incParticleCount2( 1 ); // FIRE-34600 - bugsplat AVX2 particle count mismatch } LLViewerPart::~LLViewerPart() @@ -107,7 +107,7 @@ LLViewerPart::~LLViewerPart() mPartSourcep = NULL; - --LLViewerPartSim::sParticleCount2 ; + LLViewerPartSim::decParticleCount2( 1 ); // FIRE-34600 - bugsplat AVX2 particle count mismatch } void LLViewerPart::init(LLPointer sourcep, LLViewerTexture *imagep, LLVPCallback cb) @@ -205,7 +205,7 @@ LLViewerPartGroup::~LLViewerPartGroup() } mParticles.clear(); - LLViewerPartSim::decPartCount(count); + LLViewerPartSim::decParticleCount(count); // FIRE-34600 - bugsplat AVX2 particle count mismatch } void LLViewerPartGroup::cleanup() @@ -268,7 +268,7 @@ bool LLViewerPartGroup::addPart(LLViewerPart* part, F32 desired_size) mParticles.push_back(part); part->mSkipOffset=mSkippedTime; - LLViewerPartSim::incPartCount(1); + LLViewerPartSim::incParticleCount(1); // FIRE-34600 - bugsplat AVX2 particle count mismatch return true; } @@ -432,7 +432,7 @@ void LLViewerPartGroup::updateParticles(const F32 lastdt) { gPipeline.markRebuild(mVOPartGroupp->mDrawable, LLDrawable::REBUILD_ALL); } - LLViewerPartSim::decPartCount(removed); + LLViewerPartSim::decParticleCount(removed); // FIRE-34600 - bugsplat AVX2 particle count mismatch } // Kill the viewer object if this particle group is empty @@ -478,14 +478,22 @@ void LLViewerPartGroup::removeParticlesByID(const U32 source_id) //static void LLViewerPartSim::checkParticleCount(U32 size) { - if(LLViewerPartSim::sParticleCount2 != LLViewerPartSim::sParticleCount) + // FIRE-34600 - bugsplat AVX2 particle count mismatch + // if(LLViewerPartSim::sParticleCount2 != LLViewerPartSim::sParticleCount) + S32 count = LLViewerPartSim::getParticleCount(); + S32 count2 = LLViewerPartSim::getParticleCount2(); + if( count != count2 ) + // { - LL_ERRS() << "sParticleCount: " << LLViewerPartSim::sParticleCount << " ; sParticleCount2: " << LLViewerPartSim::sParticleCount2 << LL_ENDL ; + LL_ERRS() << "sParticleCount: " << count << " ; sParticleCount2: " << count2 << LL_ENDL ; // FIRE-34600 - bugsplat AVX2 particle count mismatch } - if(size > (U32)LLViewerPartSim::sParticleCount2) + // FIRE-34600 - bugsplat AVX2 particle count mismatch + // if(size > (U32)LLViewerPartSim::sParticleCount2) + if( size > static_cast(count2) ) + // { - LL_ERRS() << "curren particle size: " << LLViewerPartSim::sParticleCount2 << " array size: " << size << LL_ENDL ; + LL_ERRS() << "current particle size: " << count2 << " array size: " << size << LL_ENDL ; // FIRE-34600 - bugsplat AVX2 particle count mismatch } } @@ -531,14 +539,18 @@ void LLViewerPartSim::destroyClass() //static bool LLViewerPartSim::shouldAddPart() { - if (sParticleCount >= MAX_PART_COUNT) + // FIRE-34600 - bugsplat AVX2 particle count mismatch + // if (sParticleCount < MAX_PART_COUNT) + auto count = LLViewerPartSim::getParticleCount(); + if ( count >= MAX_PART_COUNT) + // { return false; } - if (sParticleCount > PART_THROTTLE_THRESHOLD*sMaxParticleCount) + if ( count > PART_THROTTLE_THRESHOLD*sMaxParticleCount) // FIRE-34600 - bugsplat AVX2 particle count mismatch { - F32 frac = (F32)sParticleCount/(F32)sMaxParticleCount; + F32 frac = (F32)count/(F32)sMaxParticleCount; // FIRE-34600 - bugsplat AVX2 particle count mismatch frac -= PART_THROTTLE_THRESHOLD; frac *= PART_THROTTLE_RESCALE; if (ll_frand() < frac) @@ -560,7 +572,7 @@ bool LLViewerPartSim::shouldAddPart() void LLViewerPartSim::addPart(LLViewerPart* part) { - if (sParticleCount < MAX_PART_COUNT) + if (LLViewerPartSim::getParticleCount() < MAX_PART_COUNT) { put(part); } @@ -794,14 +806,19 @@ void LLViewerPartSim::updateSimulation() } if (LLDrawable::getCurrentFrame()%16==0) { - if (sParticleCount > sMaxParticleCount * 0.875f + // FIRE-34600 - bugsplat AVX2 particle count mismatch + // if (sParticleCount > sMaxParticleCount * 0.875f + // && sParticleAdaptiveRate < 2.0f) + auto count = LLViewerPartSim::getParticleCount(); + if ( count > sMaxParticleCount * 0.875f && sParticleAdaptiveRate < 2.0f) + // { sParticleAdaptiveRate *= PART_ADAPT_RATE_MULT; } else { - if (sParticleCount < sMaxParticleCount * 0.5f + if ( count < sMaxParticleCount * 0.5f // FIRE-34600 - bugsplat AVX2 particle count mismatch && sParticleAdaptiveRate > 0.03125f) { sParticleAdaptiveRate *= PART_ADAPT_RATE_MULT_RECIP; @@ -818,15 +835,25 @@ void LLViewerPartSim::updatePartBurstRate() { if (!(LLDrawable::getCurrentFrame() & 0xf)) { - if (sParticleCount >= MAX_PART_COUNT) //set rate to zero + // FIRE-34600 - bugsplat AVX2 particle count mismatch + // if (sParticleCount >= MAX_PART_COUNT) //set rate to zero + auto count = LLViewerPartSim::getParticleCount(); + if (count >= MAX_PART_COUNT) //set rate to zero + // { sParticleBurstRate = 0.0f ; } - else if(sParticleCount > 0) + // FIRE-34600 - bugsplat AVX2 particle count mismatch + // else if(sParticleCount > 0) + else if (count > 0) + // { if(sParticleBurstRate > 0.0000001f) { - F32 total_particles = sParticleCount / sParticleBurstRate ; //estimated + // FIRE-34600 - bugsplat AVX2 particle count mismatch + // F32 total_particles = sParticleCount / sParticleBurstRate ; //estimated + F32 total_particles = count / sParticleBurstRate ; //estimated + // F32 new_rate = llclamp(0.9f * sMaxParticleCount / total_particles, 0.0f, 1.0f) ; F32 delta_rate_threshold = llmin(0.1f * llmax(new_rate, sParticleBurstRate), 0.1f) ; F32 delta_rate = llclamp(new_rate - sParticleBurstRate, -1.0f * delta_rate_threshold, delta_rate_threshold) ; diff --git a/indra/newview/llviewerpartsim.h b/indra/newview/llviewerpartsim.h index cf3843bd66..3e92a1988d 100644 --- a/indra/newview/llviewerpartsim.h +++ b/indra/newview/llviewerpartsim.h @@ -155,14 +155,25 @@ public: static bool shouldAddPart(); // Just decides whether this particle should be added or not (for particle count capping) F32 maxRate() // Return maximum particle generation rate { - if (sParticleCount >= MAX_PART_COUNT) + // FIRE-34600 - bugsplat AVX2 particle count mismatch + // if (sParticleCount >= MAX_PART_COUNT) + // { + // return 1.f; + // } + // if (sParticleCount > PART_THROTTLE_THRESHOLD*sMaxParticleCount) + // { + // return (((F32)sParticleCount/(F32)sMaxParticleCount)-PART_THROTTLE_THRESHOLD)*PART_THROTTLE_RESCALE; + // } + const auto count = getParticleCount(); + if ( count >= MAX_PART_COUNT) { return 1.f; } - if (sParticleCount > PART_THROTTLE_THRESHOLD*sMaxParticleCount) + if ( count > PART_THROTTLE_THRESHOLD*sMaxParticleCount) { - return (((F32)sParticleCount/(F32)sMaxParticleCount)-PART_THROTTLE_THRESHOLD)*PART_THROTTLE_RESCALE; + return (((F32)count/(F32)sMaxParticleCount)-PART_THROTTLE_THRESHOLD)*PART_THROTTLE_RESCALE; } + // return 0.f; } F32 getRefRate() { return sParticleAdaptiveRate; } @@ -177,12 +188,28 @@ public: friend class LLViewerPartGroup; - bool aboveParticleLimit() const { return sParticleCount > sMaxParticleCount; } - + // FIRE-34600 - bugsplat AVX2 particle count mismatch + // bool aboveParticleLimit() const { return sParticleCount > sMaxParticleCount; } + bool aboveParticleLimit() const { return getParticleCount() > sMaxParticleCount; } + // static void setMaxPartCount(const S32 max_parts) { sMaxParticleCount = max_parts; } static S32 getMaxPartCount() { return sMaxParticleCount; } - static void incPartCount(const S32 count) { sParticleCount += count; } - static void decPartCount(const S32 count) { sParticleCount -= count; } + + // FIRE-34600 - bugsplat AVX2 particle count mismatch + // static void incPartCount(const S32 count) { sParticleCount += count; } + // static void decPartCount(const S32 count) { sParticleCount -= count; } + static void incParticleCount(const S32 count, std::memory_order order = std::memory_order_seq_cst ) + { sParticleCount.fetch_add( count , std::memory_order_seq_cst ); } + static void decParticleCount(const S32 count, std::memory_order order = std::memory_order_seq_cst ) + { sParticleCount.fetch_sub( count , std::memory_order_seq_cst ); } + static void incParticleCount2(const S32 count, std::memory_order order = std::memory_order_seq_cst ) + { sParticleCount2.fetch_add( count , std::memory_order_seq_cst ); } + static void decParticleCount2(const S32 count, std::memory_order order = std::memory_order_seq_cst ) + { sParticleCount2.fetch_sub( count , std::memory_order_seq_cst ); } + static inline S32 getParticleCount(std::memory_order order = std::memory_order_seq_cst) { return sParticleCount.load(order); } + + static inline S32 getParticleCount2(std::memory_order order = std::memory_order_seq_cst) { return sParticleCount2.load(order); } + // U32 mID; @@ -195,7 +222,7 @@ protected: LLFrameTimer mSimulationTimer; static S32 sMaxParticleCount; - static S32 sParticleCount; + static std::atomic sParticleCount; // FIRE-34600 - bugsplat AVX2 particle count mismatch static F32 sParticleAdaptiveRate; static F32 sParticleBurstRate; @@ -207,7 +234,7 @@ protected: //debug use only public: - static S32 sParticleCount2; + static std::atomic sParticleCount2; // FIRE-34600 - bugsplat AVX2 particle count mismatch static void checkParticleCount(U32 size = 0) ; }; diff --git a/indra/newview/skins/default/xui/de/floater_phototools_camera.xml b/indra/newview/skins/default/xui/de/floater_phototools_camera.xml index 621fe231f4..25490cfcad 100644 --- a/indra/newview/skins/default/xui/de/floater_phototools_camera.xml +++ b/indra/newview/skins/default/xui/de/floater_phototools_camera.xml @@ -56,6 +56,8 @@ + + +