diff --git a/.github/workflows/build_viewer.yml b/.github/workflows/build_viewer.yml
index 08872166db..8adec3ef10 100644
--- a/.github/workflows/build_viewer.yml
+++ b/.github/workflows/build_viewer.yml
@@ -1,8 +1,14 @@
name: Build viewer
-on: push
-env:
+on:
+ push:
+ branches:
+ - "*release"
+ - master
+ schedule:
+ - cron: '00 03 * * *' # Run every day at 3am UTC
+env:
AUTOBUILD_VARIABLES_FILE: ${{github.workspace}}/build-variables/variables
- EXTRA_ARGS: -DFMODSTUDIO=ON -DUSE_KDU=ON --crashreporting
+ EXTRA_ARGS: -DUSE_FMODSTUDIO=ON -DUSE_KDU=ON --crashreporting
build_secrets_checkout: ${{github.workspace}}/signing
@@ -67,15 +73,22 @@ jobs:
- name: find channel from Branch name
run: |
- if [[ "${{ github.ref_name }}" == *"Release"* ]]; then
- FS_RELEASE_CHAN="Release"
+ if [[ "${{ github.ref_name }}" == *Release* ]]; then
+ FS_RELEASE_TYPE=Release
else
- FS_RELEASE_CHAN="Beta"
+ if [[ "${{github.event_name}}" == 'schedule' ]]; then
+ FS_RELEASE_TYPE=Nightly
+ else
+ FS_RELEASE_TYPE=Beta
+ fi
fi
if [[ "${{ matrix.addrsize }}" == "64" ]]; then
- FS_RELEASE_CHAN="${FS_RELEASE_CHAN}x64"
+ FS_RELEASE_CHAN="${FS_RELEASE_TYPE}x64"
+ else
+ FS_RELEASE_CHAN=${FS_RELEASE_TYPE}
fi
- echo "FS_RELEASE_CHAN=\"${FS_RELEASE_CHAN}\"" >> $GITHUB_ENV
+ echo "FS_RELEASE_TYPE=${FS_RELEASE_TYPE}" >> $GITHUB_ENV
+ echo "FS_RELEASE_CHAN=${FS_RELEASE_CHAN}" >> $GITHUB_ENV
echo "Building for channel ${FS_RELEASE_CHAN}"
shell: bash
@@ -187,18 +200,18 @@ jobs:
run: rm *${{ env.fallback_platform }}*bz2
shell: bash
- name: Configure
- run: autobuild configure --debug -c ReleaseFS -A${{matrix.addrsize}} -- --package --chan ${{env.FS_RELEASE_CHAN}} ${{env.EXTRA_ARGS}} ${{env.FS_GRID}}
+ run: autobuild configure -c ReleaseFS -A${{matrix.addrsize}} -- --package --chan ${{env.FS_RELEASE_CHAN}} ${{env.EXTRA_ARGS}} ${{env.FS_GRID}}
shell: bash
- name: build
- run: autobuild build --debug -c ReleaseFS -A${{matrix.addrsize}} --no-configure
+ run: autobuild build -c ReleaseFS -A${{matrix.addrsize}} --no-configure
shell: bash
-
- - name: publish Windows artifacts
+
+ - name: Publish artifacts
if: runner.os == 'Windows'
uses: actions/upload-artifact@v3
with:
- name: ${{ matrix.os }}-${{matrix.addrsize}}-${{matrix.grid}}-artifacts.zip
+ name: ${{ env.FS_RELEASE_TYPE }}-${{ matrix.os }}-${{ matrix.addrsize }}-${{ matrix.grid }}-artifacts.zip
path: |
build-*/newview/Release/*Setup.exe
build-*/newview/Release/*.xz
@@ -207,7 +220,7 @@ jobs:
if: runner.os == 'Linux'
uses: actions/upload-artifact@v3
with:
- name: ${{ matrix.os }}-${{matrix.addrsize}}-${{matrix.grid}}-artifacts.zip
+ name: ${{ env.FS_RELEASE_TYPE }}-${{ matrix.os }}-${{matrix.addrsize}}-${{matrix.grid}}-artifacts.zip
path: |
build-linux-*/newview/*.xz
build-linux-*/newview/*.bz2
@@ -216,7 +229,53 @@ jobs:
if: runner.os == 'macOS'
uses: actions/upload-artifact@v3
with:
- name: ${{ matrix.os }}-${{matrix.addrsize}}-${{matrix.grid}}-artifacts.zip
+ name: ${{ env.FS_RELEASE_TYPE }}-${{ matrix.os }}-${{matrix.addrsize}}-${{matrix.grid}}-artifacts.zip
path: |
build-darwin-*/newview/*.dmg
build-darwin-*/newview/*.bz2
+ deploy:
+ runs-on: ubuntu-latest
+ needs: build_matrix
+ if: always()
+ steps:
+ - name: Checkout files
+ uses: Bhacaz/checkout-files@v2
+ with:
+ files: fsutils/download_list.py
+ branch: ${{ github.head_ref || github.ref_name || 'master' }}
+ - name: Install discord-webhook library
+ run: pip install discord-webhook
+
+ - name: find channel from Branch name
+ run: |
+ if [[ "${{ github.ref_name }}" == *Release* ]]; then
+ FS_RELEASE_FOLDER=release
+ else
+ if [[ "${{github.event_name}}" == 'schedule' ]]; then
+ FS_RELEASE_FOLDER=nightly
+ else
+ FS_RELEASE_FOLDER=preview
+ fi
+ fi
+ echo "FS_RELEASE_FOLDER=${FS_RELEASE_FOLDER}" >> $GITHUB_ENV
+
+ - name: Download artifacts
+ uses: actions/download-artifact@v3
+ id: download
+ with:
+ path: to_deploy
+ - name: List artifacts download
+ run: ls -R
+ working-directory: ${{steps.download.outputs.download-path}}
+
+ - name: Reorganise artifacts ready for server upload.
+ run: python ./fsutils/download_list.py -u ${{steps.download.outputs.download-path}} -w ${{ secrets.RELEASE_WEBHOOK_URL }}
+
+ - name: Setup rclone and download the folder
+ uses: beqjanus/setup-rclone@main
+ with:
+ rclone_config: ${{ secrets.RCLONE_CONFIG }}
+
+ - name: Copy files to remote host
+ run: rclone copy ${{steps.download.outputs.download-path}}/${{ env.FS_RELEASE_FOLDER }} fs_deploy:${{ env.FS_RELEASE_FOLDER }}
+
diff --git a/autobuild.xml b/autobuild.xml
index f434703137..a1d6228cc7 100644
--- a/autobuild.xml
+++ b/autobuild.xml
@@ -1,6 +1,5 @@
-
-
diff --git a/doc/contributions.txt b/doc/contributions.txt
index 2d928116a5..3a06bd36b3 100755
--- a/doc/contributions.txt
+++ b/doc/contributions.txt
@@ -285,9 +285,11 @@ Beq Janus
SL-11300
SL-15709
SL-16021
- SL-16027
+ SL-18202
+ SL-18586
SL-18592
SL-18637
+ SL-19317
Beth Walcher
Bezilon Kasei
Biancaluce Robbiani
diff --git a/fsutils/download_list.py b/fsutils/download_list.py
index 0747ae7e4c..b8534efeff 100644
--- a/fsutils/download_list.py
+++ b/fsutils/download_list.py
@@ -6,14 +6,9 @@ import time
import zipfile
import glob
import shutil
+from discord_webhook import DiscordWebhook
+
-# iterate over the files in a directory and pass them to a command line subshell
-def get_files(path):
- files = []
- for root, dirs, files in os.walk(path):
- # print(f"Found : {files}")
- return files
- return None
# run a command line subshell and return the output
@@ -65,6 +60,14 @@ def get_files(path):
# MD5: 9D5D8021F376194B42F6E7D8E537E45E
# -------------------------------------------------------------------------------------------------------
+# iterate over the files in a directory and pass them to a command line subshell
+def get_files(path):
+ files = []
+ for root, dirs, filenames in os.walk(path):
+ for filename in filenames:
+ files.append(filename)
+ print(f"Found : {files} on {path}")
+ return files
def run_cmd(cmd):
# print(cmd)
@@ -73,12 +76,12 @@ def run_cmd(cmd):
#using the md5sum command get the md5 for the file
def get_md5(mdfile):
- # print(f"mdfile is {mdfile}")
md5sum = run_cmd(f"md5sum {mdfile}")
#split md5sum on space
md5sum = md5sum.split()[0]
#remove leading '\'
md5sum = md5sum[1:]
+ print(f"generating md5sum for {mdfile} as {md5sum}")
return md5sum
def unzip_file(zip_file, unzip_dir):
@@ -86,6 +89,7 @@ def unzip_file(zip_file, unzip_dir):
zip_ref.extractall(unzip_dir)
def flatten_tree(tree_root):
+ print(f"Flattening tree {tree_root}")
for root, flatten_dirs, files in os.walk(tree_root, topdown=False):
for file in files:
# Construct the full path to the file
@@ -107,6 +111,8 @@ parser = argparse.ArgumentParser(
)
parser.add_argument("-r", "--release", required=False, default=False, action="store_true", help="use the release folder in the target URL")
parser.add_argument("-u", "--unzip", required=False, default=False, action="store_true", help="unzip the github artifact first")
+parser.add_argument("-w", "--webhook", help="post details to the webhook")
+
# add path_to_directory required parameter to parser
parser.add_argument("path_to_directory", help="path to the directory in which we'll look for the files")
@@ -114,102 +120,162 @@ args = parser.parse_args()
path_to_directory = args.path_to_directory
release = args.release
+# Create a webhook object with the webhook URL
+if args.webhook:
+ webhook = DiscordWebhook(url=args.webhook)
+
dirs = ["windows", "mac", "linux"]
-if args.unzip:
- # unzip the github artifact for this OS (`dir`) into the folder `dir`
- # get the .zip files in args.path_to_directory using glob
- zips = glob.glob(f"{args.path_to_directory}/*.zip")
- for file in zips:
- # print(f"unzipping {file}")
- if "ubuntu" in file.lower():
- unzip_file(file, os.path.join(args.path_to_directory, "linux"))
- if "windows" in file.lower():
- unzip_file(file, os.path.join(args.path_to_directory, "windows"))
- if "macos" in file.lower():
- unzip_file(file, os.path.join(args.path_to_directory, "mac"))
+# build_types is a map from Beta, Release and Nightly to folder names preview release and nightly
+build_types = {
+ "Beta": "preview",
+ "Release": "release",
+ "Nightly": "nightly"
+}
+
+target_folder = {
+ "ubuntu":"linux",
+ "windows":"windows",
+ "macos":"mac"
+}
+
+# unzip the github artifact for this OS (`dir`) into the folder `dir`
+# get the .zip files in args.path_to_directory using glob
+print(f"Processing artifacts in {args.path_to_directory}")
+build_types_created = set()
+zips = glob.glob(f"{args.path_to_directory}/*.zip")
+for file in zips:
+ # print(f"unzipping {file}")
+ #extract first word (delimited by '-' from the file name)
+ # build_type is a fullpath but we only want the last folder, remove the leading part of the path leaving just the foldername using basename
+ filename = os.path.basename(file)
+ build_type = filename.split("-")[0]
+ platform = filename.split("-")[1].lower()
+
+ # print(f"build_type is {build_type}")
+ if build_type not in build_types:
+ print(f"Invalid build_type {build_type} using file {file}")
+ continue
+ else:
+ build_folder = build_types[build_type]
+
+ build_types_created.add(build_type)
+
+ build_type_dir = os.path.join(args.path_to_directory, build_folder)
+
+ if platform not in target_folder:
+ print(f"Invalid platform {platform} using file {file}")
+ continue
+
+ unpack_folder = os.path.join(build_type_dir, target_folder[platform])
+ print(f"unpacking {filename} to {unpack_folder}")
+
+ if os.path.isfile(file):
+ # this is an actual zip file
+ unzip_file(file, unpack_folder)
+ else:
+ # Create the destination folder if it doesn't exist
+ # if not os.path.exists(unpack_folder):
+ # os.makedirs(unpack_folder)
+ # Copy the contents of the source folder to the destination folder recursively
+ shutil.copytree(file, unpack_folder, dirs_exist_ok=True)
+
+output = ""
+for build_type in build_types_created:
+ build_type_dir = os.path.join(args.path_to_directory, build_types[build_type])
+ if not os.path.exists(build_type_dir):
+ print(f"Unexpected error: {build_type_dir} does not exist, even though it was in the set.")
+ continue
+ # loop over the folder in the build_type_dir
for dir in dirs:
- flatten_tree(os.path.join(args.path_to_directory, dir))
+ print(f"Cleaning up {dir}")
+ # Traverse the directory tree and move all of the files to the root directory
+ flatten_tree(os.path.join(build_type_dir, dir))
# Now move the symbols files to the symbols folder
- symbols_folder = os.path.join(args.path_to_directory, "symbols")
+ # prep the symbols folder
+ symbols_folder = os.path.join(build_type_dir, "symbols")
os.mkdir(symbols_folder)
- # Traverse the directory tree and move all of the files to the root directory
- symbol_archives = glob.glob(f"{args.path_to_directory}/**/*_hvk*", recursive=True)
+ symbol_archives = glob.glob(f"{build_type_dir}/**/*_hvk*", recursive=True)
for sym_file in symbol_archives:
print(f"Moving {sym_file} to {symbols_folder}")
shutil.move(sym_file, symbols_folder)
- symbol_archives = glob.glob(f"{args.path_to_directory}/**/*_oss*", recursive=True)
+ symbol_archives = glob.glob(f"{build_type_dir}/**/*_oss*", recursive=True)
for sym_file in symbol_archives:
print(f"Moving {sym_file} to {symbols_folder}")
shutil.move(sym_file, symbols_folder)
-
-file_dict = {}
-md5_dict = {}
+ # While we're at it, let's print the md5 listing
+ file_dict = {}
+ md5_dict = {}
+ platforms_printable = {"windows":"MS Windows", "mac":"MacOS", "linux":"Linux"}
+ grids_printable = {"SL":"Second Life", "OS":"OpenSim"}
-for dir in dirs:
- dir = dir.lower()
- files = get_files(os.path.join(args.path_to_directory, dir))
- for file in files:
- full_file = os.path.join(args.path_to_directory, dir, file)
- md5 = get_md5(full_file)
- base_name = os.path.basename(file)
- if "-Release-" in base_name or "-Beta-" in base_name:
- wordsize = "32"
- else:
- wordsize = "64"
-
- if "FirestormOS-" in base_name:
- grid = "OS"
- else:
- grid = "SL"
-
- if dir in dirs:
- file_dict[f"{grid}{dir}{wordsize}"] = full_file
- md5_dict[f"{grid}{dir}{wordsize}"] = md5
-
-download_root_preview = "https://downloads.firestormviewer.org/preview"
-download_root_release = "https://downloads.firestormviewer.org/release"
-
-if args.release:
- download_root = download_root_release
-else:
- download_root = download_root_preview
-
-print('''
-DOWNLOADS''')
-
-platforms_printable = {"windows":"MS Windows", "mac":"MacOS", "linux":"Linux"}
-grids_printable = {"SL":"Second Life", "OS":"OpenSim"}
-
-for dir in dirs:
- print(f'''-------------------------------------------------------------------------------------------------------
-{platforms_printable[dir]}
-''')
- dir=dir.lower()
- wordsize = "64"
- platform = f"{platforms_printable[dir]}"
- for grid in ["SL", "OS"]:
- grid_printable = f"{grids_printable[grid]}"
+ download_root = f"https://downloads.firestormviewer.org/{build_types[build_type]}/"
+ for dir in dirs:
+ print(f"Getting files for {dir} in {build_type_dir}")
+ files = get_files(os.path.join(build_type_dir, dir))
try:
- print (f"{platform} for {grid_printable} ({wordsize}-bit)")
- print ( "{}/{}/{}".format(download_root,dir,os.path.basename(file_dict[f"{grid}{dir}{wordsize}"])) )
- print ()
- print ( "MD5: {}".format(md5_dict[f"{grid}{dir}{wordsize}"]) )
- print ()
- if(dir == "windows"):
- # Need to do 32 bit as well
- wordsize = "32"
- print (f"{platform} for {grid_printable} ({wordsize}-bit)")
- print ( "{}/{}/{}".format(download_root,dir,os.path.basename(file_dict[f"{grid}{dir}{wordsize}"])) )
- print ()
- print ( "MD5: {}".format(md5_dict[f"{grid}{dir}{wordsize}"]) )
- print ()
- wordsize = "64"
- except KeyError:
- print (f"{platform} for {grid_printable} ({wordsize}-bit) - NOT AVAILABLE")
- print ()
+ for file in files:
+ full_file = os.path.join(build_type_dir, dir, file)
+ md5 = get_md5(full_file)
+ base_name = os.path.basename(file)
+ if "x64" in base_name:
+ wordsize = "64"
+ else:
+ wordsize = "32"
+
+ if "FirestormOS-" in base_name:
+ grid = "OS"
+ else:
+ grid = "SL"
-print('''
--------------------------------------------------------------------------------------------------------''')
+ if dir in dirs:
+ file_dict[f"{grid}{dir}{wordsize}"] = full_file
+ md5_dict[f"{grid}{dir}{wordsize}"] = md5
+ except TypeError:
+ print(f"No files found for {dir} in {build_type_dir}")
+
+
+ output += f'''
+DOWNLOADS - {build_type}
+'''
+
+ output += f'''-------------------------------------------------------------------------------------------------------
+{platforms_printable[dir]}
+'''
+ dir = dir.lower()
+ wordsize = "64"
+ platform = f"{platforms_printable[dir]}"
+ for grid in ["SL", "OS"]:
+ grid_printable = f"{grids_printable[grid]}"
+ try:
+ output += f"{platform} for {grid_printable} ({wordsize}-bit)\n"
+ output += f"{download_root}/{dir}/{os.path.basename(file_dict[f'{grid}{dir}{wordsize}'])}\n"
+ output += "\n"
+ output += f"MD5: {md5_dict[f'{grid}{dir}{wordsize}']}\n"
+ output += "\n"
+ if dir == "windows":
+ # Need to do 32 bit as well
+ wordsize = "32"
+ output += f"{platform} for {grid_printable} ({wordsize}-bit)\n"
+ output += f"{download_root}/{dir}/{os.path.basename(file_dict[f'{grid}{dir}{wordsize}'])}\n"
+ output += "\n"
+ output += f"MD5: {md5_dict[f'{grid}{dir}{wordsize}']}\n"
+ output += "\n"
+ wordsize = "64"
+ except KeyError:
+ output += f"{platform} for {grid_printable} ({wordsize}-bit) - NOT AVAILABLE\n"
+ output += "\n"
+ output += '''
+-------------------------------------------------------------------------------------------------------
+'''
+
+ if args.webhook:
+ # Add the message to the webhook
+ webhook.set_content(content=output)
+ # Send the webhook
+ response = webhook.execute()
+ # Print the response
+ print(f"Webhook response: {response}")
+ print(output)
diff --git a/indra/cmake/Copy3rdPartyLibs.cmake b/indra/cmake/Copy3rdPartyLibs.cmake
index 4fb9531dfe..269560034b 100644
--- a/indra/cmake/Copy3rdPartyLibs.cmake
+++ b/indra/cmake/Copy3rdPartyLibs.cmake
@@ -281,6 +281,7 @@ elseif(LINUX)
libhunspell-1.3.so.0.0.0
+ #libopenjp2.so
libuuid.so.16
libuuid.so.16.0.22
@@ -356,6 +357,6 @@ if(DARWIN)
# that end up in any of the above SHARED_LIB_STAGING_DIR_MUMBLE
# directories.
add_custom_command( TARGET stage_third_party_libs POST_BUILD
- COMMAND cmake -E create_symlink ${SHARED_LIB_STAGING_DIR} ${CMAKE_BINARY_DIR}/sharedlibs/Resources
+ COMMAND ${CMAKE_COMMAND} -E create_symlink ${SHARED_LIB_STAGING_DIR} ${CMAKE_BINARY_DIR}/sharedlibs/Resources
)
endif()
diff --git a/indra/edit-me-to-trigger-new-build.txt b/indra/edit-me-to-trigger-new-build.txt
index eab7c17b71..8b13789179 100644
--- a/indra/edit-me-to-trigger-new-build.txt
+++ b/indra/edit-me-to-trigger-new-build.txt
@@ -1,4 +1 @@
-euclid 5/29/2020
-euclid 7/23/2020
-euclid 4/29/2021
-euclid 10/5/2021 DRTVWR-546
+
diff --git a/indra/llcommon/tests/llprocess_test.cpp b/indra/llcommon/tests/llprocess_test.cpp
index 999d432079..81449b4a42 100644
--- a/indra/llcommon/tests/llprocess_test.cpp
+++ b/indra/llcommon/tests/llprocess_test.cpp
@@ -356,7 +356,7 @@ namespace tut
// Create a script file in a temporary place.
NamedTempFile script("py",
- "from __future__ import print_function" EOL
+ "from __future__ import print_function" EOL
"import sys" EOL
"import time" EOL
EOL
@@ -366,7 +366,7 @@ namespace tut
"time.sleep(2)" EOL
"print('stderr after wait',file=sys.stderr)" EOL
"sys.stderr.flush()" EOL
- );
+ );
// Arrange to track the history of our interaction with child: what we
// fetched, which pipe it came from, how many tries it took before we
@@ -862,8 +862,8 @@ namespace tut
set_test_name("'bogus' test");
CaptureLog recorder;
PythonProcessLauncher py(get_test_name(),
- "from __future__ import print_function\n"
- "print('Hello world')\n");
+ "from __future__ import print_function\n"
+ "print('Hello world')\n");
py.mParams.files.add(LLProcess::FileParam("bogus"));
py.mPy = LLProcess::create(py.mParams);
ensure("should have rejected 'bogus'", ! py.mPy);
@@ -878,8 +878,8 @@ namespace tut
// Replace this test with one or more real 'file' tests when we
// implement 'file' support
PythonProcessLauncher py(get_test_name(),
- "from __future__ import print_function\n"
- "print('Hello world')\n");
+ "from __future__ import print_function\n"
+ "print('Hello world')\n");
py.mParams.files.add(LLProcess::FileParam());
py.mParams.files.add(LLProcess::FileParam("file"));
py.mPy = LLProcess::create(py.mParams);
@@ -894,8 +894,8 @@ namespace tut
// implement 'tpipe' support
CaptureLog recorder;
PythonProcessLauncher py(get_test_name(),
- "from __future__ import print_function\n"
- "print('Hello world')\n");
+ "from __future__ import print_function\n"
+ "print('Hello world')\n");
py.mParams.files.add(LLProcess::FileParam());
py.mParams.files.add(LLProcess::FileParam("tpipe"));
py.mPy = LLProcess::create(py.mParams);
@@ -912,8 +912,8 @@ namespace tut
// implement 'npipe' support
CaptureLog recorder;
PythonProcessLauncher py(get_test_name(),
- "from __future__ import print_function\n"
- "print('Hello world')\n");
+ "from __future__ import print_function\n"
+ "print('Hello world')\n");
py.mParams.files.add(LLProcess::FileParam());
py.mParams.files.add(LLProcess::FileParam());
py.mParams.files.add(LLProcess::FileParam("npipe"));
@@ -989,20 +989,20 @@ namespace tut
{
set_test_name("get*Pipe() validation");
PythonProcessLauncher py(get_test_name(),
- "from __future__ import print_function\n"
- "print('this output is expected')\n");
+ "from __future__ import print_function\n"
+ "print('this output is expected')\n");
py.mParams.files.add(LLProcess::FileParam("pipe")); // pipe for stdin
py.mParams.files.add(LLProcess::FileParam()); // inherit stdout
py.mParams.files.add(LLProcess::FileParam("pipe")); // pipe for stderr
py.run();
TEST_getPipe(*py.mPy, getWritePipe, getOptWritePipe,
- LLProcess::STDIN, // VALID
- LLProcess::STDOUT, // NOPIPE
- LLProcess::STDERR); // BADPIPE
+ LLProcess::STDIN, // VALID
+ LLProcess::STDOUT, // NOPIPE
+ LLProcess::STDERR); // BADPIPE
TEST_getPipe(*py.mPy, getReadPipe, getOptReadPipe,
- LLProcess::STDERR, // VALID
- LLProcess::STDOUT, // NOPIPE
- LLProcess::STDIN); // BADPIPE
+ LLProcess::STDERR, // VALID
+ LLProcess::STDOUT, // NOPIPE
+ LLProcess::STDIN); // BADPIPE
}
template<> template<>
@@ -1129,8 +1129,8 @@ namespace tut
{
set_test_name("ReadPipe \"eof\" event");
PythonProcessLauncher py(get_test_name(),
- "from __future__ import print_function\n"
- "print('Hello from Python!')\n");
+ "from __future__ import print_function\n"
+ "print('Hello from Python!')\n");
py.mParams.files.add(LLProcess::FileParam()); // stdin
py.mParams.files.add(LLProcess::FileParam("pipe")); // stdout
py.launch();
diff --git a/indra/llinventory/llsettingswater.cpp b/indra/llinventory/llsettingswater.cpp
index f19beb5be5..eb709585b8 100644
--- a/indra/llinventory/llsettingswater.cpp
+++ b/indra/llinventory/llsettingswater.cpp
@@ -286,6 +286,20 @@ F32 LLSettingsWater::getModifiedWaterFogDensity(bool underwater) const
if (underwater && underwater_fog_mod > 0.0f)
{
underwater_fog_mod = llclamp(underwater_fog_mod, 0.0f, 10.0f);
+ // BUG-233797/BUG-233798 -ve underwater fog density can cause (unrecoverable) blackout.
+ // raising a negative number to a non-integral power results in a non-real result (which is NaN for our purposes)
+ // Two methods were tested, number 2 is being used:
+ // 1) Force the fog_mod to be integral. The effect is unlikely to be nice, but it is better than blackness.
+ // In this method a few of the combinations are "usable" but the water colour is effectively inverted (blue becomes yellow)
+ // this seems to be unlikely to be a desirable use case for the majority.
+ // 2) Force density to be an arbitrary non-negative (i.e. 1) when underwater and modifier is not an integer (1 was aribtrarily chosen as it gives at least some notion of fog in the transition)
+ // This is more restrictive, effectively forcing a density under certain conditions, but allowing the range of #1 and avoiding blackness in other cases
+ // at the cost of overriding the fog density.
+ if(fog_density < 0.0f && underwater_fog_mod != (F32)llround(underwater_fog_mod) )
+ {
+ fog_density = 1.0f;
+ }
+ //
fog_density = pow(fog_density, underwater_fog_mod);
}
return fog_density;
diff --git a/indra/llwindow/llwindow.cpp b/indra/llwindow/llwindow.cpp
index ef7d18ddaf..1390c7ff6b 100644
--- a/indra/llwindow/llwindow.cpp
+++ b/indra/llwindow/llwindow.cpp
@@ -126,7 +126,8 @@ LLWindow::LLWindow(LLWindowCallbacks* callbacks, BOOL fullscreen, U32 flags)
mSwapMethod(SWAP_METHOD_UNDEFINED),
mHideCursorPermanent(FALSE),
mFlags(flags),
- mHighSurrogate(0)
+ mHighSurrogate(0),
+ mRefreshRate(0)
{
}
diff --git a/indra/llwindow/llwindow.h b/indra/llwindow/llwindow.h
index d8ac4aad43..2bc9842b05 100644
--- a/indra/llwindow/llwindow.h
+++ b/indra/llwindow/llwindow.h
@@ -197,6 +197,8 @@ public:
// windows only DirectInput8 for joysticks
virtual void* getDirectInput8() { return NULL; };
virtual bool getInputDevices(U32 device_type_filter, void * devices_callback, void* userdata) { return false; };
+
+ virtual S32 getRefreshRate() { return mRefreshRate; }
protected:
LLWindow(LLWindowCallbacks* callbacks, BOOL fullscreen, U32 flags);
virtual ~LLWindow();
@@ -230,6 +232,7 @@ protected:
U16 mHighSurrogate;
S32 mMinWindowWidth;
S32 mMinWindowHeight;
+ S32 mRefreshRate;
// Handle a UTF-16 encoding unit received from keyboard.
// Converting the series of UTF-16 encoding units to UTF-32 data,
diff --git a/indra/llwindow/llwindowmacosx.cpp b/indra/llwindow/llwindowmacosx.cpp
index 31a295b34b..c3382e06c5 100644
--- a/indra/llwindow/llwindowmacosx.cpp
+++ b/indra/llwindow/llwindowmacosx.cpp
@@ -53,6 +53,8 @@ BOOL check_for_card(const char* RENDERER, const char* bad_card);
const char* cursorIDToName(int id);
//
+const S32 DEFAULT_REFRESH_RATE = 60;
+
namespace
{
NSKeyEventRef mRawKeyEvent = NULL;
@@ -664,6 +666,13 @@ BOOL LLWindowMacOSX::createContext(int x, int y, int width, int height, int bits
}
}
+ mRefreshRate = CGDisplayModeGetRefreshRate(CGDisplayCopyDisplayMode(mDisplay));
+ if(mRefreshRate == 0)
+ {
+ //consider adding more appropriate fallback later
+ mRefreshRate = DEFAULT_REFRESH_RATE;
+ }
+
// Disable vertical sync for swap
toggleVSync(enable_vsync);
diff --git a/indra/llwindow/llwindowwin32.cpp b/indra/llwindow/llwindowwin32.cpp
index 9fa7ad0254..47c172e32e 100644
--- a/indra/llwindow/llwindowwin32.cpp
+++ b/indra/llwindow/llwindowwin32.cpp
@@ -589,7 +589,7 @@ LLWindowWin32::LLWindowWin32(LLWindowCallbacks* callbacks,
{
current_refresh = 60;
}
-
+ mRefreshRate = current_refresh;
//-----------------------------------------------------------------------
// Drop resolution and go fullscreen
// use a display mode with our desired size and depth, with a refresh
@@ -1075,6 +1075,7 @@ BOOL LLWindowWin32::switchContext(BOOL fullscreen, const LLCoordScreen& size, BO
{
current_refresh = 60;
}
+ mRefreshRate = current_refresh;
gGLManager.shutdownGL();
//destroy gl context
diff --git a/indra/newview/CMakeLists.txt b/indra/newview/CMakeLists.txt
index 0ac1f63ea1..8692c4b219 100644
--- a/indra/newview/CMakeLists.txt
+++ b/indra/newview/CMakeLists.txt
@@ -367,8 +367,8 @@ set(viewer_SOURCE_FILES
llfloaterpathfindinglinksets.cpp
llfloaterpathfindingobjects.cpp
llfloaterpay.cpp
- # llfloaterperformance.cpp replaced with fs version due to large changes and likelihood that LL version will not release.
- fsfloaterperformance.cpp
+ # llfloaterperformance.cpp
+ fsfloaterperformance.cpp # restore fs perf floater
llfloaterperms.cpp
llfloaterpostprocess.cpp
llfloaterprofile.cpp
@@ -1627,6 +1627,9 @@ set(viewer_HEADER_FILES
NACLfloaterexploresounds.h
)
+ list(APPEND viewer_SOURCE_FILES llperfstats.cpp)
+ list(APPEND viewer_HEADER_FILES llperfstats.h)
+
# Flickr / Discord keys and fsversionvalues headers are generated in here
include_directories( ${CMAKE_CURRENT_BINARY_DIR} )
@@ -1660,10 +1663,6 @@ configure_file(
list(APPEND viewer_HEADER_FILES ${CMAKE_CURRENT_BINARY_DIR}/fsversionvalues.h)
#
- # Performance stast support
- list(APPEND viewer_SOURCE_FILES fsperfstats.cpp)
- list(APPEND viewer_HEADER_FILES fsperfstats.h)
- #
source_group("CMake Rules" FILES ViewerInstall.cmake)
#build_data.json creation moved to viewer_manifest.py MAINT-6413
diff --git a/indra/newview/NACLantispam.cpp b/indra/newview/NACLantispam.cpp
index a72bbbffc8..9b5e709f10 100644
--- a/indra/newview/NACLantispam.cpp
+++ b/indra/newview/NACLantispam.cpp
@@ -103,18 +103,18 @@ NACLAntiSpamQueueEntry* NACLAntiSpamQueue::getEntry(const LLUUID& source)
}
else
{
- return NULL;
+ return nullptr;
}
}
void NACLAntiSpamQueue::clearEntries()
{
- for (spam_queue_entry_map_t::iterator it = mEntries.begin(); it != mEntries.end(); ++it)
+ for (auto& [id, entry] : mEntries)
{
//AO: Only clear entries that are not blocked.
- if (!it->second->getBlocked())
+ if (!entry->getBlocked())
{
- it->second->clearEntry();
+ entry->clearEntry();
}
}
}
@@ -139,15 +139,14 @@ void NACLAntiSpamQueue::blockEntry(const LLUUID& source)
mEntries[source]->setBlocked();
}
-S32 NACLAntiSpamQueue::checkEntry(const LLUUID& name, U32 multiplier)
-// Returns 0 if unblocked, 1 if check results in a new block, 2 if by an existing block
+EAntispamCheckResult NACLAntiSpamQueue::checkEntry(const LLUUID& name, U32 multiplier)
{
spam_queue_entry_map_t::iterator it = mEntries.find(name);
if (it != mEntries.end())
{
if (it->second->getBlocked())
{
- return 2;
+ return EAntispamCheckResult::ExistingBlock;
}
U32 eTime = it->second->getEntryTime();
U32 currentTime = time(0);
@@ -158,11 +157,11 @@ S32 NACLAntiSpamQueue::checkEntry(const LLUUID& name, U32 multiplier)
if (eAmount > (mQueueAmount * multiplier))
{
it->second->setBlocked();
- return 1;
+ return EAntispamCheckResult::NewBlock;
}
else
{
- return 0;
+ return EAntispamCheckResult::Unblocked;
}
}
else
@@ -170,7 +169,7 @@ S32 NACLAntiSpamQueue::checkEntry(const LLUUID& name, U32 multiplier)
it->second->clearEntry();
it->second->updateEntryAmount();
it->second->updateEntryTime();
- return 0;
+ return EAntispamCheckResult::Unblocked;
}
}
else
@@ -180,7 +179,7 @@ S32 NACLAntiSpamQueue::checkEntry(const LLUUID& name, U32 multiplier)
entry->updateEntryAmount();
entry->updateEntryTime();
mEntries[name] = entry;
- return 0;
+ return EAntispamCheckResult::Unblocked;
}
}
@@ -219,7 +218,7 @@ NACLAntiSpamRegistry::~NACLAntiSpamRegistry()
const char* NACLAntiSpamRegistry::getQueueName(EAntispamQueue queue)
{
- if (queue >= ANTISPAM_QUEUE_MAX)
+ if (queue >= ANTISPAM_QUEUE_MAX || queue < ANTISPAM_QUEUE_CHAT)
{
return "Unknown";
}
@@ -228,7 +227,7 @@ const char* NACLAntiSpamRegistry::getQueueName(EAntispamQueue queue)
void NACLAntiSpamRegistry::setRegisteredQueueTime(EAntispamQueue queue, U32 time)
{
- if (queue >= ANTISPAM_QUEUE_MAX || mQueues[queue] == NULL)
+ if (queue >= ANTISPAM_QUEUE_MAX || queue < ANTISPAM_QUEUE_CHAT || mQueues[queue] == nullptr)
{
LL_ERRS("AntiSpam") << "CODE BUG: Attempting to use a antispam queue that was not created or was outside of the reasonable range of queues. Queue: " << getQueueName(queue) << LL_ENDL;
return;
@@ -239,7 +238,7 @@ void NACLAntiSpamRegistry::setRegisteredQueueTime(EAntispamQueue queue, U32 time
void NACLAntiSpamRegistry::setRegisteredQueueAmount(EAntispamQueue queue, U32 amount)
{
- if (queue >= ANTISPAM_QUEUE_MAX || mQueues[queue] == NULL)
+ if (queue >= ANTISPAM_QUEUE_MAX || queue < ANTISPAM_QUEUE_CHAT || mQueues[queue] == nullptr)
{
LL_ERRS("AntiSpam") << "CODE BUG: Attempting to use a antispam queue that was not created or was outside of the reasonable range of queues. Queue: " << getQueueName(queue) << LL_ENDL;
return;
@@ -283,7 +282,7 @@ void NACLAntiSpamRegistry::setAllQueueAmounts(U32 amount)
void NACLAntiSpamRegistry::clearRegisteredQueue(EAntispamQueue queue)
{
- if (queue >= ANTISPAM_QUEUE_MAX || mQueues[queue] == NULL)
+ if (queue >= ANTISPAM_QUEUE_MAX || queue < ANTISPAM_QUEUE_CHAT || mQueues[queue] == nullptr)
{
LL_ERRS("AntiSpam") << "CODE BUG: Attempting to use a antispam queue that was not created or was outside of the reasonable range of queues. Queue: " << getQueueName(queue) << LL_ENDL;
return;
@@ -294,7 +293,7 @@ void NACLAntiSpamRegistry::clearRegisteredQueue(EAntispamQueue queue)
void NACLAntiSpamRegistry::purgeRegisteredQueue(EAntispamQueue queue)
{
- if (queue >= ANTISPAM_QUEUE_MAX || mQueues[queue] == NULL)
+ if (queue >= ANTISPAM_QUEUE_MAX || queue < ANTISPAM_QUEUE_CHAT || mQueues[queue] == nullptr)
{
LL_ERRS("AntiSpam") << "CODE BUG: Attempting to use a antispam queue that was not created or was outside of the reasonable range of queues. Queue: " << getQueueName(queue) << LL_ENDL;
return;
@@ -317,7 +316,7 @@ void NACLAntiSpamRegistry::blockOnQueue(EAntispamQueue queue, const LLUUID& sour
}
else
{
- if (queue >= ANTISPAM_QUEUE_MAX || mQueues[queue] == NULL)
+ if (queue >= ANTISPAM_QUEUE_MAX || queue < ANTISPAM_QUEUE_CHAT || mQueues[queue] == nullptr)
{
LL_ERRS("AntiSpam") << "CODE BUG: Attempting to use a antispam queue that was not created or was outside of the reasonable range of queues. Queue: " << getQueueName(queue) << LL_ENDL;
return;
@@ -362,14 +361,14 @@ bool NACLAntiSpamRegistry::checkQueue(EAntispamQueue queue, const LLUUID& source
}
}
- S32 result = 0;
+ EAntispamCheckResult result{ EAntispamCheckResult::Unblocked };
if (mGlobalQueue)
{
result = checkGlobalEntry(source, multiplier);
}
else
{
- if (queue >= ANTISPAM_QUEUE_MAX || mQueues[queue] == NULL)
+ if (queue >= ANTISPAM_QUEUE_MAX || queue < ANTISPAM_QUEUE_CHAT || mQueues[queue] == nullptr)
{
LL_ERRS("AntiSpam") << "CODE BUG: Attempting to use a antispam queue that was not created or was outside of the reasonable range of queues. Queue: " << getQueueName(queue) << LL_ENDL;
return false;
@@ -377,17 +376,17 @@ bool NACLAntiSpamRegistry::checkQueue(EAntispamQueue queue, const LLUUID& source
result = mQueues[queue]->checkEntry(source, multiplier);
}
- if (result == 0) // safe
+ if (result == EAntispamCheckResult::Unblocked) // safe
{
return false;
}
- if (result == 2) // previously blocked
+ if (result == EAntispamCheckResult::ExistingBlock) // previously blocked
{
return true;
}
- if (result == 1) // newly blocked, result == 1
+ if (result == EAntispamCheckResult::NewBlock) // newly blocked, result == 1
{
if (!LLMuteList::getInstance()->isMuted(source))
{
@@ -402,16 +401,14 @@ bool NACLAntiSpamRegistry::checkQueue(EAntispamQueue queue, const LLUUID& source
{
bool sent = false;
- for (LLWorld::region_list_t::const_iterator iter = LLWorld::getInstance()->getRegionList().begin();
- iter != LLWorld::getInstance()->getRegionList().end(); ++iter)
+ for (auto region : LLWorld::getInstance()->getRegionList())
{
- LLViewerRegion* region = *iter;
if (gMessageSystem && region && region->isAlive())
{
gMessageSystem->newMessage(_PREHASH_RequestObjectPropertiesFamily);
gMessageSystem->nextBlockFast(_PREHASH_AgentData);
gMessageSystem->addUUIDFast(_PREHASH_AgentID, gAgentID);
- gMessageSystem->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
+ gMessageSystem->addUUIDFast(_PREHASH_SessionID, gAgentSessionID);
gMessageSystem->nextBlockFast(_PREHASH_ObjectData);
gMessageSystem->addU32Fast(_PREHASH_RequestFlags, 0);
gMessageSystem->addUUIDFast(_PREHASH_ObjectID, source);
@@ -499,7 +496,7 @@ bool NACLAntiSpamRegistry::isBlockedOnQueue(EAntispamQueue queue, const LLUUID&
}
else
{
- if (queue >= ANTISPAM_QUEUE_MAX || mQueues[queue] == NULL)
+ if (queue >= ANTISPAM_QUEUE_MAX || queue < ANTISPAM_QUEUE_CHAT || mQueues[queue] == nullptr)
{
LL_ERRS("AntiSpam") << "CODE BUG: Attempting to use a antispam queue that was not created or was outside of the reasonable range of queues. Queue: " << getQueueName(queue) << LL_ENDL;
return false;
@@ -547,12 +544,11 @@ void NACLAntiSpamRegistry::clearAllQueues()
void NACLAntiSpamRegistry::purgeAllQueues()
{
- std::map::iterator it = mAvatarNameCallbackConnections.begin();
- for (; it != mAvatarNameCallbackConnections.end(); ++it)
+ for (auto& [avid, callback] : mAvatarNameCallbackConnections)
{
- if (it->second.connected())
+ if (callback.connected())
{
- it->second.disconnect();
+ callback.disconnect();
}
}
mAvatarNameCallbackConnections.clear();
@@ -574,14 +570,14 @@ void NACLAntiSpamRegistry::purgeAllQueues()
mObjectData.clear();
}
-S32 NACLAntiSpamRegistry::checkGlobalEntry(const LLUUID& source, U32 multiplier)
+EAntispamCheckResult NACLAntiSpamRegistry::checkGlobalEntry(const LLUUID& source, U32 multiplier)
{
spam_queue_entry_map_t::iterator it = mGlobalEntries.find(source);
if (it != mGlobalEntries.end())
{
if (it->second->getBlocked())
{
- return 2;
+ return EAntispamCheckResult::ExistingBlock;
}
U32 eTime = it->second->getEntryTime();
@@ -592,11 +588,11 @@ S32 NACLAntiSpamRegistry::checkGlobalEntry(const LLUUID& source, U32 multiplier)
U32 eAmount = it->second->getEntryAmount();
if (eAmount > (mGlobalAmount * multiplier))
{
- return 1;
+ return EAntispamCheckResult::NewBlock;
}
else
{
- return 0;
+ return EAntispamCheckResult::Unblocked;
}
}
else
@@ -604,7 +600,7 @@ S32 NACLAntiSpamRegistry::checkGlobalEntry(const LLUUID& source, U32 multiplier)
it->second->clearEntry();
it->second->updateEntryAmount();
it->second->updateEntryTime();
- return 0;
+ return EAntispamCheckResult::Unblocked;
}
}
else
@@ -613,15 +609,15 @@ S32 NACLAntiSpamRegistry::checkGlobalEntry(const LLUUID& source, U32 multiplier)
entry->updateEntryAmount();
entry->updateEntryTime();
mGlobalEntries[source] = entry;
- return 0;
+ return EAntispamCheckResult::Unblocked;
}
}
void NACLAntiSpamRegistry::clearGlobalEntries()
{
- for (spam_queue_entry_map_t::iterator it = mGlobalEntries.begin(); it != mGlobalEntries.end(); ++it)
+ for (auto& [id, entry] : mGlobalEntries)
{
- it->second->clearEntry();
+ entry->clearEntry();
}
}
diff --git a/indra/newview/NACLantispam.h b/indra/newview/NACLantispam.h
index d5cf7889a6..cf85aa3dca 100644
--- a/indra/newview/NACLantispam.h
+++ b/indra/newview/NACLantispam.h
@@ -1,8 +1,8 @@
#ifndef NACL_ANTISPAM_H
#define NACL_ANTISPAM_H
-#include
-#include
+#include
+#include
#include "llsingleton.h"
#include "llavatarnamecache.h"
@@ -25,6 +25,14 @@ typedef enum e_antispam_source_type
ANTISPAM_SOURCE_OBJECT
} EAntispamSource;
+
+enum class EAntispamCheckResult
+{
+ Unblocked,
+ NewBlock,
+ ExistingBlock
+};
+
struct AntispamObjectData
{
std::string mName;
@@ -58,8 +66,8 @@ private:
bool mBlocked;
};
-typedef boost::unordered_map spam_queue_entry_map_t;
-typedef boost::unordered_set collision_sound_set_t;
+typedef std::unordered_map spam_queue_entry_map_t;
+typedef std::unordered_set collision_sound_set_t;
class NACLAntiSpamQueue
{
@@ -77,7 +85,7 @@ protected:
void setTime(U32 time);
void blockEntry(const LLUUID& source);
- S32 checkEntry(const LLUUID& source, U32 multiplier);
+ EAntispamCheckResult checkEntry(const LLUUID& source, U32 multiplier);
NACLAntiSpamQueueEntry* getEntry(const LLUUID& source);
void clearEntries();
@@ -119,7 +127,7 @@ private:
const char* getQueueName(EAntispamQueue queue);
void blockGlobalEntry(const LLUUID& source);
- S32 checkGlobalEntry(const LLUUID& source, U32 multiplier);
+ EAntispamCheckResult checkGlobalEntry(const LLUUID& source, U32 multiplier);
void clearGlobalEntries();
void purgeGlobalEntries();
diff --git a/indra/newview/VIEWER_VERSION.txt b/indra/newview/VIEWER_VERSION.txt
index 8a68577213..5ea36a044a 100644
--- a/indra/newview/VIEWER_VERSION.txt
+++ b/indra/newview/VIEWER_VERSION.txt
@@ -1 +1 @@
-6.6.11
+6.6.12
diff --git a/indra/newview/app_settings/settings.xml b/indra/newview/app_settings/settings.xml
index e448d278d7..60ea148dcf 100644
--- a/indra/newview/app_settings/settings.xml
+++ b/indra/newview/app_settings/settings.xml
@@ -11706,6 +11706,28 @@ Change of this parameter will affect the layout of buttons in notification toast
Value
1
+ RenderClass0MemoryBandwidth
+
+ Comment
+ Memory bandwidth at which to default to Class 0 in gigabytes per second. Used as basis for other classes.
+ Persist
+ 1
+ Type
+ F32
+ Value
+ 16.0
+
+ RenderCPUBasis
+
+ Comment
+ Reference CPU clockspeed to use to bias GPU class (in MHz).
+ Persist
+ 1
+ Type
+ F32
+ Value
+ 3000.0
+
RenderComplexityColorMin
Comment
@@ -11981,6 +12003,17 @@ Change of this parameter will affect the layout of buttons in notification toast
Backup
0
+ RenderShadowSplits
+
+ Comment
+ Amount of shadow map splits to render (0 - 3).
+ Persist
+ 1
+ Type
+ S32
+ Value
+ 3
+
RenderSSAOScale
Comment
@@ -21968,6 +22001,160 @@ Change of this parameter will affect the layout of buttons in notification toast
Value
0
+ TargetFPS
+
+ Comment
+ Desired minimum FPS
+ Persist
+ 1
+ Type
+ U32
+ Value
+ 15
+
+ AutoTuneFPS
+
+ Comment
+ Allow the viewer to adjust your settings to achieve target FPS
+ Persist
+ 1
+ Type
+ Boolean
+ Value
+ 0
+
+ AutoTuneLock
+
+ Comment
+ When enabled the viewer will dynamically change settings until auto tune is explicitly turned off.
+ Persist
+ 1
+ Type
+ Boolean
+ Value
+ 0
+
+ KeepAutoTuneLock
+
+ Comment
+ When enabled the AutoTuneLock will be maintainted all following sessions.
+ Persist
+ 1
+ Type
+ U32
+ Value
+ 1
+
+ AllowSelfImpostor
+
+ Comment
+ Allow own render time to impostor your avatar.
+ Persist
+ 1
+ Type
+ Boolean
+ Value
+ 0
+
+ ShowTunedART
+
+ Comment
+ Show the current render time not the pre-tuning render time in the avatar display.
+ Persist
+ 1
+ Type
+ Boolean
+ Value
+ 1
+
+ RenderAvatarMaxART
+
+ Comment
+ Render Time Limit in microseconds (0.0 = no limit)
+ Persist
+ 0
+ Type
+ F32
+ Value
+ 4.699
+
+ AutoTuneRenderFarClipMin
+
+ Comment
+ The lowest draw distance that auto tune is allowed to use
+ Persist
+ 0
+ Type
+ F32
+ Value
+ 32.0
+
+ AutoTuneRenderFarClipTarget
+
+ Comment
+ The draw distance that auto tune will try to achieve
+ Persist
+ 0
+ Type
+ F32
+ Value
+ 256.0
+
+ UserTargetReflections
+
+ Comment
+ Set by auto tune floater on build
+ Persist
+ 0
+ Type
+ S32
+ Value
+ 4
+
+ PerfStatsCaptureEnabled
+
+ Comment
+ Enable/disable render time data to support autotune.
+ Persist
+ 1
+ Type
+ Boolean
+ Value
+ 1
+
+ AutoTuneImpostorByDistEnabled
+
+ Comment
+ Enable/disable using MaxNonImpostor to limit avatar rendering by distance.
+ Persist
+ 1
+ Type
+ Boolean
+ Value
+ 0
+
+ AutoTuneImpostorFarAwayDistance
+
+ Comment
+ Avatars beyond this range will automatically be optimized
+ Persist
+ 0
+ Type
+ F32
+ Value
+ 64.0
+
+ TuningFPSStrategy
+
+ Comment
+ Strategy to use when tuning FPS. 0=Tune avatar rendering only, 1=Tune both avatar and global scene settings, 2=Tune only global scene.
+ Persist
+ 1
+ Type
+ U32
+ Value
+ 1
+
CameraOpacity
Comment
@@ -26019,28 +26206,6 @@ Change of this parameter will affect the layout of buttons in notification toast
Value
0
- FSTargetFPS
-
- Comment
- Desired minimum FPS
- Persist
- 1
- Type
- U32
- Value
- 25
-
- FSAutoTuneFPS
-
- Comment
- Allow the viewer to adjust your settings to achieve target FPS
- Persist
- 0
- Type
- Boolean
- Value
- 0
-
FSPerfFloaterSmoothingPeriods
Comment
@@ -26085,127 +26250,6 @@ Change of this parameter will affect the layout of buttons in notification toast
Value
1
- FSPerfStatsCaptureEnabled
-
- Comment
- Enable/disable render time data to support autotune.
- Persist
- 1
- Type
- Boolean
- Value
- 1
-
- FSAutoTuneImpostorByDistEnabled
-
- Comment
- Enable/disable using MaxNonImpostor to limit avatar rendering by distance.
- Persist
- 1
- Type
- Boolean
- Value
- 0
-
- FSAutoTuneLock
-
- Comment
- When enabled the viewer will dynamically change settings until auto tune is explicitly turned off.
- Persist
- 1
- Type
- Boolean
- Value
- 1
-
- FSAllowSelfImpostor
-
- Comment
- Allow own render time to impostor your avatar.
- Persist
- 1
- Type
- Boolean
- Value
- 0
-
- FSShowTunedART
-
- Comment
- Show the tuned render time in the avatar display.
- Persist
- 1
- Type
- Boolean
- Value
- 0
-
- FSRenderAvatarMaxART
-
- Comment
- Render Time Limit in microseconds (0.0 = no limit)
- Persist
- 0
- Type
- F32
- Value
- 4.699
-
- FSAutoTuneRenderFarClipMin
-
- Comment
- The lowest draw distance that auto tune is allowed to use
- Persist
- 0
- Type
- F32
- Value
- 32.0
-
- FSAutoTuneRenderFarClipTarget
-
- Comment
- The draw distance that auto tune will try to achieve
- Persist
- 0
- Type
- F32
- Value
- 256.0
-
- FSAutoTuneImpostorFarAwayDistance
-
- Comment
- Avatars beyond this range will automatically be optimized
- Persist
- 0
- Type
- F32
- Value
- 64.0
-
- FSTuningFPSStrategy
-
- Comment
- Strategy to use when tuning FPS. 0=Tune avatar rendering only, 1=Tune both avatar and global scene settings.
- Persist
- 1
- Type
- U32
- Value
- 0
-
- FSUserTargetReflections
-
- Comment
- Set by auto tune floater on build
- Persist
- 0
- Type
- S32
- Value
- 4
-
FSReportRegionRestartToChat
Comment
@@ -26228,17 +26272,6 @@ Change of this parameter will affect the layout of buttons in notification toast
Value
473405
- FSUseCoRoFor360Capture
-
- Comment
- Use co-routine to extract 360 photos.
- Persist
- 1
- Type
- Boolean
- Value
- 0
-
SDL2IMEDefaultVerticalOffset
Comment
diff --git a/indra/newview/featuretable.txt b/indra/newview/featuretable.txt
index 310c0af25d..8113755d78 100644
--- a/indra/newview/featuretable.txt
+++ b/indra/newview/featuretable.txt
@@ -112,6 +112,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 0.5
RenderAvatarMaxComplexity 1 100000
RenderAvatarPhysicsLODFactor 1 0.75
+RenderAvatarMaxNonImpostors 1 5
RenderFarClip 1 96
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 8
@@ -141,6 +142,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 1.0
RenderAvatarMaxComplexity 1 200000
RenderAvatarPhysicsLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 7
RenderFarClip 1 128
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 9
@@ -170,6 +172,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 1.0
RenderAvatarMaxComplexity 1 250000
RenderAvatarPhysicsLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 9
RenderFarClip 1 128
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 9
@@ -199,6 +202,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 1.0
RenderAvatarMaxComplexity 1 300000
RenderAvatarPhysicsLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 11
RenderFarClip 1 128
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 9
@@ -228,6 +232,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 1.0
RenderAvatarMaxComplexity 1 350000
RenderAvatarPhysicsLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 16
RenderFarClip 1 128
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 9
@@ -255,6 +260,7 @@ list Ultra
RenderAnisotropic 1 1
RenderAvatarCloth 1 1
RenderAvatarLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 16
RenderAvatarPhysicsLODFactor 1 1.0
RenderFarClip 1 256
RenderFlexTimeFactor 1 1.0
diff --git a/indra/newview/featuretable_linux.txt b/indra/newview/featuretable_linux.txt
index fb16e7005d..3867a8e8f7 100644
--- a/indra/newview/featuretable_linux.txt
+++ b/indra/newview/featuretable_linux.txt
@@ -1,10 +1,10 @@
-version 29
+version 30
// The version number above should be incremented IF AND ONLY IF some
// change has been made that is sufficiently important to justify
// resetting the graphics preferences of all users to the recommended
// defaults. This should be as rare an event as we can manage.
-// NOTE: This is mostly identical to featuretable_mac.txt with a few differences
+// NOTE: This is mostly identical to featuretable_mac.txt with a few differences
// Should be combined into one table
//
@@ -112,6 +112,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 0.5
RenderAvatarMaxComplexity 1 100000
RenderAvatarPhysicsLODFactor 1 0.75
+RenderAvatarMaxNonImpostors 1 5
RenderFarClip 1 96
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 8
@@ -141,6 +142,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 1.0
RenderAvatarMaxComplexity 1 200000
RenderAvatarPhysicsLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 7
RenderFarClip 1 128
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 9
@@ -170,6 +172,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 1.0
RenderAvatarMaxComplexity 1 250000
RenderAvatarPhysicsLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 9
RenderFarClip 1 128
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 9
@@ -199,6 +202,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 1.0
RenderAvatarMaxComplexity 1 300000
RenderAvatarPhysicsLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 11
RenderFarClip 1 128
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 9
@@ -228,6 +232,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 1.0
RenderAvatarMaxComplexity 1 350000
RenderAvatarPhysicsLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 16
RenderFarClip 1 128
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 9
@@ -255,6 +260,7 @@ list Ultra
RenderAnisotropic 1 1
RenderAvatarCloth 1 1
RenderAvatarLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 16
RenderAvatarPhysicsLODFactor 1 1.0
RenderFarClip 1 256
RenderFlexTimeFactor 1 1.0
diff --git a/indra/newview/featuretable_mac.txt b/indra/newview/featuretable_mac.txt
index bffbbec13b..f63f65bf3b 100644
--- a/indra/newview/featuretable_mac.txt
+++ b/indra/newview/featuretable_mac.txt
@@ -111,6 +111,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 0.5
RenderAvatarMaxComplexity 1 100000
RenderAvatarPhysicsLODFactor 1 0.75
+RenderAvatarMaxNonImpostors 1 5
RenderFarClip 1 96
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 8
@@ -140,6 +141,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 1.0
RenderAvatarMaxComplexity 1 200000
RenderAvatarPhysicsLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 7
RenderFarClip 1 128
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 9
@@ -169,6 +171,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 1.0
RenderAvatarMaxComplexity 1 250000
RenderAvatarPhysicsLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 9
RenderFarClip 1 128
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 9
@@ -198,6 +201,7 @@ RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 1.0
RenderAvatarMaxComplexity 1 300000
RenderAvatarPhysicsLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 11
RenderFarClip 1 128
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 9
@@ -225,6 +229,7 @@ list HighUltra
RenderAnisotropic 1 1
RenderAvatarCloth 1 0
RenderAvatarLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 16
RenderAvatarMaxComplexity 1 350000
RenderAvatarPhysicsLODFactor 1 1.0
RenderFarClip 1 128
@@ -255,6 +260,7 @@ RenderAnisotropic 1 1
RenderAvatarCloth 1 1
RenderAvatarLODFactor 1 1.0
RenderAvatarPhysicsLODFactor 1 1.0
+RenderAvatarMaxNonImpostors 1 16
RenderFarClip 1 256
RenderFlexTimeFactor 1 1.0
RenderGlowResolutionPow 1 9
diff --git a/indra/newview/fsfloaterperformance.cpp b/indra/newview/fsfloaterperformance.cpp
index 0979553e30..23da5a884c 100644
--- a/indra/newview/fsfloaterperformance.cpp
+++ b/indra/newview/fsfloaterperformance.cpp
@@ -1,5 +1,5 @@
/**
- * @file llfloaterperformance.cpp
+ * @file fsfloaterperformance.cpp
*
* $LicenseInfo:firstyear=2021&license=viewerlgpl$
* Second Life Viewer Source Code
@@ -48,11 +48,12 @@
#include "llviewermediafocus.h"
#include "llvoavatar.h"
#include "llvoavatarself.h"
+#include "llperfstats.h"
#include "pipeline.h"
#include "llviewercontrol.h"
#include "fsavatarrenderpersistence.h"
#include "llpresetsmanager.h"
-#include "fsperfstats.h" // performance stats support
+#include "llwindow.h"
#include "fslslbridge.h"
#include
@@ -63,10 +64,10 @@ const S32 BAR_LEFT_PAD = 2;
const S32 BAR_RIGHT_PAD = 5;
const S32 BAR_BOTTOM_PAD = 9;
-constexpr auto AvType {FSPerfStats::ObjType_t::OT_AVATAR};
-constexpr auto AttType {FSPerfStats::ObjType_t::OT_ATTACHMENT};
-constexpr auto HudType {FSPerfStats::ObjType_t::OT_HUD};
-constexpr auto SceneType {FSPerfStats::ObjType_t::OT_GENERAL};
+constexpr auto AvType {LLPerfStats::ObjType_t::OT_AVATAR};
+constexpr auto AttType {LLPerfStats::ObjType_t::OT_ATTACHMENT};
+constexpr auto HudType {LLPerfStats::ObjType_t::OT_HUD};
+constexpr auto SceneType {LLPerfStats::ObjType_t::OT_GENERAL};
class FSExceptionsContextMenu : public LLListContextMenu
{
public:
@@ -124,7 +125,7 @@ BOOL FSFloaterPerformance::postBuild()
if (tgt_panel)
{
tgt_panel->getChild("target_btn")->setCommitCallback(boost::bind(&FSFloaterPerformance::showSelectedPanel, this, mAutoTunePanel));
- tgt_panel->getChild("FSTuningFPSStrategy")->setCurrentByIndex(gSavedSettings.getU32("FSTuningFPSStrategy"));
+ tgt_panel->getChild("FSTuningFPSStrategy")->setCurrentByIndex(gSavedSettings.getU32("TuningFPSStrategy"));
tgt_panel->getChild("PrefSaveButton")->setCommitCallback(boost::bind(&FSFloaterPerformance::savePreset, this));
tgt_panel->getChild("PrefLoadButton")->setCommitCallback(boost::bind(&FSFloaterPerformance::loadPreset, this));
tgt_panel->getChild("Defaults")->setCommitCallback(boost::bind(&FSFloaterPerformance::setHardwareDefaults, this));
@@ -159,21 +160,21 @@ BOOL FSFloaterPerformance::postBuild()
mComplexityChangedSignal = gSavedSettings.getControl("RenderAvatarMaxComplexity")->getCommitSignal()->connect(boost::bind(&FSFloaterPerformance::updateComplexityText, this));
mNearbyPanel->getChild("IndirectMaxComplexity")->setCommitCallback(boost::bind(&FSFloaterPerformance::updateMaxComplexity, this));
- mMaxARTChangedSignal = gSavedSettings.getControl("FSRenderAvatarMaxART")->getCommitSignal()->connect(boost::bind(&FSFloaterPerformance::updateMaxRenderTime, this));
- mNearbyPanel->getChild("FSRenderAvatarMaxART")->setCommitCallback(boost::bind(&FSFloaterPerformance::updateMaxRenderTime, this));
+ mMaxARTChangedSignal = gSavedSettings.getControl("RenderAvatarMaxART")->getCommitSignal()->connect(boost::bind(&FSFloaterPerformance::updateMaxRenderTime, this));
+ mNearbyPanel->getChild("RenderAvatarMaxART")->setCommitCallback(boost::bind(&FSFloaterPerformance::updateMaxRenderTime, this));
LLAvatarComplexityControls::setIndirectMaxArc();
// store the current setting as the users desired reflection detail and DD
- gSavedSettings.setS32("FSUserTargetReflections", LLPipeline::RenderReflectionDetail);
- if(!FSPerfStats::tunables.userAutoTuneEnabled)
+ gSavedSettings.setS32("UserTargetReflections", LLPipeline::RenderReflectionDetail);
+ if(!LLPerfStats::tunables.userAutoTuneEnabled)
{
if (gSavedDrawDistance)
{
- gSavedSettings.setF32("FSAutoTuneRenderFarClipTarget", gSavedDrawDistance);
+ gSavedSettings.setF32("AutoTuneRenderFarClipTarget", gSavedDrawDistance);
}
else
{
- gSavedSettings.setF32("FSAutoTuneRenderFarClipTarget", LLPipeline::RenderFarClip);
+ gSavedSettings.setF32("AutoTuneRenderFarClipTarget", LLPipeline::RenderFarClip);
}
}
@@ -182,9 +183,9 @@ BOOL FSFloaterPerformance::postBuild()
void FSFloaterPerformance::resetMaxArtSlider()
{
- FSPerfStats::renderAvatarMaxART_ns = 0;
- FSPerfStats::tunables.updateSettingsFromRenderCostLimit();
- FSPerfStats::tunables.applyUpdates();
+ LLPerfStats::renderAvatarMaxART_ns = 0;
+ LLPerfStats::tunables.updateSettingsFromRenderCostLimit();
+ LLPerfStats::tunables.applyUpdates();
updateMaxRenderTime();
}
@@ -236,8 +237,10 @@ void FSFloaterPerformance::draw()
constexpr auto NANOS = 1000000000;
static LLCachedControl fpsCap(gSavedSettings, "FramePerSecondLimit"); // user limited FPS
- static LLCachedControl targetFPS(gSavedSettings, "FSTargetFPS"); // desired FPS
- static LLCachedControl tuningStrategy(gSavedSettings, "FSTuningFPSStrategy");
+ static LLCachedControl targetFPS(gSavedSettings, "TargetFPS"); // desired FPS
+ static LLCachedControl tuningStrategy(gSavedSettings, "TuningFPSStrategy");
+ static LLCachedControl vsyncEnabled(gSavedSettings, "RenderVSyncEnable");
+
if (mUpdateTimer->hasExpired())
{
@@ -248,47 +251,47 @@ void FSFloaterPerformance::draw()
auto target_frame_time_ns = NANOS/(targetFPS==0?1:targetFPS);
- FSPerfStats::bufferToggleLock.lock(); // prevent toggle for a moment
+ LLPerfStats::bufferToggleLock.lock(); // prevent toggle for a moment
- auto tot_frame_time_raw = FSPerfStats::StatsRecorder::getSceneStat(FSPerfStats::StatType_t::RENDER_FRAME);
+ auto tot_frame_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_FRAME);
// cumulative avatar time (includes idle processing, attachments and base av)
- auto tot_avatar_time_raw = FSPerfStats::StatsRecorder::getSum(AvType, FSPerfStats::StatType_t::RENDER_COMBINED);
+ auto tot_avatar_time_raw = LLPerfStats::StatsRecorder::getSum(AvType, LLPerfStats::StatType_t::RENDER_COMBINED);
// cumulative avatar render specific time (a bit arbitrary as the processing is too.)
- // auto tot_av_idle_time_raw = FSPerfStats::StatsRecorder::getSum(AvType, FSPerfStats::StatType_t::RENDER_IDLE);
+ // auto tot_av_idle_time_raw = LLPerfStats::StatsRecorder::getSum(AvType, LLPerfStats::StatType_t::RENDER_IDLE);
// auto tot_avatar_render_time_raw = tot_avatar_time_raw - tot_av_idle_time_raw;
// the time spent this frame on the "display()" call. Treated as "tot time rendering"
- auto tot_render_time_raw = FSPerfStats::StatsRecorder::getSceneStat(FSPerfStats::StatType_t::RENDER_DISPLAY);
+ auto tot_render_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_DISPLAY);
// sleep time is basically forced sleep when window out of focus
- auto tot_sleep_time_raw = FSPerfStats::StatsRecorder::getSceneStat(FSPerfStats::StatType_t::RENDER_SLEEP);
+ auto tot_sleep_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_SLEEP);
// time spent on UI
- auto tot_ui_time_raw = FSPerfStats::StatsRecorder::getSceneStat(FSPerfStats::StatType_t::RENDER_UI);
+ auto tot_ui_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_UI);
// cumulative time spent rendering HUDS
- auto tot_huds_time_raw = FSPerfStats::StatsRecorder::getSceneStat(FSPerfStats::StatType_t::RENDER_HUDS);
+ auto tot_huds_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_HUDS);
// "idle" time. This is the time spent in the idle poll section of the main loop
- auto tot_idle_time_raw = FSPerfStats::StatsRecorder::getSceneStat(FSPerfStats::StatType_t::RENDER_IDLE);
+ auto tot_idle_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_IDLE);
// similar to sleep time, induced by FPS limit
- auto tot_limit_time_raw = FSPerfStats::StatsRecorder::getSceneStat(FSPerfStats::StatType_t::RENDER_FPSLIMIT);
+ auto tot_limit_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_FPSLIMIT);
// swap time is time spent in swap buffer
- auto tot_swap_time_raw = FSPerfStats::StatsRecorder::getSceneStat(FSPerfStats::StatType_t::RENDER_SWAP);
+ auto tot_swap_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_SWAP);
- FSPerfStats::bufferToggleLock.unlock();
+ LLPerfStats::bufferToggleLock.unlock();
auto unreliable = false; // if there is something to skew the stats such as sleep of fps cap
- auto tot_frame_time_ns = FSPerfStats::raw_to_ns(tot_frame_time_raw);
- auto tot_avatar_time_ns = FSPerfStats::raw_to_ns( tot_avatar_time_raw );
- auto tot_huds_time_ns = FSPerfStats::raw_to_ns( tot_huds_time_raw );
+ auto tot_frame_time_ns = LLPerfStats::raw_to_ns(tot_frame_time_raw);
+ auto tot_avatar_time_ns = LLPerfStats::raw_to_ns( tot_avatar_time_raw );
+ auto tot_huds_time_ns = LLPerfStats::raw_to_ns( tot_huds_time_raw );
// UI time includes HUD time so dedut that before we calc percentages
- auto tot_ui_time_ns = FSPerfStats::raw_to_ns( tot_ui_time_raw - tot_huds_time_raw);
+ auto tot_ui_time_ns = LLPerfStats::raw_to_ns( tot_ui_time_raw - tot_huds_time_raw);
- // auto tot_sleep_time_ns = FSPerfStats::raw_to_ns( tot_sleep_time_raw );
- // auto tot_limit_time_ns = FSPerfStats::raw_to_ns( tot_limit_time_raw );
+ // auto tot_sleep_time_ns = LLPerfStats::raw_to_ns( tot_sleep_time_raw );
+ // auto tot_limit_time_ns = LLPerfStats::raw_to_ns( tot_limit_time_raw );
- // auto tot_render_time_ns = FSPerfStats::raw_to_ns( tot_render_time_raw );
- auto tot_idle_time_ns = FSPerfStats::raw_to_ns( tot_idle_time_raw );
- auto tot_swap_time_ns = FSPerfStats::raw_to_ns( tot_swap_time_raw );
- auto tot_scene_time_ns = FSPerfStats::raw_to_ns( tot_render_time_raw - tot_avatar_time_raw - tot_swap_time_raw - tot_ui_time_raw);
- // auto tot_overhead_time_ns = FSPerfStats::raw_to_ns( tot_frame_time_raw - tot_render_time_raw - tot_idle_time_raw );
+ // auto tot_render_time_ns = LLPerfStats::raw_to_ns( tot_render_time_raw );
+ auto tot_idle_time_ns = LLPerfStats::raw_to_ns( tot_idle_time_raw );
+ auto tot_swap_time_ns = LLPerfStats::raw_to_ns( tot_swap_time_raw );
+ auto tot_scene_time_ns = LLPerfStats::raw_to_ns( tot_render_time_raw - tot_avatar_time_raw - tot_swap_time_raw - tot_ui_time_raw);
+ // auto tot_overhead_time_ns = LLPerfStats::raw_to_ns( tot_frame_time_raw - tot_render_time_raw - tot_idle_time_raw );
// // remove time spent sleeping for fps limit or out of focus.
// tot_frame_time_ns -= tot_limit_time_ns;
@@ -314,7 +317,13 @@ void FSFloaterPerformance::draw()
args["TOT_FRAME_TIME"] = llformat("%02u", (U32)llround(tot_frame_time_ns/1000000));
args["FPSCAP"] = llformat("%02u", (U32)fpsCap);
args["FPSTARGET"] = llformat("%02u", (U32)targetFPS);
+ S32 refresh_rate = gViewerWindow->getWindow()->getRefreshRate();
+ args["VSYNCFREQ"] = llformat("%02d", (U32)refresh_rate);
auto textbox = getChild("fps_warning");
+ // Note: the ordering of these is important.
+ // 1) background_yield should override others
+ // 2) viewer fps limits take place irrespective of vsync and so should come first.
+ // 3) vsync last.
if (tot_sleep_time_raw > 0) // We are sleeping because view is not focussed
{
textbox->setVisible(true);
@@ -329,7 +338,16 @@ void FSFloaterPerformance::draw()
textbox->setColor(LLUIColorTable::instance().getColor("DrYellow"));
unreliable = true;
}
- else if (FSPerfStats::tunables.userAutoTuneEnabled)
+ else if (vsyncEnabled)
+ {
+ textbox->setVisible(true);
+ textbox->setText(getString("max_fps", args));
+ // TODO(Beq) : When FPS is more than the frequency we can notify the user.
+ // When the FPS is lower than the frequency and also lower than the core stats then VSync might be the constraint
+ // we can notify this too. For now just display the frequency until we are sure that refresh rate is detected properly.
+ textbox->setColor(LLUIColorTable::instance().getColor("green"));
+ }
+ else if (LLPerfStats::tunables.userAutoTuneEnabled)
{
textbox->setVisible(true);
textbox->setText(getString("tuning_fps", args));
@@ -364,11 +382,11 @@ void FSFloaterPerformance::draw()
getChild("frame_breakdown")->setText(getString("frame_stats", args));
auto button = getChild("AutoTuneFPS");
- if((bool)button->getToggleState() != FSPerfStats::tunables.userAutoTuneEnabled)
+ if((bool)button->getToggleState() != LLPerfStats::tunables.userAutoTuneEnabled)
{
button->toggleState();
}
- if (FSPerfStats::tunables.userAutoTuneEnabled && !unreliable )
+ if (LLPerfStats::tunables.userAutoTuneEnabled && !unreliable )
{
// the tuning itself is managed from another thread but we can report progress here
@@ -387,7 +405,7 @@ void FSFloaterPerformance::draw()
textbox->setColor(LLUIColorTable::instance().getColor("red"));
}
}
- else if (target_frame_time_ns > (tot_frame_time_ns + FSPerfStats::renderAvatarMaxART_ns))
+ else if (target_frame_time_ns > (tot_frame_time_ns + LLPerfStats::renderAvatarMaxART_ns))
{
// if we have more time to spare. Display this (the service will update things)
textbox->setColor(LLUIColorTable::instance().getColor("green"));
@@ -459,7 +477,7 @@ void FSFloaterPerformance::populateHUDList()
max_complexity = llmax(max_complexity, (*iter).objectsCost);
}
- auto huds_max_render_time_raw = FSPerfStats::StatsRecorder::getMax(HudType, FSPerfStats::StatType_t::RENDER_GEOMETRY);
+ auto huds_max_render_time_raw = LLPerfStats::StatsRecorder::getMax(HudType, LLPerfStats::StatType_t::RENDER_GEOMETRY);
for (iter = complexity_list.begin(); iter != end; ++iter)
{
LLHUDComplexity hud_object_complexity = *iter;
@@ -469,7 +487,7 @@ void FSFloaterPerformance::populateHUDList()
continue;
}
- auto hud_render_time_raw = FSPerfStats::StatsRecorder::get(HudType, hud_object_complexity.objectId, FSPerfStats::StatType_t::RENDER_GEOMETRY);
+ auto hud_render_time_raw = LLPerfStats::StatsRecorder::get(HudType, hud_object_complexity.objectId, LLPerfStats::StatType_t::RENDER_GEOMETRY);
LLSD item;
item["special_id"] = hud_object_complexity.objectId;
@@ -485,7 +503,7 @@ void FSFloaterPerformance::populateHUDList()
row[1]["column"] = "art_value";
row[1]["type"] = "text";
- row[1]["value"] = llformat( "%.2f",FSPerfStats::raw_to_us(hud_render_time_raw) );
+ row[1]["value"] = llformat( "%.2f",LLPerfStats::raw_to_us(hud_render_time_raw) );
row[1]["font"]["name"] = "SANSSERIF";
row[2]["column"] = "name";
@@ -541,9 +559,9 @@ void FSFloaterPerformance::populateObjectList()
// for consistency we lock the buffer while we build the list. In theory this is uncontended as th ebuffer should only toggle on end of frame
{
- std::lock_guard guard{FSPerfStats::bufferToggleLock};
- auto att_max_render_time_raw = FSPerfStats::StatsRecorder::getMax(AttType, FSPerfStats::StatType_t::RENDER_COMBINED);
- auto att_sum_render_time_raw = FSPerfStats::StatsRecorder::getSum(AttType, FSPerfStats::StatType_t::RENDER_COMBINED);
+ std::lock_guard guard{LLPerfStats::bufferToggleLock};
+ auto att_max_render_time_raw = LLPerfStats::StatsRecorder::getMax(AttType, LLPerfStats::StatType_t::RENDER_COMBINED);
+ auto att_sum_render_time_raw = LLPerfStats::StatsRecorder::getSum(AttType, LLPerfStats::StatType_t::RENDER_COMBINED);
LL_DEBUGS("PerfFloater") << "Attachments for frame : " << gFrameCount << " Max:" << att_max_render_time_raw << LL_ENDL;
for (iter = attachment_list.begin(); iter != end; ++iter)
{
@@ -552,8 +570,8 @@ void FSFloaterPerformance::populateObjectList()
auto& attID{attachment_complexity.objectId};
auto& attName{attachment_complexity.objectName};
- auto attach_render_time_raw = FSPerfStats::StatsRecorder::get(AttType, attID, FSPerfStats::StatType_t::RENDER_COMBINED);
- LL_DEBUGS("PerfFloater") << "Att: " << attName << " (" << attID.asString() << ") Cost: " << FSPerfStats::raw_to_us(attach_render_time_raw) << LL_ENDL;
+ auto attach_render_time_raw = LLPerfStats::StatsRecorder::get(AttType, attID, LLPerfStats::StatType_t::RENDER_COMBINED);
+ LL_DEBUGS("PerfFloater") << "Att: " << attName << " (" << attID.asString() << ") Cost: " << LLPerfStats::raw_to_us(attach_render_time_raw) << LL_ENDL;
LLSD item;
item["special_id"] = attID;
item["target"] = LLNameListCtrl::SPECIAL;
@@ -569,7 +587,7 @@ void FSFloaterPerformance::populateObjectList()
row[1]["column"] = "art_value";
row[1]["type"] = "text";
// row[1]["value"] = std::to_string(obj_cost_short);
- row[1]["value"] = llformat( "%.2f", FSPerfStats::raw_to_us(attach_render_time_raw) );
+ row[1]["value"] = llformat( "%.2f", LLPerfStats::raw_to_us(attach_render_time_raw) );
row[1]["font"]["name"] = "SANSSERIF";
row[2]["column"] = "complex_value";
@@ -603,7 +621,7 @@ void FSFloaterPerformance::populateObjectList()
auto textbox = getChild("tot_att_count");
LLStringUtil::format_map_t args;
args["TOT_ATT"] = llformat("%d", (int64_t)attachment_list.size());
- args["TOT_ATT_TIME"] = llformat("%.2f", FSPerfStats::raw_to_us(att_sum_render_time_raw));
+ args["TOT_ATT_TIME"] = llformat("%.2f", LLPerfStats::raw_to_us(att_sum_render_time_raw));
textbox->setText(getString("tot_att_template", args));
}
@@ -615,7 +633,7 @@ void FSFloaterPerformance::populateObjectList()
void FSFloaterPerformance::populateNearbyList()
{
- static LLCachedControl showTunedART(gSavedSettings, "FSShowTunedART");
+ static LLCachedControl showTunedART(gSavedSettings, "ShowTunedART");
S32 prev_pos = mNearbyList->getScrollPos();
LLUUID prev_selected_id = mNearbyList->getStringUUIDSelectedItem();
std::string current_sort_col = mNearbyList->getSortColumnName();
@@ -635,10 +653,10 @@ void FSFloaterPerformance::populateNearbyList()
std::vector::iterator char_iter = valid_nearby_avs.begin();
- FSPerfStats::bufferToggleLock.lock();
- auto av_render_max_raw = FSPerfStats::StatsRecorder::getMax(AvType, FSPerfStats::StatType_t::RENDER_COMBINED);
- auto av_render_tot_raw = FSPerfStats::StatsRecorder::getSum(AvType, FSPerfStats::StatType_t::RENDER_COMBINED);
- FSPerfStats::bufferToggleLock.unlock();
+ LLPerfStats::bufferToggleLock.lock();
+ auto av_render_max_raw = LLPerfStats::StatsRecorder::getMax(AvType, LLPerfStats::StatType_t::RENDER_COMBINED);
+ auto av_render_tot_raw = LLPerfStats::StatsRecorder::getSum(AvType, LLPerfStats::StatType_t::RENDER_COMBINED);
+ LLPerfStats::bufferToggleLock.unlock();
// FSPlot("max ART", (int64_t)av_render_max_raw);
// FSPlot("Num av", (int64_t)valid_nearby_avs.size());
@@ -657,85 +675,128 @@ void FSFloaterPerformance::populateNearbyList()
S32 complexity_short = llmax((S32)avatar->getVisualComplexity() / 1000, 1);
- FSPerfStats::bufferToggleLock.lock();
- auto render_av_raw = FSPerfStats::StatsRecorder::get(AvType, avatar->getID(),FSPerfStats::StatType_t::RENDER_COMBINED);
- FSPerfStats::bufferToggleLock.unlock();
+ LLPerfStats::bufferToggleLock.lock();
+ auto render_av_raw = LLPerfStats::StatsRecorder::get(AvType, avatar->getID(),LLPerfStats::StatType_t::RENDER_COMBINED);
+ auto render_av_geom = LLPerfStats::StatsRecorder::get(AvType, avatar->getID(),LLPerfStats::StatType_t::RENDER_GEOMETRY);
+ auto render_av_shadow = LLPerfStats::StatsRecorder::get(AvType, avatar->getID(),LLPerfStats::StatType_t::RENDER_SHADOWS);
+ auto render_av_idle = LLPerfStats::StatsRecorder::get(AvType, avatar->getID(),LLPerfStats::StatType_t::RENDER_IDLE);
+ LLPerfStats::bufferToggleLock.unlock();
- auto is_slow = avatar->isTooSlowWithShadows();
+ auto is_slow = avatar->isTooSlow();
LLSD item;
item["id"] = avatar->getID();
LLSD& row = item["columns"];
- row[0]["column"] = "art_visual";
- row[0]["type"] = "bar";
- LLSD& value = row[0]["value"];
+ int colno = 0;
+ row[colno]["column"] = "art_visual";
+ row[colno]["type"] = "bar";
+ LLSD& value = row[colno]["value"];
// The ratio used in the bar is the current cost, as soon as we take action this changes so we keep the
// pre-tune value for the numerical column and sorting.
value["ratio"] = (double)render_av_raw / av_render_max_raw;
value["bottom"] = BAR_BOTTOM_PAD;
value["left_pad"] = BAR_LEFT_PAD;
value["right_pad"] = BAR_RIGHT_PAD;
+ colno++;
- row[1]["column"] = "art_value";
- row[1]["type"] = "text";
- if (is_slow && !showTunedART)
+ row[colno]["column"] = "art_value";
+ row[colno]["type"] = "text";
+ if (is_slow)
{
- row[1]["value"] = llformat( "%.2f", FSPerfStats::raw_to_us( avatar->getLastART() ) );
+ row[colno]["value"] = llformat( "%.2f", LLPerfStats::raw_to_us( avatar->getLastART() ) );
}
else
{
- row[1]["value"] = llformat( "%.2f", FSPerfStats::raw_to_us( render_av_raw ) );
+ row[colno]["value"] = llformat( "%.2f", LLPerfStats::raw_to_us( render_av_raw ) );
}
- row[1]["font"]["name"] = "SANSSERIF";
- row[1]["width"] = "50";
+ row[colno]["font"]["name"] = "SANSSERIF";
+ row[colno]["width"] = "50";
+ colno++;
- row[2]["column"] = "complex_value";
- row[2]["type"] = "text";
- row[2]["value"] = std::to_string(complexity_short);
- row[2]["font"]["name"] = "SANSSERIF";
- row[2]["width"] = "50";
+ if (showTunedART)
+ {
+ row[colno]["column"] = "adj_art_value";
+ row[colno]["type"] = "text";
+ if (is_slow )
+ {
+ row[colno]["value"] = llformat( "%.2f", LLPerfStats::raw_to_us( render_av_raw ) );
+ }
+ else
+ {
+ row[colno]["value"] = llformat( "--" );
+ }
+ row[colno]["font"]["name"] = "SANSSERIF";
+ row[colno]["width"] = "50";
+ colno++;
+ }
- row[3]["column"] = "state";
- row[3]["type"] = "text";
+ row[colno]["column"] = "complex_value";
+ row[colno]["type"] = "text";
+ row[colno]["value"] = std::to_string(complexity_short);
+ row[colno]["font"]["name"] = "SANSSERIF";
+ row[colno]["width"] = "50";
+
+ colno++;
+ row[colno]["column"] = "state";
+ row[colno]["type"] = "text";
if (is_slow)
{
if (avatar->isTooSlowWithoutShadows())
{
- row[3]["value"] = std::string{"I"};
+ row[colno]["value"] = std::string{"I"};
}
else
{
- row[3]["value"] = std::string{"S"};
+ row[colno]["value"] = std::string{"S"};
}
}
else
{
- row[3]["value"] = std::string{" "};
+ row[colno]["value"] = std::string{" "};
}
- row[3]["font"]["name"] = "SANSSERIF";
+ row[colno]["font"]["name"] = "SANSSERIF";
- row[4]["column"] = "name";
+ colno++;
+ row[colno]["column"] = "name";
+ colno++;
+ row[colno]["column"] = "breakdown";
+ row[colno]["type"] = "text";
+ row[colno]["value"] = llformat( "%.2f/%.2f/%.2f", LLPerfStats::raw_to_us( render_av_geom ), LLPerfStats::raw_to_us( render_av_shadow ), LLPerfStats::raw_to_us( render_av_idle ) );
+ colno++;
LLScrollListItem* av_item = mNearbyList->addElement(item);
if (av_item)
{
- LLScrollListText* art_text = dynamic_cast(av_item->getColumn(1));
+ int colno{1};
+ LLScrollListText* art_text = dynamic_cast(av_item->getColumn(colno));
if (art_text)
{
art_text->setAlignment(LLFontGL::RIGHT);
}
- LLScrollListText* value_text = dynamic_cast(av_item->getColumn(2));
+ colno++;
+ LLScrollListText* value_text = dynamic_cast(av_item->getColumn(colno));
if (value_text)
{
value_text->setAlignment(LLFontGL::RIGHT);
}
- LLScrollListText* state_text = dynamic_cast(av_item->getColumn(3));
+ colno++;
+ if (showTunedART)
+ {
+ LLScrollListText* value_text = dynamic_cast(av_item->getColumn(colno));
+ if (value_text)
+ {
+ value_text->setAlignment(LLFontGL::RIGHT);
+ }
+ colno++;
+ }
+ LLScrollListText* state_text = dynamic_cast(av_item->getColumn(colno));
if (state_text)
{
state_text->setAlignment(LLFontGL::HCENTER);
}
- LLScrollListText* name_text = dynamic_cast(av_item->getColumn(4));
+ colno++;
+ LLScrollListText* name_text = dynamic_cast(av_item->getColumn(colno));
if (name_text)
{
if (avatar->isSelf())
@@ -761,6 +822,7 @@ void FSFloaterPerformance::populateNearbyList()
name_text->setColor(LLUIColorTable::instance().getColor(color));
}
}
+ colno++;
}
}
char_iter++;
@@ -772,7 +834,7 @@ void FSFloaterPerformance::populateNearbyList()
auto textbox = getChild("tot_av_count");
LLStringUtil::format_map_t args;
args["TOT_AV"] = llformat("%d", (int64_t)valid_nearby_avs.size());
- args["TOT_AV_TIME"] = llformat("%.2f", FSPerfStats::raw_to_us(av_render_tot_raw));
+ args["TOT_AV_TIME"] = llformat("%.2f", LLPerfStats::raw_to_us(av_render_tot_raw));
textbox->setText(getString("tot_av_template", args));
}
@@ -820,7 +882,7 @@ void FSFloaterPerformance::onClickHideAvatars()
void FSFloaterPerformance::onClickFocusAvatar()
{
- FSPerfStats::StatsRecorder::setFocusAv(mNearbyCombo->getSelectedValue().asUUID());
+ LLPerfStats::StatsRecorder::setFocusAv(mNearbyCombo->getSelectedValue().asUUID());
}
void FSFloaterPerformance::onClickExceptions()
@@ -850,8 +912,8 @@ void FSFloaterPerformance::updateMaxRenderTime()
void FSFloaterPerformance::updateMaxRenderTimeText()
{
LLAvatarComplexityControls::setRenderTimeText(
- gSavedSettings.getF32("FSRenderAvatarMaxART"),
- mNearbyPanel->getChild("FSRenderAvatarMaxARTText", true),
+ gSavedSettings.getF32("RenderAvatarMaxART"),
+ mNearbyPanel->getChild("RenderAvatarMaxARTText", true),
true);
}
diff --git a/indra/newview/llagent.cpp b/indra/newview/llagent.cpp
index 6272e586bd..bda364b82d 100644
--- a/indra/newview/llagent.cpp
+++ b/indra/newview/llagent.cpp
@@ -69,6 +69,7 @@
// We don't use the mini location panel in Firestorm
// #include "llpaneltopinfobar.h"
#include "llparcel.h"
+#include "llperfstats.h"
#include "llrendersphere.h"
#include "llscriptruntimeperms.h"
#include "llsdutil.h"
@@ -4884,6 +4885,7 @@ void LLAgent::handleTeleportFinished()
mRegionp->setCapabilitiesReceivedCallback(boost::bind(&LLAgent::onCapabilitiesReceivedAfterTeleport));
}
}
+ LLPerfStats::tunables.autoTuneTimeout = true;
}
void LLAgent::handleTeleportFailed()
@@ -4915,6 +4917,8 @@ void LLAgent::handleTeleportFailed()
}
mTPNeedsNeabyChatSeparator = false;
+
+ LLPerfStats::tunables.autoTuneTimeout = true;
}
/*static*/
diff --git a/indra/newview/llappviewer.cpp b/indra/newview/llappviewer.cpp
index 093f366095..867a941154 100644
--- a/indra/newview/llappviewer.cpp
+++ b/indra/newview/llappviewer.cpp
@@ -122,6 +122,7 @@
#include "llscenemonitor.h"
#include "llavatarrenderinfoaccountant.h"
#include "lllocalbitmaps.h"
+#include "llperfstats.h"
// Linden library includes
#include "llavatarnamecache.h"
@@ -288,7 +289,6 @@ using namespace LL;
#include "fsassetblacklist.h"
// #include "fstelemetry.h" // Tracy profiler support
-#include "fsperfstats.h" // performance stats support
#if LL_LINUX && LL_GTK
#include "glib.h"
@@ -1588,131 +1588,125 @@ bool LLAppViewer::frame()
bool LLAppViewer::doFrame()
{
- LL_RECORD_BLOCK_TIME(FTM_FRAME);
-
- // Perfstats collection Frame boundary
- {
- // and now adjust the visuals from previous frame.
- if(FSPerfStats::tunables.userAutoTuneEnabled && FSPerfStats::tunables.tuningFlag != FSPerfStats::Tunables::Nothing)
+ LL_RECORD_BLOCK_TIME(FTM_FRAME);
{
- FSPerfStats::tunables.applyUpdates();
+ // and now adjust the visuals from previous frame.
+ if(LLPerfStats::tunables.userAutoTuneEnabled && LLPerfStats::tunables.tuningFlag != LLPerfStats::Tunables::Nothing)
+ {
+ LLPerfStats::tunables.applyUpdates();
}
- FSPerfStats::RecordSceneTime T (FSPerfStats::StatType_t::RENDER_FRAME);
-
+ LLPerfStats::RecordSceneTime T (LLPerfStats::StatType_t::RENDER_FRAME);
if (!LLWorld::instanceExists())
{
LLWorld::createInstance();
}
- LLEventPump& mainloop(LLEventPumps::instance().obtain("mainloop"));
- LLSD newFrame;
+ LLEventPump& mainloop(LLEventPumps::instance().obtain("mainloop"));
+ LLSD newFrame;
+ LLTimer frameTimer; // relocated - FIRE-22297: FPS limiter not working properly on Mac/Linux
+ {
+ LLPerfStats::RecordSceneTime T (LLPerfStats::StatType_t::RENDER_IDLE); // perf stats
// profiling enablement.
// This ifdef is optional but better to avoid even low overhead code in main loop where not needed.
#ifdef TRACY_ENABLE
- static bool one_time{false};
- static LLCachedControl defer_profiling(gSavedSettings, "DeferProfilingUntilConnected");
- if( !one_time && (gFrameCount % 10 == 0) )
- {
-
- // LL_INFOS() << "Profiler active: " << (LLProfiler::active?"True":"False") << LL_ENDL;
- // LL_INFOS() << "deferred_profiling: " << (defer_profiling?"True":"False") << LL_ENDL;
- // LL_INFOS() << "connected: " << (LL_PROFILE_IS_CONNECTED?"True":"False") << LL_ENDL;
-
- if( ( !LLProfiler::active ) && ( defer_profiling && LL_PROFILE_IS_CONNECTED ) )
+ static bool one_time{false};
+ static LLCachedControl defer_profiling(gSavedSettings, "DeferProfilingUntilConnected");
+ if( !one_time && (gFrameCount % 10 == 0) )
{
- LLProfiler::active = true;
- gSavedSettings.setBOOL( "ProfilingActive", LLProfiler::active );
- one_time=true; // prevent reset race if we disable manually.
- LL_INFOS() << "Profiler or collector connected" << LL_ENDL;
+
+ // LL_INFOS() << "Profiler active: " << (LLProfiler::active?"True":"False") << LL_ENDL;
+ // LL_INFOS() << "deferred_profiling: " << (defer_profiling?"True":"False") << LL_ENDL;
+ // LL_INFOS() << "connected: " << (LL_PROFILE_IS_CONNECTED?"True":"False") << LL_ENDL;
+
+ if( ( !LLProfiler::active ) && ( defer_profiling && LL_PROFILE_IS_CONNECTED ) )
+ {
+ LLProfiler::active = true;
+ gSavedSettings.setBOOL( "ProfilingActive", LLProfiler::active );
+ one_time=true; // prevent reset race if we disable manually.
+ LL_INFOS() << "Profiler or collector connected" << LL_ENDL;
+ }
+ if( !defer_profiling )
+ {
+ // no point in checking if we are not waiting.
+ // TODO(Beq): At the moment we have only two options
+ // 1) start capturing immediately
+ // 2) start capturing only when a profiler is connected
+ // Ideally we could have another flag to control profiling at start
+ // this would then allow a fully manual enablement.
+ one_time = true;
+ LL_INFOS() << "Manual profiling control selected" << LL_ENDL;
+ }
}
- if( !defer_profiling )
- {
- // no point in checking if we are not waiting.
- // TODO(Beq): At the moment we have only two options
- // 1) start capturing immediately
- // 2) start capturing only when a profiler is connected
- // Ideally we could have another flag to control profiling at start
- // this would then allow a fully manual enablement.
- one_time = true;
- LL_INFOS() << "Manual profiling control selected" << LL_ENDL;
- }
- }
#endif
//
- // FIRE-22297: FPS limiter not working properly on Mac/Linux
- LLTimer frameTimer;
- {FSPerfStats::RecordSceneTime T (FSPerfStats::StatType_t::RENDER_IDLE); // perf stats
-
nd::etw::logFrame(); // Write the start of each frame. Even if our Provider (Firestorm) would be enabled, this has only light impact. Does nothing on OSX and Linux.
- {
- LL_PROFILE_ZONE_NAMED_CATEGORY_APP("df LLTrace");
- if (LLFloaterReg::instanceVisible("block_timers"))
{
- LLTrace::BlockTimer::processTimes();
+ LL_PROFILE_ZONE_NAMED_CATEGORY_APP("df LLTrace");
+ if (LLFloaterReg::instanceVisible("block_timers"))
+ {
+ LLTrace::BlockTimer::processTimes();
+ }
+
+ LLTrace::get_frame_recording().nextPeriod();
+ LLTrace::BlockTimer::logStats();
}
-
- LLTrace::get_frame_recording().nextPeriod();
- LLTrace::BlockTimer::logStats();
- }
- LLTrace::get_thread_recorder()->pullFromChildren();
+ LLTrace::get_thread_recorder()->pullFromChildren();
- //clear call stack records
- LL_CLEAR_CALLSTACKS();
- } // perf stats (close NonRender/IDLE tracking starting at event pump)
- {
- {FSPerfStats::RecordSceneTime T (FSPerfStats::StatType_t::RENDER_IDLE); // ensure we have the entire top scope of frame covered (input event and coro)
+ //clear call stack records
+ LL_CLEAR_CALLSTACKS();
+ }
+ {
+ {
+ LLPerfStats::RecordSceneTime T(LLPerfStats::StatType_t::RENDER_IDLE); // ensure we have the entire top scope of frame covered (input event and coro)
+ LL_PROFILE_ZONE_NAMED_CATEGORY_APP("df processMiscNativeEvents");
+ pingMainloopTimeout("Main:MiscNativeWindowEvents");
- LL_PROFILE_ZONE_NAMED_CATEGORY_APP( "df processMiscNativeEvents" )
- pingMainloopTimeout("Main:MiscNativeWindowEvents");
+ if (gViewerWindow)
+ {
+ LL_RECORD_BLOCK_TIME(FTM_MESSAGES);
+ gViewerWindow->getWindow()->processMiscNativeEvents();
+ }
- if (gViewerWindow)
- {
- LL_RECORD_BLOCK_TIME(FTM_MESSAGES);
- gViewerWindow->getWindow()->processMiscNativeEvents();
- }
+ {
+ LL_PROFILE_ZONE_NAMED_CATEGORY_APP("df gatherInput")
+ pingMainloopTimeout("Main:GatherInput");
+ }
- {
- LL_PROFILE_ZONE_NAMED_CATEGORY_APP( "df gatherInput" )
- pingMainloopTimeout("Main:GatherInput");
- }
-
- if (gViewerWindow)
- {
+ if (gViewerWindow)
+ {
LL_RECORD_BLOCK_TIME(FTM_MESSAGES2);
- if (!restoreErrorTrap())
- {
- LL_WARNS() << " Someone took over my signal/exception handler (post messagehandling)!" << LL_ENDL;
- }
+ if (!restoreErrorTrap())
+ {
+ LL_WARNS() << " Someone took over my signal/exception handler (post messagehandling)!" << LL_ENDL;
+ }
- gViewerWindow->getWindow()->gatherInput();
- }
+ gViewerWindow->getWindow()->gatherInput();
+ }
- //memory leaking simulation
- if (gSimulateMemLeak)
- {
- LLFloaterMemLeak* mem_leak_instance =
- LLFloaterReg::findTypedInstance("mem_leaking");
- if (mem_leak_instance)
- {
- mem_leak_instance->idle();
- }
- }
+ //memory leaking simulation
+ if (gSimulateMemLeak)
+ {
+ LLFloaterMemLeak* mem_leak_instance =
+ LLFloaterReg::findTypedInstance("mem_leaking");
+ if (mem_leak_instance)
+ {
+ mem_leak_instance->idle();
+ }
+ }
- {
- LL_PROFILE_ZONE_NAMED_CATEGORY_APP( "df mainloop" )
- // canonical per-frame event
- mainloop.post(newFrame);
- }
- {
- LL_PROFILE_ZONE_NAMED_CATEGORY_APP( "df suspend" )
- // give listeners a chance to run
- llcoro::suspend();
- // if one of our coroutines threw an uncaught exception, rethrow it now
- LLCoros::instance().rethrow();
- }
- }// ensure we have the entire top scope of frame covered (close input event and coro "idle")
+ {
+ LL_PROFILE_ZONE_NAMED_CATEGORY_APP("df mainloop")
+ // canonical per-frame event
+ mainloop.post(newFrame);
+ }
+ {
+ LL_PROFILE_ZONE_NAMED_CATEGORY_APP("df suspend")
+ // give listeners a chance to run
+ llcoro::suspend();
+ }
+ }
if (!LLApp::isExiting())
{
@@ -1729,8 +1723,7 @@ bool LLAppViewer::doFrame()
&& (gHeadlessClient || !gViewerWindow->getShowProgress())
&& !gFocusMgr.focusLocked())
{
- FSPerfStats::RecordSceneTime T (FSPerfStats::StatType_t::RENDER_IDLE);
- LL_PROFILE_ZONE_NAMED_CATEGORY_APP( "df JoystickKeyboard" )
+ LLPerfStats::RecordSceneTime T (LLPerfStats::StatType_t::RENDER_IDLE);
joystick->scanJoystick();
gKeyboard->scanKeyboard();
gViewerInput.scanMouse();
@@ -1746,19 +1739,21 @@ bool LLAppViewer::doFrame()
// Update state based on messages, user input, object idle.
{
- LL_PROFILE_ZONE_NAMED_CATEGORY_APP( "df pauseMainloopTimeout" )
- pauseMainloopTimeout(); // *TODO: Remove. Messages shouldn't be stalling for 20+ seconds!
- }
+ {
+ LL_PROFILE_ZONE_NAMED_CATEGORY_APP( "df pauseMainloopTimeout" )
+ pauseMainloopTimeout(); // *TODO: Remove. Messages shouldn't be stalling for 20+ seconds!
+ }
- {
- FSPerfStats::RecordSceneTime T (FSPerfStats::StatType_t::RENDER_IDLE);
- LL_PROFILE_ZONE_NAMED_CATEGORY_APP("df idle"); //LL_RECORD_BLOCK_TIME(FTM_IDLE);
- idle();
- }
+ {
+ LLPerfStats::RecordSceneTime T (LLPerfStats::StatType_t::RENDER_IDLE);
+ LL_PROFILE_ZONE_NAMED_CATEGORY_APP("df idle"); //LL_RECORD_BLOCK_TIME(FTM_IDLE);
+ idle();
+ }
- {
- LL_PROFILE_ZONE_NAMED_CATEGORY_APP( "df resumeMainloopTimeout" )
- resumeMainloopTimeout();
+ {
+ LL_PROFILE_ZONE_NAMED_CATEGORY_APP( "df resumeMainloopTimeout" )
+ resumeMainloopTimeout();
+ }
}
if (gDoDisconnect && (LLStartUp::getStartupState() == STATE_STARTED))
@@ -1786,15 +1781,15 @@ bool LLAppViewer::doFrame()
display();
- {
- FSPerfStats::RecordSceneTime T(FSPerfStats::StatType_t::RENDER_IDLE);
- LL_PROFILE_ZONE_NAMED_CATEGORY_APP("df Snapshot")
- pingMainloopTimeout("Main:Snapshot");
- LLFloaterSnapshot::update(); // take snapshots
- LLFloaterSimpleOutfitSnapshot::update();
- gGLActive = FALSE;
- }
- }
+ {
+ LLPerfStats::RecordSceneTime T(LLPerfStats::StatType_t::RENDER_IDLE);
+ LL_PROFILE_ZONE_NAMED_CATEGORY_APP( "df Snapshot" )
+ pingMainloopTimeout("Main:Snapshot");
+ LLFloaterSnapshot::update(); // take snapshots
+ LLFloaterSimpleOutfitSnapshot::update();
+ gGLActive = FALSE;
+ }
+ }
}
{
@@ -1842,8 +1837,8 @@ bool LLAppViewer::doFrame()
// of equal priority on Windows
if (milliseconds_to_sleep > 0)
{
- FSPerfStats::RecordSceneTime T ( FSPerfStats::StatType_t::RENDER_SLEEP );
- ms_sleep(milliseconds_to_sleep);
+ LLPerfStats::RecordSceneTime T ( LLPerfStats::StatType_t::RENDER_SLEEP );
+ ms_sleep(milliseconds_to_sleep);
// also pause worker threads during this wait period
LLAppViewer::getTextureCache()->pause();
LLAppViewer::getImageDecodeThread()->pause();
@@ -1871,8 +1866,6 @@ bool LLAppViewer::doFrame()
// instrument image decodes
{
LL_PROFILE_ZONE_NAMED_CATEGORY_APP("updateTextureThreads");
- // FSPlot("max_time_ms",max_time);
- //
work_pending += updateTextureThreads(max_time);
} // instrument image decodes
@@ -1927,7 +1920,7 @@ bool LLAppViewer::doFrame()
if (fsLimitFramerate && LLStartUp::getStartupState() == STATE_STARTED && !gTeleportDisplay && !logoutRequestSent() && max_fps > F_APPROXIMATELY_ZERO)
{
// Sleep a while to limit frame rate.
- FSPerfStats::RecordSceneTime T ( FSPerfStats::StatType_t::RENDER_FPSLIMIT );
+ LLPerfStats::RecordSceneTime T ( LLPerfStats::StatType_t::RENDER_FPSLIMIT );
F32 min_frame_time = 1.f / (F32)max_fps;
S32 milliseconds_to_sleep = llclamp((S32)((min_frame_time - frameTimer.getElapsedTimeF64()) * 1000.f), 0, 1000);
if (milliseconds_to_sleep > 0)
@@ -1966,8 +1959,7 @@ bool LLAppViewer::doFrame()
LL_INFOS() << "Exiting main_loop" << LL_ENDL;
}
-
- }FSPerfStats::StatsRecorder::endFrame();
+ }LLPerfStats::StatsRecorder::endFrame();
LL_PROFILER_FRAME_END
return ! LLApp::isRunning();
@@ -3587,15 +3579,9 @@ void LLAppViewer::initStrings()
//
}
-//
-// This function decides whether the client machine meets the minimum requirements to
-// run in a maximized window, per the consensus of davep, boa and nyx on 3/30/2011.
-//
bool LLAppViewer::meetsRequirementsForMaximizedStart()
{
- bool maximizedOk = (LLFeatureManager::getInstance()->getGPUClass() >= GPU_CLASS_2);
-
- maximizedOk &= (gSysMemory.getPhysicalMemoryKB() >= U32Gigabytes(1));
+ bool maximizedOk = (gSysMemory.getPhysicalMemoryKB() >= U32Gigabytes(1));
return maximizedOk;
}
@@ -5857,7 +5843,7 @@ void LLAppViewer::idle()
if (!(logoutRequestSent() && hasSavedFinalSnapshot()))
{
- FSPerfStats::tunedAvatars=0; // reset the number of avatars that have been tweaked.
+ LLPerfStats::tunedAvatars=0; // reset the number of avatars that have been tweaked.
gObjectList.update(gAgent);
}
}
diff --git a/indra/newview/lldrawpool.cpp b/indra/newview/lldrawpool.cpp
index b71f322060..594cfe513d 100644
--- a/indra/newview/lldrawpool.cpp
+++ b/indra/newview/lldrawpool.cpp
@@ -52,7 +52,7 @@
#include "llglcommonfunc.h"
#include "llvoavatar.h"
#include "llviewershadermgr.h"
-#include "fsperfstats.h" // performance stats support
+#include "llperfstats.h"
S32 LLDrawPool::sNumDrawPools = 0;
@@ -392,24 +392,22 @@ void LLRenderPass::renderGroup(LLSpatialGroup* group, U32 type, U32 mask, BOOL t
{
LL_PROFILE_ZONE_SCOPED_CATEGORY_DRAWPOOL;
LLSpatialGroup::drawmap_elem_t& draw_info = group->mDrawMap[type];
-
- std::unique_ptr ratPtr{}; // Perf stats
+
+ std::unique_ptr ratPtr{}; // Perf stats
for (LLSpatialGroup::drawmap_elem_t::iterator k = draw_info.begin(); k != draw_info.end(); ++k)
{
LLDrawInfo *pparams = *k;
if (pparams)
{
- // Capture render times
- if(pparams->mFace)
- {
- LLViewerObject* vobj = pparams->mFace->getViewerObject();
- if(vobj->isAttachment())
- {
- trackAttachments( vobj, false,&ratPtr);
- }
- }
- //
- pushBatch(*pparams, mask, texture);
+ if(pparams->mFace)
+ {
+ LLViewerObject* vobj = pparams->mFace->getViewerObject();
+ if(vobj->isAttachment())
+ {
+ trackAttachments(vobj, false, &ratPtr);
+ }
+ }
+ pushBatch(*pparams, mask, texture);
}
}
}
@@ -422,22 +420,21 @@ void LLRenderPass::renderRiggedGroup(LLSpatialGroup* group, U32 type, U32 mask,
U64 lastMeshId = 0;
mask |= LLVertexBuffer::MAP_WEIGHT4;
- std::unique_ptr ratPtr{}; // Perf stats
+ std::unique_ptr ratPtr{}; // Perf stats
for (LLSpatialGroup::drawmap_elem_t::iterator k = draw_info.begin(); k != draw_info.end(); ++k)
{
LLDrawInfo* pparams = *k;
if (pparams)
{
- // Capture render times
- if(pparams->mFace)
- {
- LLViewerObject* vobj = pparams->mFace->getViewerObject();
- if(vobj->isAttachment())
- {
- trackAttachments( vobj, true ,&ratPtr);
- }
- }
- //
+ if(pparams->mFace)
+ {
+ LLViewerObject* vobj = pparams->mFace->getViewerObject();
+ if(vobj->isAttachment())
+ {
+ trackAttachments( vobj, true ,&ratPtr);
+ }
+ }
+
if (lastAvatar != pparams->mAvatar || lastMeshId != pparams->mSkinInfo->mHash)
{
uploadMatrixPalette(*pparams);
@@ -453,23 +450,21 @@ void LLRenderPass::renderRiggedGroup(LLSpatialGroup* group, U32 type, U32 mask,
void LLRenderPass::pushBatches(U32 type, U32 mask, BOOL texture, BOOL batch_textures)
{
LL_PROFILE_ZONE_SCOPED_CATEGORY_DRAWPOOL;
- std::unique_ptr ratPtr{};
+ std::unique_ptr ratPtr{};
for (LLCullResult::drawinfo_iterator i = gPipeline.beginRenderMap(type); i != gPipeline.endRenderMap(type); ++i)
{
LLDrawInfo* pparams = *i;
if (pparams)
{
- // Capture render times
- if(pparams->mFace)
- {
- LLViewerObject* vobj = pparams->mFace->getViewerObject();
- if(vobj->isAttachment())
- {
- trackAttachments( vobj, false, &ratPtr);
- }
- }
- //
- pushBatch(*pparams, mask, texture, batch_textures);
+ if(pparams->mFace)
+ {
+ LLViewerObject* vobj = pparams->mFace->getViewerObject();
+ if(vobj->isAttachment())
+ {
+ trackAttachments( vobj, false, &ratPtr);
+ }
+ }
+ pushBatch(*pparams, mask, texture, batch_textures);
}
}
}
@@ -480,22 +475,21 @@ void LLRenderPass::pushRiggedBatches(U32 type, U32 mask, BOOL texture, BOOL batc
LLVOAvatar* lastAvatar = nullptr;
U64 lastMeshId = 0;
mask |= LLVertexBuffer::MAP_WEIGHT4;
- std::unique_ptr ratPtr{}; // Perf stats
+ std::unique_ptr ratPtr{}; // Perf stats
for (LLCullResult::drawinfo_iterator i = gPipeline.beginRenderMap(type); i != gPipeline.endRenderMap(type); ++i)
{
LLDrawInfo* pparams = *i;
if (pparams)
{
- // Capture render times
- if(pparams->mFace)
- {
- LLViewerObject* vobj = pparams->mFace->getViewerObject();
- if(vobj->isAttachment())
- {
- trackAttachments( vobj, true, &ratPtr);
- }
- }
- //
+ if(pparams->mFace)
+ {
+ LLViewerObject* vobj = pparams->mFace->getViewerObject();
+ if(vobj->isAttachment())
+ {
+ trackAttachments( vobj, true, &ratPtr);
+ }
+ }
+
if (pparams->mAvatar.notNull() && (lastAvatar != pparams->mAvatar || lastMeshId != pparams->mSkinInfo->mHash))
{
uploadMatrixPalette(*pparams);
@@ -511,22 +505,20 @@ void LLRenderPass::pushRiggedBatches(U32 type, U32 mask, BOOL texture, BOOL batc
void LLRenderPass::pushMaskBatches(U32 type, U32 mask, BOOL texture, BOOL batch_textures)
{
LL_PROFILE_ZONE_SCOPED_CATEGORY_DRAWPOOL;
- std::unique_ptr ratPtr{};
+ std::unique_ptr ratPtr{};
for (LLCullResult::drawinfo_iterator i = gPipeline.beginRenderMap(type); i != gPipeline.endRenderMap(type); ++i)
{
LLDrawInfo* pparams = *i;
if (pparams)
{
- // Capture render times
- if((*pparams).mFace)
- {
- LLViewerObject* vobj = (*pparams).mFace->getViewerObject();
- if(vobj->isAttachment())
- {
- trackAttachments( vobj, false, &ratPtr);
- }
- }
- //
+ if((*pparams).mFace)
+ {
+ LLViewerObject* vobj = (*pparams).mFace->getViewerObject();
+ if(vobj->isAttachment())
+ {
+ trackAttachments( vobj, false, &ratPtr);
+ }
+ }
LLGLSLShader::sCurBoundShaderPtr->setMinimumAlpha(pparams->mAlphaMaskCutoff);
pushBatch(*pparams, mask, texture, batch_textures);
}
@@ -538,22 +530,20 @@ void LLRenderPass::pushRiggedMaskBatches(U32 type, U32 mask, BOOL texture, BOOL
LL_PROFILE_ZONE_SCOPED_CATEGORY_DRAWPOOL;
LLVOAvatar* lastAvatar = nullptr;
U64 lastMeshId = 0;
- std::unique_ptr ratPtr{};
+ std::unique_ptr ratPtr{};
for (LLCullResult::drawinfo_iterator i = gPipeline.beginRenderMap(type); i != gPipeline.endRenderMap(type); ++i)
{
LLDrawInfo* pparams = *i;
if (pparams)
{
- // Capture render times
- if((*pparams).mFace)
- {
- LLViewerObject* vobj = (*pparams).mFace->getViewerObject();
- if(vobj->isAttachment())
- {
- trackAttachments( vobj, true, &ratPtr);
- }
- }
- //
+ if((*pparams).mFace)
+ {
+ LLViewerObject* vobj = (*pparams).mFace->getViewerObject();
+ if(vobj->isAttachment())
+ {
+ trackAttachments( vobj, true, &ratPtr);
+ }
+ }
if (LLGLSLShader::sCurBoundShaderPtr)
{
LLGLSLShader::sCurBoundShaderPtr->setMinimumAlpha(pparams->mAlphaMaskCutoff);
diff --git a/indra/newview/lldrawpoolalpha.cpp b/indra/newview/lldrawpoolalpha.cpp
index 6caecb9dab..5df2a35629 100644
--- a/indra/newview/lldrawpoolalpha.cpp
+++ b/indra/newview/lldrawpoolalpha.cpp
@@ -49,7 +49,7 @@
#include "llspatialpartition.h"
#include "llglcommonfunc.h"
#include "llvoavatar.h"
-#include "fsperfstats.h" // performance stats support
+#include "llperfstats.h"
BOOL LLDrawPoolAlpha::sShowDebugAlpha = FALSE;
BOOL LLDrawPoolAlpha::sShowDebugAlphaRigged = FALSE;
@@ -346,11 +346,20 @@ void LLDrawPoolAlpha::renderAlphaHighlight(U32 mask)
{
LLSpatialGroup::drawmap_elem_t& draw_info = group->mDrawMap[LLRenderPass::PASS_ALPHA+pass]; // <-- hacky + pass to use PASS_ALPHA_RIGGED on second pass
- std::unique_ptr ratPtr{}; // Render time Stats collection
+ std::unique_ptr ratPtr{}; // Render time Stats collection
for (LLSpatialGroup::drawmap_elem_t::iterator k = draw_info.begin(); k != draw_info.end(); ++k)
{
LLDrawInfo& params = **k;
+ if(params.mFace)
+ {
+ LLViewerObject* vobj = (LLViewerObject *)params.mFace->getViewerObject();
+ if(vobj->isAttachment())
+ {
+ trackAttachments( vobj, params.mFace->isState(LLFace::RIGGED), &ratPtr );
+ }
+ }
+
if (params.mParticle)
{
continue;
@@ -543,17 +552,15 @@ void LLDrawPoolAlpha::renderRiggedEmissives(U32 mask, std::vector&
mask |= LLVertexBuffer::MAP_WEIGHT4;
- std::unique_ptr ratPtr{}; // Render time Stats collection
+ std::unique_ptr ratPtr{}; // Render time Stats collection
for (LLDrawInfo* draw : emissives)
{
- // Capture render times
- LL_PROFILE_ZONE_NAMED_CATEGORY_DRAWPOOL("Emissives");
- auto vobj = draw->mFace?draw->mFace->getViewerObject():nullptr;
- if(vobj && vobj->isAttachment())
- {
- trackAttachments( vobj, draw->mFace->isState(LLFace::RIGGED), &ratPtr );
- }
- //
+ LL_PROFILE_ZONE_NAMED_CATEGORY_DRAWPOOL("Emissives");
+ auto vobj = draw->mFace?draw->mFace->getViewerObject():nullptr;
+ if(vobj && vobj->isAttachment())
+ {
+ trackAttachments( vobj, draw->mFace->isState(LLFace::RIGGED), &ratPtr );
+ }
bool tex_setup = TexSetup(draw, false);
if (lastAvatar != draw->mAvatar || lastMeshId != draw->mSkinInfo->mHash)
@@ -628,8 +635,8 @@ void LLDrawPoolAlpha::renderAlpha(U32 mask, bool depth_only, bool rigged)
LLSpatialGroup::drawmap_elem_t& draw_info = rigged ? group->mDrawMap[LLRenderPass::PASS_ALPHA_RIGGED] : group->mDrawMap[LLRenderPass::PASS_ALPHA];
- std::unique_ptr ratPtr{}; // Render time Stats collection
- for (LLSpatialGroup::drawmap_elem_t::iterator k = draw_info.begin(); k != draw_info.end(); ++k)
+ std::unique_ptr ratPtr{}; // Render time Stats collection
+ for (LLSpatialGroup::drawmap_elem_t::iterator k = draw_info.begin(); k != draw_info.end(); ++k)
{
LLDrawInfo& params = **k;
if ((bool)params.mAvatar != rigged)
@@ -651,17 +658,15 @@ void LLDrawPoolAlpha::renderAlpha(U32 mask, bool depth_only, bool rigged)
continue;
}
- // Capture render times
- if(params.mFace)
- {
- LLViewerObject* vobj = (LLViewerObject *)params.mFace->getViewerObject();
-
- if(vobj->isAttachment())
- {
- trackAttachments( vobj, params.mFace->isState(LLFace::RIGGED), &ratPtr );
- }
- }
- //
+ if(params.mFace)
+ {
+ LLViewerObject* vobj = (LLViewerObject *)params.mFace->getViewerObject();
+
+ if(vobj->isAttachment())
+ {
+ trackAttachments( vobj, params.mFace->isState(LLFace::RIGGED), &ratPtr );
+ }
+ }
if(depth_only)
{
@@ -854,6 +859,8 @@ void LLDrawPoolAlpha::renderAlpha(U32 mask, bool depth_only, bool rigged)
ratPtr.reset(); // force the final batch to terminate to avoid double counting on the subsidiary batches for FB and Emmissives
//
+ ratPtr.reset(); // force the final batch to terminate to avoid double counting on the subsidiary batches for FB and Emmissives
+
// render emissive faces into alpha channel for bloom effects
if (!depth_only)
{
diff --git a/indra/newview/lldrawpoolavatar.cpp b/indra/newview/lldrawpoolavatar.cpp
index 5aa172e0c1..13bb10cc4e 100644
--- a/indra/newview/lldrawpoolavatar.cpp
+++ b/indra/newview/lldrawpoolavatar.cpp
@@ -52,6 +52,7 @@
#include "llviewerpartsim.h"
#include "llviewercontrol.h" // for gSavedSettings
#include "llviewertexturelist.h"
+#include "llperfstats.h"
// Add avatar hitbox debug
#include "llviewercontrol.h"
@@ -59,7 +60,6 @@
// void drawBoxOutline(const LLVector3& pos,const LLVector3& size); // llspatialpartition.cpp
//
#include "llnetmap.h"
-#include "fsperfstats.h" // performance stats support
static U32 sDataMask = LLDrawPoolAvatar::VERTEX_DATA_MASK;
@@ -389,14 +389,12 @@ void LLDrawPoolAvatar::renderShadow(S32 pass)
{
return;
}
- FSPerfStats::RecordAvatarTime T(avatarp->getID(), FSPerfStats::StatType_t::RENDER_SHADOWS);
+ LLPerfStats::RecordAvatarTime T(avatarp->getID(), LLPerfStats::StatType_t::RENDER_SHADOWS);
LLVOAvatar::AvatarOverallAppearance oa = avatarp->getOverallAppearance();
- BOOL impostor = !LLPipeline::sImpostorRender && avatarp->isImpostor();
- // no shadows if the shadows are causing this avatar to breach the limit.
- //if (impostor || (oa == LLVOAvatar::AOA_INVISIBLE))
- if (avatarp->isTooSlowWithShadows() || impostor || (oa == LLVOAvatar::AOA_INVISIBLE))
- //
+ BOOL impostor = !LLPipeline::sImpostorRender && avatarp->isImpostor();
+ // no shadows if the shadows are causing this avatar to breach the limit.
+ if (avatarp->isTooSlow() || impostor || (oa == LLVOAvatar::AOA_INVISIBLE))
{
// No shadows for impostored (including jellydolled) or invisible avs.
return;
@@ -805,7 +803,7 @@ void LLDrawPoolAvatar::renderAvatars(LLVOAvatar* single_avatar, S32 pass)
{
return;
}
- FSPerfStats::RecordAvatarTime T(avatarp->getID(), FSPerfStats::StatType_t::RENDER_GEOMETRY);
+ LLPerfStats::RecordAvatarTime T(avatarp->getID(), LLPerfStats::StatType_t::RENDER_GEOMETRY);
// Add avatar hitbox debug
static LLCachedControl render_hitbox(gSavedSettings, "DebugRenderHitboxes", false);
diff --git a/indra/newview/lldrawpoolbump.cpp b/indra/newview/lldrawpoolbump.cpp
index 7231381667..65de49dd16 100644
--- a/indra/newview/lldrawpoolbump.cpp
+++ b/indra/newview/lldrawpoolbump.cpp
@@ -49,7 +49,7 @@
#include "llspatialpartition.h"
#include "llviewershadermgr.h"
#include "llmodel.h"
-#include "fsperfstats.h" // performance stats support
+#include "llperfstats.h"
//#include "llimagebmp.h"
//#include "../tools/imdebug/imdebug.h"
@@ -548,18 +548,18 @@ void LLDrawPoolBump::renderGroup(LLSpatialGroup* group, U32 type, U32 mask, BOOL
LL_PROFILE_ZONE_SCOPED_CATEGORY_DRAWPOOL;
LLSpatialGroup::drawmap_elem_t& draw_info = group->mDrawMap[type];
- std::unique_ptr ratPtr{}; // render time capture
- for (LLSpatialGroup::drawmap_elem_t::iterator k = draw_info.begin(); k != draw_info.end(); ++k)
+ std::unique_ptr ratPtr{};
+ for (LLSpatialGroup::drawmap_elem_t::iterator k = draw_info.begin(); k != draw_info.end(); ++k)
{
LLDrawInfo& params = **k;
- // Capture render times
- LLViewerObject* vobj = (LLViewerObject *)params.mFace->getViewerObject();
- if( vobj && vobj->isAttachment() )
- {
- trackAttachments( vobj, params.mFace->isState(LLFace::RIGGED), &ratPtr );
- }
- //
+ LLViewerObject* vobj = (LLViewerObject *)params.mFace->getViewerObject();
+
+ if( vobj && vobj->isAttachment() )
+ {
+ trackAttachments( vobj, params.mFace->isState(LLFace::RIGGED), &ratPtr );
+ }
+
applyModelMatrix(params);
if (params.mGroup)
@@ -728,22 +728,20 @@ void LLDrawPoolBump::renderDeferred(S32 pass)
LLVOAvatar* avatar = nullptr;
U64 skin = 0;
- std::unique_ptr ratPtr{}; // render time capture
+ std::unique_ptr ratPtr{};
for (LLCullResult::drawinfo_iterator i = begin; i != end; ++i)
{
LLDrawInfo& params = **i;
- // Capture render times
if(params.mFace)
{
LLViewerObject* vobj = (LLViewerObject *)params.mFace->getViewerObject();
if(vobj && vobj->isAttachment())
{
- trackAttachments( vobj, params.mFace->isState(LLFace::RIGGED), &ratPtr );
+ trackAttachments( vobj, params.mFace->isState(LLFace::RIGGED), &ratPtr );
}
}
- //
LLGLSLShader::sCurBoundShaderPtr->setMinimumAlpha(params.mAlphaMaskCutoff);
LLDrawPoolBump::bindBumpMap(params, bump_channel);
@@ -1374,7 +1372,7 @@ void LLDrawPoolBump::renderBump(U32 type, U32 mask)
LLCullResult::drawinfo_iterator begin = gPipeline.beginRenderMap(type);
LLCullResult::drawinfo_iterator end = gPipeline.endRenderMap(type);
- std::unique_ptr ratPtr{}; // render time capture
+ std::unique_ptr ratPtr{};
for (LLCullResult::drawinfo_iterator i = begin; i != end; ++i)
{
LLDrawInfo& params = **i;
@@ -1390,6 +1388,16 @@ void LLDrawPoolBump::renderBump(U32 type, U32 mask)
}
//
+ if(params.mFace)
+ {
+ LLViewerObject* vobj = (LLViewerObject *)params.mFace->getViewerObject();
+
+ if( vobj && vobj->isAttachment() )
+ {
+ trackAttachments( vobj, params.mFace->isState(LLFace::RIGGED), &ratPtr );
+ }
+ }
+
if (LLDrawPoolBump::bindBumpMap(params))
{
if (mRigged)
diff --git a/indra/newview/lldrawpoolmaterials.cpp b/indra/newview/lldrawpoolmaterials.cpp
index d4539c6916..f2408a3294 100644
--- a/indra/newview/lldrawpoolmaterials.cpp
+++ b/indra/newview/lldrawpoolmaterials.cpp
@@ -32,7 +32,7 @@
#include "pipeline.h"
#include "llglcommonfunc.h"
#include "llvoavatar.h"
-#include "fsperfstats.h" // performance stats support
+#include "llperfstats.h"
S32 diffuse_channel = -1;
@@ -165,23 +165,21 @@ void LLDrawPoolMaterials::renderDeferred(S32 pass)
LLCullResult::drawinfo_iterator begin = gPipeline.beginRenderMap(type);
LLCullResult::drawinfo_iterator end = gPipeline.endRenderMap(type);
- std::unique_ptr ratPtr{}; // render time capture
- for (LLCullResult::drawinfo_iterator i = begin; i != end; ++i)
+ std::unique_ptr ratPtr{};
+ for (LLCullResult::drawinfo_iterator i = begin; i != end; ++i)
{
LLDrawInfo& params = **i;
- // Capture render times
- if(params.mFace)
- {
- LLViewerObject* vobj = (LLViewerObject *)params.mFace->getViewerObject();
-
- if( vobj && vobj->isAttachment() )
- {
- trackAttachments( vobj, params.mFace->isState(LLFace::RIGGED), &ratPtr );
- }
- }
- //
+ if(params.mFace)
+ {
+ LLViewerObject* vobj = (LLViewerObject *)params.mFace->getViewerObject();
+ if( vobj && vobj->isAttachment() )
+ {
+ trackAttachments( vobj, params.mFace->isState(LLFace::RIGGED), &ratPtr );
+ }
+ }
+
mShader->uniform4f(LLShaderMgr::SPECULAR_COLOR, params.mSpecColor.mV[0], params.mSpecColor.mV[1], params.mSpecColor.mV[2], params.mSpecColor.mV[3]);
mShader->uniform1f(LLShaderMgr::ENVIRONMENT_INTENSITY, params.mEnvIntensity);
diff --git a/indra/newview/llface.cpp b/indra/newview/llface.cpp
index 29e321cb3c..e52500ce3f 100644
--- a/indra/newview/llface.cpp
+++ b/indra/newview/llface.cpp
@@ -60,7 +60,7 @@
// [RLVa:KB] - Checked: RLVa-2.0.0
#include "rlvhandler.h"
// [/RLVa:KB]
-#include "fsperfstats.h" // performance stats support
+#include "llperfstats.h"
#if LL_LINUX
// Work-around spurious used before init warning on Vector4a
diff --git a/indra/newview/llfeaturemanager.cpp b/indra/newview/llfeaturemanager.cpp
index 0e0cf3c1a1..ba6fbf35ac 100644
--- a/indra/newview/llfeaturemanager.cpp
+++ b/indra/newview/llfeaturemanager.cpp
@@ -413,6 +413,7 @@ bool LLFeatureManager::loadGPUClass()
{
if (!gSavedSettings.getBOOL("SkipBenchmark"))
{
+ F32 class0_gbps = gSavedSettings.getF32("RenderClass0MemoryBandwidth");
//get memory bandwidth from benchmark
F32 gbps;
try
@@ -434,6 +435,14 @@ bool LLFeatureManager::loadGPUClass()
LL_WARNS("RenderInit") << "GPU benchmark failed: " << e.what() << LL_ENDL;
}
+ mGPUMemoryBandwidth = gbps;
+
+ // bias by CPU speed
+ F32 cpu_basis_mhz = gSavedSettings.getF32("RenderCPUBasis");
+ F32 cpu_mhz = (F32) gSysCPU.getMHz();
+ F32 cpu_bias = llclamp(cpu_mhz / cpu_basis_mhz, 0.5f, 1.f);
+ gbps *= cpu_bias;
+
if (gbps < 0.f)
{ //couldn't bench, use GLVersion
#if LL_DARWIN
@@ -476,23 +485,23 @@ bool LLFeatureManager::loadGPUClass()
{
mGPUClass = GPU_CLASS_1;
}
- else if (gbps <= 5.f)
+ else if (gbps <= class0_gbps)
{
mGPUClass = GPU_CLASS_0;
}
- else if (gbps <= 8.f)
+ else if (gbps <= class0_gbps*2.f)
{
mGPUClass = GPU_CLASS_1;
}
- else if (gbps <= 16.f)
+ else if (gbps <= class0_gbps*4.f)
{
mGPUClass = GPU_CLASS_2;
}
- else if (gbps <= 40.f)
+ else if (gbps <= class0_gbps*8.f)
{
mGPUClass = GPU_CLASS_3;
}
- else if (gbps <= 80.f)
+ else if (gbps <= class0_gbps*16.f)
{
mGPUClass = GPU_CLASS_4;
}
diff --git a/indra/newview/llfeaturemanager.h b/indra/newview/llfeaturemanager.h
index d9269224af..70c6c09e0d 100644
--- a/indra/newview/llfeaturemanager.h
+++ b/indra/newview/llfeaturemanager.h
@@ -111,6 +111,10 @@ public:
EGPUClass getGPUClass() { return mGPUClass; }
std::string& getGPUString() { return mGPUString; }
+
+ // get the measured GPU memory bandwidth in GB/sec
+ // may return 0 of benchmark has not been run or failed to run
+ F32 getGPUMemoryBandwidth() { return mGPUMemoryBandwidth; }
BOOL isGPUSupported() { return mGPUSupported; }
F32 getExpectedGLVersion() { return mExpectedGLVersion; }
@@ -162,6 +166,7 @@ protected:
S32 mTableVersion;
BOOL mSafe; // Reinitialize everything to the "safe" mask
EGPUClass mGPUClass;
+ F32 mGPUMemoryBandwidth = 0.f; // measured memory bandwidth of GPU in GB/second
F32 mExpectedGLVersion; //expected GL version according to gpu table
std::string mGPUString;
BOOL mGPUSupported;
diff --git a/indra/newview/llfloater360capture.cpp b/indra/newview/llfloater360capture.cpp
index 8cdf3f7bf6..0648d651d1 100644
--- a/indra/newview/llfloater360capture.cpp
+++ b/indra/newview/llfloater360capture.cpp
@@ -323,25 +323,7 @@ const std::string LLFloater360Capture::getHTMLBaseFolder()
// triggered when the 'capture' button in the UI is pressed
void LLFloater360Capture::onCapture360ImagesBtn()
{
- // FIRE-31942 Avoid CoRo that appears to never usefully yield
- // Allow option to re-enable on the off chance a low power machine can benefit
- if(gSavedSettings.getBOOL("FSUseCoRoFor360Capture"))
- {
- //
- // launch the main capture code in a coroutine so we can
- // yield/suspend at some points to give the main UI
- // thread a look-in occasionally.
- LLCoros::instance().launch("capture360cap", [this]()
- {
- capture360Images();
- });
- // FIRE-31942 Avoid CoRo that appears to never usefully yield
- }
- else
- {
- capture360Images();
- }
- //
+ capture360Images();
}
// Gets the full path name for a given JavaScript file in the HTML folder. We
@@ -702,10 +684,6 @@ void LLFloater360Capture::capture360Images()
mCaptureBtn->setEnabled(true);
mSaveLocalBtn->setEnabled(true);
- // allow the UI to update by suspending and waiting for the
- // main render loop to update the UI
- if(gSavedSettings.getBOOL("FSUseCoRoFor360Capture")) // FIRE-31942 - make apparently pointless CoRo optional (just in case)
- suspendForAFrame();
}
// once the request is made to navigate to the web page containing the code
diff --git a/indra/newview/llfloateravatarrendersettings.cpp b/indra/newview/llfloateravatarrendersettings.cpp
index 866f5c7638..d3b549258b 100644
--- a/indra/newview/llfloateravatarrendersettings.cpp
+++ b/indra/newview/llfloateravatarrendersettings.cpp
@@ -91,8 +91,6 @@ BOOL LLFloaterAvatarRenderSettings::postBuild()
LLFloater::postBuild();
mAvatarSettingsList = getChild("render_settings_list");
mAvatarSettingsList->setRightMouseDownCallback(boost::bind(&LLFloaterAvatarRenderSettings::onAvatarListRightClick, this, _1, _2, _3));
- mAvatarSettingsList->setAlternateSort();
- getChild("people_filter_input")->setCommitCallback(boost::bind(&LLFloaterAvatarRenderSettings::onFilterEdit, this, _2));
return TRUE;
}
@@ -136,37 +134,13 @@ void LLFloaterAvatarRenderSettings::updateList()
{
item_params.value = iter->first;
LLAvatarNameCache::get(iter->first, &av_name);
- if(!isHiddenRow(av_name.getCompleteName()))
- {
- item_params.columns.add().value(av_name.getCompleteName()).column("name");
- std::string setting = getString(iter->second == 1 ? "av_never_render" : "av_always_render");
- item_params.columns.add().value(setting).column("setting");
- S32 mute_date = LLRenderMuteList::getInstance()->getVisualMuteDate(iter->first);
- item_params.columns.add().value(createTimestamp(mute_date)).column("timestamp").alt_value(std::to_string(mute_date));
- mAvatarSettingsList->addNameItemRow(item_params);
- }
+ item_params.columns.add().value(av_name.getCompleteName()).column("name");
+ std::string setting = getString(iter->second == 1 ? "av_never_render" : "av_always_render");
+ item_params.columns.add().value(setting).column("setting");
+ mAvatarSettingsList->addNameItemRow(item_params);
}
}
-void LLFloaterAvatarRenderSettings::onFilterEdit(const std::string& search_string)
-{
- std::string filter_upper = search_string;
- LLStringUtil::toUpper(filter_upper);
- if (mNameFilter != filter_upper)
- {
- mNameFilter = filter_upper;
- mNeedsUpdate = true;
- }
-}
-
-bool LLFloaterAvatarRenderSettings::isHiddenRow(const std::string& av_name)
-{
- if (mNameFilter.empty()) return false;
- std::string upper_name = av_name;
- LLStringUtil::toUpper(upper_name);
- return std::string::npos == upper_name.find(mNameFilter);
-}
-
static LLVOAvatar* find_avatar(const LLUUID& id)
{
LLViewerObject *obj = gObjectList.findObject(id);
@@ -217,6 +191,10 @@ bool LLFloaterAvatarRenderSettings::isActionChecked(const LLSD& userdata, const
{
return (visual_setting == S32(LLVOAvatar::AV_RENDER_NORMALLY));
}
+ else if ("non_default" == command_name)
+ {
+ return (visual_setting != S32(LLVOAvatar::AV_RENDER_NORMALLY));
+ }
else if ("never" == command_name)
{
return (visual_setting == S32(LLVOAvatar::AV_DO_NOT_RENDER));
diff --git a/indra/newview/llfloaterimagepreview.cpp b/indra/newview/llfloaterimagepreview.cpp
index bedfd6a9f7..244e47b706 100644
--- a/indra/newview/llfloaterimagepreview.cpp
+++ b/indra/newview/llfloaterimagepreview.cpp
@@ -164,6 +164,49 @@ BOOL LLFloaterImagePreview::postBuild()
}
getChild("temp_check")->setVisible(enable_temp_uploads);
//
+
+ // detect and strip empty alpha layers from images on upload
+ getChild("ok_btn")->setCommitCallback(boost::bind(&LLFloaterImagePreview::onBtnUpload, this));
+
+ getChild("uploaded_size_text")->setTextArg("[X_RES]", llformat("%d", mRawImagep->getWidth()));
+ getChild("uploaded_size_text")->setTextArg("[Y_RES]", llformat("%d", mRawImagep->getHeight()));
+
+ mEmptyAlphaCheck = getChild("strip_alpha_check");
+
+ if (mRawImagep->getComponents() != 4)
+ {
+ getChild("image_alpha_warning")->setVisible(false);
+ getChild("uploaded_size_text")->setTextArg("[ALPHA]", getString("no_alpha"));
+ return true;
+ }
+
+ U32 imageBytes = mRawImagep->getWidth() * mRawImagep->getHeight() * 4;
+
+ U32 emptyAlphaCount = 0;
+ U8* data = mRawImagep->getData();
+ for (U32 i = 3; i < imageBytes; i += 4)
+ {
+ if (data[i] > ALPHA_EMPTY_THRESHOLD)
+ {
+ emptyAlphaCount++;
+ }
+ }
+
+ if (emptyAlphaCount > (imageBytes / 4 * ALPHA_EMPTY_THRESHOLD_RATIO))
+ {
+ getChild("image_alpha_warning")->setVisible(true);
+
+ mEmptyAlphaCheck->setCommitCallback(boost::bind(&LLFloaterImagePreview::emptyAlphaCheckboxCallback, this));
+ mEmptyAlphaCheck->setValue(true);
+ }
+ else
+ {
+ getChild("image_alpha_warning")->setVisible(false);
+ mEmptyAlphaCheck->setValue(false);
+ }
+
+ getChild("uploaded_size_text")->setTextArg("[ALPHA]", getString(mEmptyAlphaCheck->getValue() ? "no_alpha" : "with_alpha"));
+ //
}
else
{
@@ -181,47 +224,6 @@ BOOL LLFloaterImagePreview::postBuild()
// detect and strip empty alpha layers from images on upload
// getChild("ok_btn")->setCommitCallback(boost::bind(&LLFloaterNameDesc::onBtnOK, this));
- getChild("ok_btn")->setCommitCallback(boost::bind(&LLFloaterImagePreview::onBtnUpload, this));
-
- getChild("uploaded_size_text")->setTextArg("[X_RES]", llformat("%d", mRawImagep->getWidth()));
- getChild("uploaded_size_text")->setTextArg("[Y_RES]", llformat("%d", mRawImagep->getHeight()));
-
- mEmptyAlphaCheck = getChild("strip_alpha_check");
-
- if (mRawImagep->getComponents() != 4)
- {
- getChild("image_alpha_warning")->setVisible(false);
- getChild("uploaded_size_text")->setTextArg("[ALPHA]", getString("no_alpha"));
- return true;
- }
-
- U32 imageBytes = mRawImagep->getWidth() * mRawImagep->getHeight() * 4;
-
- U32 emptyAlphaCount = 0;
- U8* data = mRawImagep->getData();
- for (U32 i = 3; i < imageBytes; i += 4)
- {
- if (data[i] > ALPHA_EMPTY_THRESHOLD)
- {
- emptyAlphaCount++;
- }
- }
-
- if (emptyAlphaCount > (imageBytes / 4 * ALPHA_EMPTY_THRESHOLD_RATIO))
- {
- getChild("image_alpha_warning")->setVisible(true);
-
- mEmptyAlphaCheck->setCommitCallback(boost::bind(&LLFloaterImagePreview::emptyAlphaCheckboxCallback, this));
- mEmptyAlphaCheck->setValue(true);
- }
- else
- {
- getChild("image_alpha_warning")->setVisible(false);
- mEmptyAlphaCheck->setValue(false);
- }
-
- getChild("uploaded_size_text")->setTextArg("[ALPHA]", getString(mEmptyAlphaCheck->getValue() ? "no_alpha" : "with_alpha"));
- //
return TRUE;
}
diff --git a/indra/newview/llfloaterperformance.cpp b/indra/newview/llfloaterperformance.cpp
new file mode 100644
index 0000000000..e35fa55564
--- /dev/null
+++ b/indra/newview/llfloaterperformance.cpp
@@ -0,0 +1,699 @@
+/**
+ * @file llfloaterperformance.cpp
+ *
+ * $LicenseInfo:firstyear=2021&license=viewerlgpl$
+ * Second Life Viewer Source Code
+ * Copyright (C) 2021, 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.
+ *
+ * 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.
+ *
+ * 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
+ *
+ * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
+ * $/LicenseInfo$
+ */
+
+#include "llviewerprecompiledheaders.h"
+#include "llfloaterperformance.h"
+
+#include "llagent.h"
+#include "llagentcamera.h"
+#include "llappearancemgr.h"
+#include "llavataractions.h"
+#include "llavatarrendernotifier.h"
+#include "llcheckboxctrl.h"
+#include "llcombobox.h"
+#include "llfeaturemanager.h"
+#include "llfloaterpreference.h" // LLAvatarComplexityControls
+#include "llfloaterreg.h"
+#include "llnamelistctrl.h"
+#include "llnotificationsutil.h"
+#include "llperfstats.h"
+#include "llpresetsmanager.h"
+#include "llradiogroup.h"
+#include "llsliderctrl.h"
+#include "lltextbox.h"
+#include "lltrans.h"
+#include "llviewerobjectlist.h"
+#include "llviewerwindow.h"
+#include "llvoavatar.h"
+#include "llvoavatarself.h"
+#include "llworld.h"
+#include "pipeline.h"
+
+const F32 REFRESH_INTERVAL = 1.0f;
+const S32 BAR_LEFT_PAD = 2;
+const S32 BAR_RIGHT_PAD = 5;
+const S32 BAR_BOTTOM_PAD = 9;
+
+constexpr auto AvType {LLPerfStats::ObjType_t::OT_AVATAR};
+constexpr auto AttType {LLPerfStats::ObjType_t::OT_ATTACHMENT};
+constexpr auto HudType {LLPerfStats::ObjType_t::OT_HUD};
+
+class LLExceptionsContextMenu : public LLListContextMenu
+{
+public:
+ LLExceptionsContextMenu(LLFloaterPerformance* floater_settings)
+ : mFloaterPerformance(floater_settings)
+ {}
+protected:
+ LLContextMenu* createMenu()
+ {
+ LLUICtrl::CommitCallbackRegistry::ScopedRegistrar registrar;
+ LLUICtrl::EnableCallbackRegistry::ScopedRegistrar enable_registrar;
+ registrar.add("Settings.SetRendering", boost::bind(&LLFloaterPerformance::onCustomAction, mFloaterPerformance, _2, mUUIDs.front()));
+ enable_registrar.add("Settings.IsSelected", boost::bind(&LLFloaterPerformance::isActionChecked, mFloaterPerformance, _2, mUUIDs.front()));
+ LLContextMenu* menu = createFromFile("menu_avatar_rendering_settings.xml");
+
+ return menu;
+ }
+
+ LLFloaterPerformance* mFloaterPerformance;
+};
+
+LLFloaterPerformance::LLFloaterPerformance(const LLSD& key)
+: LLFloater(key),
+ mUpdateTimer(new LLTimer()),
+ mNearbyMaxComplexity(0)
+{
+ mContextMenu = new LLExceptionsContextMenu(this);
+}
+
+LLFloaterPerformance::~LLFloaterPerformance()
+{
+ mMaxARTChangedSignal.disconnect();
+ delete mContextMenu;
+ delete mUpdateTimer;
+}
+
+BOOL LLFloaterPerformance::postBuild()
+{
+ mMainPanel = getChild("panel_performance_main");
+ mNearbyPanel = getChild("panel_performance_nearby");
+ mComplexityPanel = getChild("panel_performance_complexity");
+ mSettingsPanel = getChild("panel_performance_preferences");
+ mHUDsPanel = getChild("panel_performance_huds");
+ mAutoadjustmentsPanel = getChild("panel_performance_autoadjustments");
+
+ getChild("nearby_subpanel")->setMouseDownCallback(boost::bind(&LLFloaterPerformance::showSelectedPanel, this, mNearbyPanel));
+ getChild("complexity_subpanel")->setMouseDownCallback(boost::bind(&LLFloaterPerformance::showSelectedPanel, this, mComplexityPanel));
+ getChild("settings_subpanel")->setMouseDownCallback(boost::bind(&LLFloaterPerformance::showSelectedPanel, this, mSettingsPanel));
+ getChild("huds_subpanel")->setMouseDownCallback(boost::bind(&LLFloaterPerformance::showSelectedPanel, this, mHUDsPanel));
+ getChild("autoadjustments_subpanel")->setMouseDownCallback(boost::bind(&LLFloaterPerformance::showSelectedPanel, this, mAutoadjustmentsPanel));
+
+ initBackBtn(mNearbyPanel);
+ initBackBtn(mComplexityPanel);
+ initBackBtn(mSettingsPanel);
+ initBackBtn(mHUDsPanel);
+ initBackBtn(mAutoadjustmentsPanel);
+
+ mHUDList = mHUDsPanel->getChild("hud_list");
+ mHUDList->setNameListType(LLNameListCtrl::SPECIAL);
+ mHUDList->setHoverIconName("StopReload_Off");
+ mHUDList->setIconClickedCallback(boost::bind(&LLFloaterPerformance::detachItem, this, _1));
+
+ mObjectList = mComplexityPanel->getChild("obj_list");
+ mObjectList->setNameListType(LLNameListCtrl::SPECIAL);
+ mObjectList->setHoverIconName("StopReload_Off");
+ mObjectList->setIconClickedCallback(boost::bind(&LLFloaterPerformance::detachItem, this, _1));
+
+ mSettingsPanel->getChild("advanced_btn")->setCommitCallback(boost::bind(&LLFloaterPerformance::onClickAdvanced, this));
+ mSettingsPanel->getChild("defaults_btn")->setCommitCallback(boost::bind(&LLFloaterPerformance::onClickDefaults, this));
+ mSettingsPanel->getChild("graphics_quality")->setCommitCallback(boost::bind(&LLFloaterPerformance::onChangeQuality, this, _2));
+ mSettingsPanel->getChild("advanced_lighting_model")->setMouseDownCallback(boost::bind(&LLFloaterPerformance::onClickAdvancedLighting, this));
+ mSettingsPanel->getChild("ShadowDetail")->setMouseDownCallback(boost::bind(&LLFloaterPerformance::onClickShadows, this));
+
+ mNearbyPanel->getChild("exceptions_btn")->setCommitCallback(boost::bind(&LLFloaterPerformance::onClickExceptions, this));
+ mNearbyPanel->getChild("hide_avatars")->setCommitCallback(boost::bind(&LLFloaterPerformance::onClickHideAvatars, this));
+ mNearbyPanel->getChild("hide_avatars")->set(!LLPipeline::hasRenderTypeControl(LLPipeline::RENDER_TYPE_AVATAR));
+ mNearbyList = mNearbyPanel->getChild("nearby_list");
+ mNearbyList->setRightMouseDownCallback(boost::bind(&LLFloaterPerformance::onAvatarListRightClick, this, _1, _2, _3));
+
+ mMaxARTChangedSignal = gSavedSettings.getControl("RenderAvatarMaxART")->getCommitSignal()->connect(boost::bind(&LLFloaterPerformance::updateMaxRenderTime, this));
+ mNearbyPanel->getChild("RenderAvatarMaxART")->setCommitCallback(boost::bind(&LLFloaterPerformance::updateMaxRenderTime, this));
+
+ // store the current setting as the users desired reflection detail and DD
+ gSavedSettings.setS32("UserTargetReflections", LLPipeline::RenderReflectionDetail);
+ if(!LLPerfStats::tunables.userAutoTuneEnabled)
+ {
+ gSavedSettings.setF32("AutoTuneRenderFarClipTarget", LLPipeline::RenderFarClip);
+ }
+
+ LLStringExplicit fps_limit(llformat("%d", gViewerWindow->getWindow()->getRefreshRate()));
+ mAutoadjustmentsPanel->getChild("vsync_desc_limit")->setTextArg("[FPS_LIMIT]", fps_limit);
+ mAutoadjustmentsPanel->getChild("display_desc")->setTextArg("[FPS_LIMIT]", fps_limit);
+ mAutoadjustmentsPanel->getChild("defaults_btn")->setCommitCallback(boost::bind(&LLFloaterPerformance::onClickDefaults, this));
+
+ mStartAutotuneBtn = mAutoadjustmentsPanel->getChild("start_autotune");
+ mStopAutotuneBtn = mAutoadjustmentsPanel->getChild("stop_autotune");
+ mStartAutotuneBtn->setCommitCallback(boost::bind(&LLFloaterPerformance::startAutotune, this));
+ mStopAutotuneBtn->setCommitCallback(boost::bind(&LLFloaterPerformance::stopAutotune, this));
+
+ gSavedPerAccountSettings.declareBOOL("HadEnabledAutoFPS", FALSE, "User had enabled AutoFPS at least once", LLControlVariable::PERSIST_ALWAYS);
+
+ return TRUE;
+}
+
+void LLFloaterPerformance::showSelectedPanel(LLPanel* selected_panel)
+{
+ hidePanels();
+ mMainPanel->setVisible(FALSE);
+ selected_panel->setVisible(TRUE);
+
+ if (mHUDsPanel == selected_panel)
+ {
+ populateHUDList();
+ }
+ else if (mNearbyPanel == selected_panel)
+ {
+ populateNearbyList();
+ }
+ else if (mComplexityPanel == selected_panel)
+ {
+ populateObjectList();
+ }
+}
+
+void LLFloaterPerformance::showAutoadjustmentsPanel()
+{
+ showSelectedPanel(mAutoadjustmentsPanel);
+}
+
+void LLFloaterPerformance::draw()
+{
+ enableAutotuneWarning();
+
+ if (mUpdateTimer->hasExpired() &&
+ !LLFloaterReg::instanceVisible("save_pref_preset", PRESETS_GRAPHIC)) // give user a chance to save the graphics settings before updating them
+ {
+ setFPSText();
+ if (mHUDsPanel->getVisible())
+ {
+ populateHUDList();
+ }
+ else if (mNearbyPanel->getVisible())
+ {
+ populateNearbyList();
+ mNearbyPanel->getChild("hide_avatars")->set(!LLPipeline::hasRenderTypeControl(LLPipeline::RENDER_TYPE_AVATAR));
+ }
+ else if (mComplexityPanel->getVisible())
+ {
+ populateObjectList();
+ }
+
+ mUpdateTimer->setTimerExpirySec(REFRESH_INTERVAL);
+ }
+ updateAutotuneCtrls(LLPerfStats::tunables.userAutoTuneEnabled);
+
+ LLFloater::draw();
+}
+
+void LLFloaterPerformance::showMainPanel()
+{
+ hidePanels();
+ mMainPanel->setVisible(TRUE);
+}
+
+void LLFloaterPerformance::hidePanels()
+{
+ mNearbyPanel->setVisible(FALSE);
+ mComplexityPanel->setVisible(FALSE);
+ mHUDsPanel->setVisible(FALSE);
+ mSettingsPanel->setVisible(FALSE);
+ mAutoadjustmentsPanel->setVisible(FALSE);
+}
+
+void LLFloaterPerformance::initBackBtn(LLPanel* panel)
+{
+ panel->getChild("back_btn")->setCommitCallback(boost::bind(&LLFloaterPerformance::showMainPanel, this));
+
+ panel->getChild("back_lbl")->setShowCursorHand(false);
+ panel->getChild("back_lbl")->setSoundFlags(LLView::MOUSE_UP);
+ panel->getChild("back_lbl")->setClickedCallback(boost::bind(&LLFloaterPerformance::showMainPanel, this));
+}
+
+void LLFloaterPerformance::populateHUDList()
+{
+ S32 prev_pos = mHUDList->getScrollPos();
+ LLUUID prev_selected_id = mHUDList->getSelectedSpecialId();
+ mHUDList->clearRows();
+ mHUDList->updateColumns(true);
+
+ hud_complexity_list_t complexity_list = LLHUDRenderNotifier::getInstance()->getHUDComplexityList();
+
+ hud_complexity_list_t::iterator iter = complexity_list.begin();
+ hud_complexity_list_t::iterator end = complexity_list.end();
+
+ auto huds_max_render_time_raw = LLPerfStats::StatsRecorder::getMax(HudType, LLPerfStats::StatType_t::RENDER_GEOMETRY);
+ for (iter = complexity_list.begin(); iter != end; ++iter)
+ {
+ LLHUDComplexity hud_object_complexity = *iter;
+
+ auto hud_render_time_raw = LLPerfStats::StatsRecorder::get(HudType, hud_object_complexity.objectId, LLPerfStats::StatType_t::RENDER_GEOMETRY);
+
+ LLSD item;
+ item["special_id"] = hud_object_complexity.objectId;
+ item["target"] = LLNameListCtrl::SPECIAL;
+ LLSD& row = item["columns"];
+ row[0]["column"] = "complex_visual";
+ row[0]["type"] = "bar";
+ LLSD& value = row[0]["value"];
+ value["ratio"] = (F32)hud_render_time_raw / huds_max_render_time_raw;
+ value["bottom"] = BAR_BOTTOM_PAD;
+ value["left_pad"] = BAR_LEFT_PAD;
+ value["right_pad"] = BAR_RIGHT_PAD;
+
+ row[1]["column"] = "complex_value";
+ row[1]["type"] = "text";
+ row[1]["value"] = llformat( "%.f", llmax(LLPerfStats::raw_to_us(hud_render_time_raw), (double)1));
+ row[1]["font"]["name"] = "SANSSERIF";
+
+ row[2]["column"] = "name";
+ row[2]["type"] = "text";
+ row[2]["value"] = hud_object_complexity.objectName;
+ row[2]["font"]["name"] = "SANSSERIF";
+
+ LLScrollListItem* obj = mHUDList->addElement(item);
+ if (obj)
+ {
+ LLScrollListText* value_text = dynamic_cast(obj->getColumn(1));
+ if (value_text)
+ {
+ value_text->setAlignment(LLFontGL::HCENTER);
+ }
+ }
+ }
+ mHUDList->sortByColumnIndex(1, FALSE);
+ mHUDList->setScrollPos(prev_pos);
+ mHUDList->selectItemBySpecialId(prev_selected_id);
+}
+
+void LLFloaterPerformance::populateObjectList()
+{
+ S32 prev_pos = mObjectList->getScrollPos();
+ LLUUID prev_selected_id = mObjectList->getSelectedSpecialId();
+ mObjectList->clearRows();
+ mObjectList->updateColumns(true);
+
+ object_complexity_list_t complexity_list = LLAvatarRenderNotifier::getInstance()->getObjectComplexityList();
+
+ object_complexity_list_t::iterator iter = complexity_list.begin();
+ object_complexity_list_t::iterator end = complexity_list.end();
+
+ // for consistency we lock the buffer while we build the list. In theory this is uncontended as the buffer should only toggle on end of frame
+ {
+ std::lock_guard guard{ LLPerfStats::bufferToggleLock };
+ auto att_max_render_time_raw = LLPerfStats::StatsRecorder::getMax(AttType, LLPerfStats::StatType_t::RENDER_COMBINED);
+
+ for (iter = complexity_list.begin(); iter != end; ++iter)
+ {
+ LLObjectComplexity object_complexity = *iter;
+
+ auto attach_render_time_raw = LLPerfStats::StatsRecorder::get(AttType, object_complexity.objectId, LLPerfStats::StatType_t::RENDER_COMBINED);
+ LLSD item;
+ item["special_id"] = object_complexity.objectId;
+ item["target"] = LLNameListCtrl::SPECIAL;
+ LLSD& row = item["columns"];
+ row[0]["column"] = "complex_visual";
+ row[0]["type"] = "bar";
+ LLSD& value = row[0]["value"];
+ value["ratio"] = ((F32)attach_render_time_raw) / att_max_render_time_raw;
+ value["bottom"] = BAR_BOTTOM_PAD;
+ value["left_pad"] = BAR_LEFT_PAD;
+ value["right_pad"] = BAR_RIGHT_PAD;
+
+ row[1]["column"] = "complex_value";
+ row[1]["type"] = "text";
+ row[1]["value"] = llformat("%.f", llmax(LLPerfStats::raw_to_us(attach_render_time_raw), (double)1));
+ row[1]["font"]["name"] = "SANSSERIF";
+
+ row[2]["column"] = "name";
+ row[2]["type"] = "text";
+ row[2]["value"] = object_complexity.objectName;
+ row[2]["font"]["name"] = "SANSSERIF";
+
+ LLScrollListItem* obj = mObjectList->addElement(item);
+ if (obj)
+ {
+ LLScrollListText* value_text = dynamic_cast(obj->getColumn(1));
+ if (value_text)
+ {
+ value_text->setAlignment(LLFontGL::HCENTER);
+ }
+ }
+ }
+ }
+ mObjectList->sortByColumnIndex(1, FALSE);
+ mObjectList->setScrollPos(prev_pos);
+ mObjectList->selectItemBySpecialId(prev_selected_id);
+}
+
+void LLFloaterPerformance::populateNearbyList()
+{
+ static LLCachedControl showTunedART(gSavedSettings, "ShowTunedART");
+ S32 prev_pos = mNearbyList->getScrollPos();
+ LLUUID prev_selected_id = mNearbyList->getStringUUIDSelectedItem();
+ mNearbyList->clearRows();
+ mNearbyList->updateColumns(true);
+
+ static LLCachedControl max_render_cost(gSavedSettings, "RenderAvatarMaxComplexity", 0);
+ std::vector valid_nearby_avs;
+ mNearbyMaxComplexity = LLWorld::getInstance()->getNearbyAvatarsAndCompl(valid_nearby_avs);
+
+ std::vector::iterator char_iter = valid_nearby_avs.begin();
+
+ LLPerfStats::bufferToggleLock.lock();
+ auto av_render_max_raw = LLPerfStats::StatsRecorder::getMax(AvType, LLPerfStats::StatType_t::RENDER_COMBINED);
+ LLPerfStats::bufferToggleLock.unlock();
+
+ while (char_iter != valid_nearby_avs.end())
+ {
+ LLVOAvatar* avatar = dynamic_cast(*char_iter);
+ if (avatar && (LLVOAvatar::AOA_INVISIBLE != avatar->getOverallAppearance()))
+ {
+ LLPerfStats::bufferToggleLock.lock();
+ auto render_av_raw = LLPerfStats::StatsRecorder::get(AvType, avatar->getID(),LLPerfStats::StatType_t::RENDER_COMBINED);
+ LLPerfStats::bufferToggleLock.unlock();
+
+ auto is_slow = avatar->isTooSlow();
+ LLSD item;
+ item["id"] = avatar->getID();
+ LLSD& row = item["columns"];
+ row[0]["column"] = "complex_visual";
+ row[0]["type"] = "bar";
+ LLSD& value = row[0]["value"];
+ // The ratio used in the bar is the current cost, as soon as we take action this changes so we keep the
+ // pre-tune value for the numerical column and sorting.
+ value["ratio"] = (double)render_av_raw / av_render_max_raw;
+ value["bottom"] = BAR_BOTTOM_PAD;
+ value["left_pad"] = BAR_LEFT_PAD;
+ value["right_pad"] = BAR_RIGHT_PAD;
+
+ row[1]["column"] = "complex_value";
+ row[1]["type"] = "text";
+ if (is_slow && !showTunedART)
+ {
+ row[1]["value"] = llformat( "%.f", LLPerfStats::raw_to_us( avatar->getLastART() ) );
+ }
+ else
+ {
+ row[1]["value"] = llformat( "%.f", LLPerfStats::raw_to_us( render_av_raw ) );
+ }
+ row[1]["font"]["name"] = "SANSSERIF";
+
+ row[2]["column"] = "name";
+ row[2]["type"] = "text";
+ row[2]["value"] = avatar->getFullname();
+ row[2]["font"]["name"] = "SANSSERIF";
+
+ LLScrollListItem* av_item = mNearbyList->addElement(item);
+ if(av_item)
+ {
+ LLScrollListText* value_text = dynamic_cast(av_item->getColumn(1));
+ if (value_text)
+ {
+ value_text->setAlignment(LLFontGL::HCENTER);
+ }
+ LLScrollListText* name_text = dynamic_cast(av_item->getColumn(2));
+ if (name_text)
+ {
+ if (avatar->isSelf())
+ {
+ name_text->setColor(LLUIColorTable::instance().getColor("DrYellow"));
+ }
+ else
+ {
+ std::string color = "white";
+ if (is_slow || LLVOAvatar::AOA_JELLYDOLL == avatar->getOverallAppearance())
+ {
+ color = "LabelDisabledColor";
+ LLScrollListBar* bar = dynamic_cast(av_item->getColumn(0));
+ if (bar)
+ {
+ bar->setColor(LLUIColorTable::instance().getColor(color));
+ }
+ }
+ else if (LLVOAvatar::AOA_NORMAL == avatar->getOverallAppearance())
+ {
+ color = LLAvatarActions::isFriend(avatar->getID()) ? "ConversationFriendColor" : "white";
+ }
+ name_text->setColor(LLUIColorTable::instance().getColor(color));
+ }
+ }
+ }
+ }
+ char_iter++;
+ }
+ mNearbyList->sortByColumnIndex(1, FALSE);
+ mNearbyList->setScrollPos(prev_pos);
+ mNearbyList->selectByID(prev_selected_id);
+}
+
+void LLFloaterPerformance::setFPSText()
+{
+ const S32 NUM_PERIODS = 50;
+ S32 current_fps = (S32)llround(LLTrace::get_frame_recording().getPeriodMedianPerSec(LLStatViewer::FPS, NUM_PERIODS));
+ getChild("fps_value")->setValue(current_fps);
+
+ std::string fps_text = getString("fps_text");
+ static LLCachedControl vsync_enabled(gSavedSettings, "RenderVSyncEnable", true);
+ S32 refresh_rate = gViewerWindow->getWindow()->getRefreshRate();
+ if (vsync_enabled && (refresh_rate > 0) && (current_fps >= refresh_rate))
+ {
+ fps_text += getString("max_text");
+ }
+ getChild("fps_lbl")->setValue(fps_text);
+}
+
+void LLFloaterPerformance::detachItem(const LLUUID& item_id)
+{
+ LLAppearanceMgr::instance().removeItemFromAvatar(item_id);
+}
+
+void LLFloaterPerformance::onClickAdvanced()
+{
+ LLFloaterPreference* instance = LLFloaterReg::getTypedInstance("preferences");
+ if (instance)
+ {
+ instance->saveSettings();
+ }
+ LLFloaterReg::showInstance("prefs_graphics_advanced");
+}
+
+void LLFloaterPerformance::onClickDefaults()
+{
+ LLFloaterPreference* instance = LLFloaterReg::getTypedInstance("preferences");
+ if (instance)
+ {
+ instance->setRecommendedSettings();
+ }
+}
+
+void LLFloaterPerformance::onChangeQuality(const LLSD& data)
+{
+ LLFloaterPreference* instance = LLFloaterReg::getTypedInstance("preferences");
+ if (instance)
+ {
+ instance->onChangeQuality(data);
+ }
+}
+
+void LLFloaterPerformance::onClickHideAvatars()
+{
+ LLPipeline::toggleRenderTypeControl(LLPipeline::RENDER_TYPE_AVATAR);
+}
+
+void LLFloaterPerformance::onClickExceptions()
+{
+ LLFloaterReg::showInstance("avatar_render_settings");
+}
+
+void LLFloaterPerformance::updateMaxRenderTime()
+{
+ LLAvatarComplexityControls::updateMaxRenderTime(
+ mNearbyPanel->getChild("RenderAvatarMaxART"),
+ mNearbyPanel->getChild("RenderAvatarMaxARTText"),
+ true);
+}
+
+static LLVOAvatar* find_avatar(const LLUUID& id)
+{
+ LLViewerObject *obj = gObjectList.findObject(id);
+ while (obj && obj->isAttachment())
+ {
+ obj = (LLViewerObject *)obj->getParent();
+ }
+
+ if (obj && obj->isAvatar())
+ {
+ return (LLVOAvatar*)obj;
+ }
+ else
+ {
+ return NULL;
+ }
+}
+
+void LLFloaterPerformance::onCustomAction(const LLSD& userdata, const LLUUID& av_id)
+{
+ const std::string command_name = userdata.asString();
+
+ S32 new_setting = 0;
+ if ("default" == command_name)
+ {
+ new_setting = S32(LLVOAvatar::AV_RENDER_NORMALLY);
+ }
+ else if ("never" == command_name)
+ {
+ new_setting = S32(LLVOAvatar::AV_DO_NOT_RENDER);
+ }
+ else if ("always" == command_name)
+ {
+ new_setting = S32(LLVOAvatar::AV_ALWAYS_RENDER);
+ }
+
+ LLVOAvatar *avatarp = find_avatar(av_id);
+ if (avatarp)
+ {
+ avatarp->setVisualMuteSettings(LLVOAvatar::VisualMuteSettings(new_setting));
+ }
+ else
+ {
+ LLRenderMuteList::getInstance()->saveVisualMuteSetting(av_id, new_setting);
+ }
+}
+
+
+bool LLFloaterPerformance::isActionChecked(const LLSD& userdata, const LLUUID& av_id)
+{
+ const std::string command_name = userdata.asString();
+
+ S32 visual_setting = LLRenderMuteList::getInstance()->getSavedVisualMuteSetting(av_id);
+ if ("default" == command_name)
+ {
+ return (visual_setting == S32(LLVOAvatar::AV_RENDER_NORMALLY));
+ }
+ else if ("non_default" == command_name)
+ {
+ return (visual_setting != S32(LLVOAvatar::AV_RENDER_NORMALLY));
+ }
+ else if ("never" == command_name)
+ {
+ return (visual_setting == S32(LLVOAvatar::AV_DO_NOT_RENDER));
+ }
+ else if ("always" == command_name)
+ {
+ return (visual_setting == S32(LLVOAvatar::AV_ALWAYS_RENDER));
+ }
+ return false;
+}
+
+void LLFloaterPerformance::onAvatarListRightClick(LLUICtrl* ctrl, S32 x, S32 y)
+{
+ LLNameListCtrl* list = dynamic_cast(ctrl);
+ if (!list) return;
+ list->selectItemAt(x, y, MASK_NONE);
+ uuid_vec_t selected_uuids;
+
+ if((list->getCurrentID().notNull()) && (list->getCurrentID() != gAgentID))
+ {
+ selected_uuids.push_back(list->getCurrentID());
+ mContextMenu->show(ctrl, selected_uuids, x, y);
+ }
+}
+
+const U32 RENDER_QUALITY_LEVEL = 3;
+void LLFloaterPerformance::changeQualityLevel(const std::string& notif)
+{
+ LLNotificationsUtil::add(notif, LLSD(), LLSD(),
+ [](const LLSD¬if, const LLSD&resp)
+ {
+ S32 opt = LLNotificationsUtil::getSelectedOption(notif, resp);
+ if (opt == 0)
+ {
+ LLFloaterPreference* instance = LLFloaterReg::getTypedInstance("preferences");
+ if (instance)
+ {
+ gSavedSettings.setU32("RenderQualityPerformance", RENDER_QUALITY_LEVEL);
+ instance->onChangeQuality(LLSD((S32)RENDER_QUALITY_LEVEL));
+ }
+ }
+ });
+}
+
+bool is_ALM_available()
+{
+ bool bumpshiny = gGLManager.mHasCubeMap && LLCubeMap::sUseCubeMaps && LLFeatureManager::getInstance()->isFeatureAvailable("RenderObjectBump") && gSavedSettings.getBOOL("RenderObjectBump");
+ bool shaders = gSavedSettings.getBOOL("WindLightUseAtmosShaders");
+
+ return LLFeatureManager::getInstance()->isFeatureAvailable("RenderDeferred") &&
+ bumpshiny &&
+ shaders;
+}
+
+void LLFloaterPerformance::onClickAdvancedLighting()
+{
+ if (!is_ALM_available())
+ {
+ changeQualityLevel("AdvancedLightingConfirm");
+ }
+}
+
+void LLFloaterPerformance::onClickShadows()
+{
+ if (!is_ALM_available() || !gSavedSettings.getBOOL("RenderDeferred"))
+ {
+ changeQualityLevel("ShadowsConfirm");
+ }
+
+}
+
+void LLFloaterPerformance::startAutotune()
+{
+ LLPerfStats::tunables.userAutoTuneEnabled = true;
+}
+
+void LLFloaterPerformance::stopAutotune()
+{
+ LLPerfStats::tunables.userAutoTuneEnabled = false;
+}
+
+void LLFloaterPerformance::updateAutotuneCtrls(bool autotune_enabled)
+{
+ static LLCachedControl auto_tune_locked(gSavedSettings, "AutoTuneLock");
+ mStartAutotuneBtn->setEnabled(!autotune_enabled && !auto_tune_locked);
+ mStopAutotuneBtn->setEnabled(autotune_enabled && !auto_tune_locked);
+ getChild("AutoTuneContinuous")->setEnabled(!autotune_enabled || (autotune_enabled && auto_tune_locked));
+
+ getChild("wip_desc")->setVisible(autotune_enabled && !auto_tune_locked);
+ getChild("display_desc")->setVisible(LLPerfStats::tunables.vsyncEnabled);
+}
+
+void LLFloaterPerformance::enableAutotuneWarning()
+{
+ if (!gSavedPerAccountSettings.getBOOL("HadEnabledAutoFPS") && LLPerfStats::tunables.userAutoTuneEnabled)
+ {
+ gSavedPerAccountSettings.setBOOL("HadEnabledAutoFPS", TRUE);
+
+ LLNotificationsUtil::add("EnableAutoFPSWarning", LLSD(), LLSD(),
+ [](const LLSD& notif, const LLSD& resp)
+ {
+ S32 opt = LLNotificationsUtil::getSelectedOption(notif, resp);
+ if (opt == 0)
+ { // offer user to save current graphics settings as a preset
+ LLFloaterReg::showInstance("save_pref_preset", PRESETS_GRAPHIC);
+ }
+ });
+ }
+}
+// EOF
diff --git a/indra/newview/llfloaterperformance.h b/indra/newview/llfloaterperformance.h
new file mode 100644
index 0000000000..00f904f6d6
--- /dev/null
+++ b/indra/newview/llfloaterperformance.h
@@ -0,0 +1,102 @@
+/**
+ * @file llfloaterperformance.h
+ *
+ * $LicenseInfo:firstyear=2021&license=viewerlgpl$
+ * Second Life Viewer Source Code
+ * Copyright (C) 2021, 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.
+ *
+ * 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.
+ *
+ * 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
+ *
+ * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
+ * $/LicenseInfo$
+ */
+
+#ifndef LL_LLFLOATERPERFORMANCE_H
+#define LL_LLFLOATERPERFORMANCE_H
+
+#include "llfloater.h"
+#include "lllistcontextmenu.h"
+
+class LLCharacter;
+class LLNameListCtrl;
+
+class LLFloaterPerformance : public LLFloater
+{
+public:
+ LLFloaterPerformance(const LLSD& key);
+ virtual ~LLFloaterPerformance();
+
+ /*virtual*/ BOOL postBuild();
+ /*virtual*/ void draw();
+
+ void showSelectedPanel(LLPanel* selected_panel);
+ void showMainPanel();
+ void hidePanels();
+ void showAutoadjustmentsPanel();
+
+ void detachItem(const LLUUID& item_id);
+
+ void onAvatarListRightClick(LLUICtrl* ctrl, S32 x, S32 y);
+
+ void onCustomAction (const LLSD& userdata, const LLUUID& av_id);
+ bool isActionChecked(const LLSD& userdata, const LLUUID& av_id);
+
+private:
+ void initBackBtn(LLPanel* panel);
+ void populateHUDList();
+ void populateObjectList();
+ void populateNearbyList();
+ void setFPSText();
+
+ void onClickAdvanced();
+ void onClickDefaults();
+ void onChangeQuality(const LLSD& data);
+ void onClickHideAvatars();
+ void onClickExceptions();
+ void onClickShadows();
+ void onClickAdvancedLighting();
+
+ void startAutotune();
+ void stopAutotune();
+ void updateAutotuneCtrls(bool autotune_enabled);
+ void enableAutotuneWarning();
+
+ void updateMaxRenderTime();
+
+ static void changeQualityLevel(const std::string& notif);
+
+ LLPanel* mMainPanel;
+ LLPanel* mNearbyPanel;
+ LLPanel* mComplexityPanel;
+ LLPanel* mHUDsPanel;
+ LLPanel* mSettingsPanel;
+ LLPanel* mAutoadjustmentsPanel;
+ LLNameListCtrl* mHUDList;
+ LLNameListCtrl* mObjectList;
+ LLNameListCtrl* mNearbyList;
+
+ LLButton* mStartAutotuneBtn;
+ LLButton* mStopAutotuneBtn;
+
+ LLListContextMenu* mContextMenu;
+
+ LLTimer* mUpdateTimer;
+
+ S32 mNearbyMaxComplexity;
+
+ boost::signals2::connection mMaxARTChangedSignal;
+};
+
+#endif // LL_LLFLOATERPERFORMANCE_H
diff --git a/indra/newview/llfloaterpreference.cpp b/indra/newview/llfloaterpreference.cpp
index 13e5e45068..aef117941e 100644
--- a/indra/newview/llfloaterpreference.cpp
+++ b/indra/newview/llfloaterpreference.cpp
@@ -54,6 +54,7 @@
#include "llfloaterabout.h"
#include "llfavoritesbar.h"
#include "llfloaterpreferencesgraphicsadvanced.h"
+#include "llfloaterperformance.h"
#include "llfloatersidepanelcontainer.h"
// [FS communication UI]
//#include "llfloaterimsession.h"
@@ -128,6 +129,7 @@
#include "llpresetsmanager.h"
#include "llsearchableui.h"
+#include "llperfstats.h"
// Firestorm Includes
#include "exogroupmutelist.h"
@@ -165,8 +167,6 @@
#endif
//
-#include "fsperfstats.h"// perfstats
-
// FIRE-19539 - Include the alert messages in Prefs>Notifications>Alerts in preference Search.
#include "llfiltereditor.h"
#include "llviewershadermgr.h"
@@ -468,6 +468,7 @@ LLFloaterPreference::LLFloaterPreference(const LLSD& key)
//
mCommitCallbackRegistrar.add("Pref.LogPath", boost::bind(&LLFloaterPreference::onClickLogPath, this));
mCommitCallbackRegistrar.add("Pref.RenderExceptions", boost::bind(&LLFloaterPreference::onClickRenderExceptions, this));
+ // mCommitCallbackRegistrar.add("Pref.AutoAdjustments", boost::bind(&LLFloaterPreference::onClickAutoAdjustments, this)); // Not required in FS at present
mCommitCallbackRegistrar.add("Pref.HardwareDefaults", boost::bind(&LLFloaterPreference::setHardwareDefaults, this));
mCommitCallbackRegistrar.add("Pref.AvatarImpostorsEnable", boost::bind(&LLFloaterPreference::onAvatarImpostorsEnable, this));
mCommitCallbackRegistrar.add("Pref.UpdateIndirectMaxComplexity", boost::bind(&LLFloaterPreference::updateMaxComplexity, this));
@@ -505,6 +506,7 @@ LLFloaterPreference::LLFloaterPreference(const LLSD& key)
gSavedSettings.getControl("UseDisplayNames")->getCommitSignal()->connect(boost::bind(&handleDisplayNamesOptionChanged, _2));
gSavedSettings.getControl("AppearanceCameraMovement")->getCommitSignal()->connect(boost::bind(&handleAppearanceCameraMovementChanged, _2));
+ gSavedSettings.getControl("WindLightUseAtmosShaders")->getCommitSignal()->connect(boost::bind(&LLFloaterPreference::onAtmosShaderChange, this));
LLAvatarPropertiesProcessor::getInstance()->addObserver( gAgent.getID(), this );
@@ -1234,17 +1236,18 @@ void LLFloaterPreference::onOpen(const LLSD& key)
// FIRE-19810: Make presets global since PresetGraphicActive setting is global as well
//bool started = (LLStartUp::getStartupState() == STATE_STARTED);
-
- //LLButton* load_btn = findChild("PrefLoadButton");
+ //LLButton* load_btn = findChild("PrefLoadButton");
//LLButton* save_btn = findChild("PrefSaveButton");
//LLButton* delete_btn = findChild("PrefDeleteButton");
//LLButton* exceptions_btn = findChild("RenderExceptionsButton");
- //if (load_btn && save_btn && delete_btn && exceptions_btn)
+ // LLButton* auto_adjustments_btn = findChild("AutoAdjustmentsButton");
+ //if (load_btn && save_btn && delete_btn && exceptions_btn && auto_adjustments_btn)
//{
// load_btn->setEnabled(started);
// save_btn->setEnabled(started);
// delete_btn->setEnabled(started);
// exceptions_btn->setEnabled(started);
+ // auto_adjustments_btn->setEnabled(started);
//}
//
collectSearchableItems();
@@ -1257,6 +1260,7 @@ void LLFloaterPreference::onOpen(const LLSD& key)
if (!tabcontainer->selectTab(gSavedSettings.getS32("LastPrefTab")))
tabcontainer->selectFirstTab();
//
+
}
// Support for tab/subtab links like:
// secondlife:///app/openfloater/preferences?tab=backup
@@ -1375,6 +1379,13 @@ void LLFloaterPreference::setHardwareDefaults()
// saveSettings(); // save here to be able to return to the previous preset by Cancel
//}
//
+ setRecommendedSettings();
+}
+
+void LLFloaterPreference::setRecommendedSettings()
+{
+ resetAutotuneSettings();
+ gSavedSettings.getControl("RenderVSyncEnable")->resetToDefault(true);
LLFeatureManager::getInstance()->applyRecommendedSettings();
@@ -1399,6 +1410,28 @@ void LLFloaterPreference::setHardwareDefaults()
}
}
+void LLFloaterPreference::resetAutotuneSettings()
+{
+ gSavedSettings.setBOOL("AutoTuneFPS", FALSE);
+
+ const std::string autotune_settings[] = {
+ "AutoTuneLock",
+ "KeepAutoTuneLock",
+ "TargetFPS",
+ "TuningFPSStrategy",
+ "AutoTuneImpostorByDistEnabled",
+ "AutoTuneImpostorFarAwayDistance" ,
+ "AutoTuneRenderFarClipMin",
+ "AutoTuneRenderFarClipTarget",
+ "RenderAvatarMaxART"
+ };
+
+ for (auto it : autotune_settings)
+ {
+ gSavedSettings.getControl(it)->resetToDefault(true);
+ }
+}
+
void LLFloaterPreference::getControlNames(std::vector& names)
{
LLView* view = findChild("display");
@@ -2853,24 +2886,23 @@ void LLAvatarComplexityControls::setText(U32 value, LLTextBox* text_box, bool sh
}
}
-// redner time controls
void LLAvatarComplexityControls::updateMaxRenderTime(LLSliderCtrl* slider, LLTextBox* value_label, bool short_val)
{
- setRenderTimeText((F32)(FSPerfStats::renderAvatarMaxART_ns/1000), value_label, short_val);
+ setRenderTimeText((F32)(LLPerfStats::renderAvatarMaxART_ns/1000), value_label, short_val);
}
void LLAvatarComplexityControls::setRenderTimeText(F32 value, LLTextBox* text_box, bool short_val)
{
- if (0 == value)
- {
- text_box->setText(LLTrans::getString("no_limit"));
- }
- else
- {
- text_box->setText(llformat("%.0f", value));
- }
+ if (0 == value)
+ {
+ text_box->setText(LLTrans::getString("no_limit"));
+ }
+ else
+ {
+ text_box->setText(llformat("%.0f", value));
+ }
}
-//
+
void LLFloaterPreference::updateMaxComplexity()
{
// Called when the IndirectMaxComplexity control changes
@@ -3034,6 +3066,17 @@ void LLFloaterPreference::onClickRenderExceptions()
LLFloaterReg::showInstance("avatar_render_settings");
}
+// Not currently used in FS
+// void LLFloaterPreference::onClickAutoAdjustments()
+// {
+// LLFloaterPerformance* performance_floater = LLFloaterReg::showTypedInstance("performance");
+// if (performance_floater)
+// {
+// performance_floater->showAutoadjustmentsPanel();
+// }
+// }
+//
+
void LLFloaterPreference::onClickAdvanced()
{
LLFloaterReg::showInstance("prefs_graphics_advanced");
@@ -3056,6 +3099,22 @@ void LLFloaterPreference::onClickActionChange()
updateClickActionControls();
}
+void LLFloaterPreference::onAtmosShaderChange()
+{
+ LLCheckBoxCtrl* ctrl_alm = getChild("UseLightShaders");
+ if(ctrl_alm)
+ {
+ //Deferred/SSAO/Shadows
+ BOOL bumpshiny = gGLManager.mHasCubeMap && LLCubeMap::sUseCubeMaps && LLFeatureManager::getInstance()->isFeatureAvailable("RenderObjectBump") && gSavedSettings.getBOOL("RenderObjectBump");
+ BOOL shaders = gSavedSettings.getBOOL("WindLightUseAtmosShaders");
+ BOOL enabled = LLFeatureManager::getInstance()->isFeatureAvailable("RenderDeferred") &&
+ bumpshiny &&
+ shaders;
+
+ ctrl_alm->setEnabled(enabled);
+ }
+}
+
void LLFloaterPreference::onClickPermsDefault()
{
LLFloaterReg::showInstance("perms_default");
diff --git a/indra/newview/llfloaterpreference.h b/indra/newview/llfloaterpreference.h
index 6aeaeb7af3..726ee89daa 100644
--- a/indra/newview/llfloaterpreference.h
+++ b/indra/newview/llfloaterpreference.h
@@ -158,6 +158,8 @@ protected:
// updates click/double-click action keybindngs depending on view values
void updateClickActionControls();
+ void onAtmosShaderChange();
+
// updates UI Sounds controls depending on values from settings.xml
void updateUISoundsControls();
@@ -276,6 +278,7 @@ public:
void onClickAutoReplace();
void onClickSpellChecker();
void onClickRenderExceptions();
+ void onClickAutoAdjustments();
void onClickAdvanced();
void applyUIColor(LLUICtrl* ctrl, const LLSD& param);
void getUIColor(LLUICtrl* ctrl, const LLSD& param);
@@ -296,6 +299,9 @@ public:
// Support preferences search SLURLs
void onCopySearch();
+ void setRecommendedSettings();
+ void resetAutotuneSettings();
+
private:
void onDeleteTranscripts();
@@ -487,10 +493,8 @@ class LLAvatarComplexityControls
public:
static void updateMax(LLSliderCtrl* slider, LLTextBox* value_label, bool short_val = false);
static void setText(U32 value, LLTextBox* text_box, bool short_val = false);
- // for render time support
static void updateMaxRenderTime(LLSliderCtrl* slider, LLTextBox* value_label, bool short_val = false);
- static void setRenderTimeText(F32 value, LLTextBox* text_box, bool short_val = false);
- //
+ static void setRenderTimeText(F32 value, LLTextBox* text_box, bool short_val = false);
static void setIndirectControls();
static void setIndirectMaxNonImpostors();
static void setIndirectMaxArc();
diff --git a/indra/newview/llfloaterpreferencesgraphicsadvanced.cpp b/indra/newview/llfloaterpreferencesgraphicsadvanced.cpp
index 653d26ff30..ad5edf0862 100644
--- a/indra/newview/llfloaterpreferencesgraphicsadvanced.cpp
+++ b/indra/newview/llfloaterpreferencesgraphicsadvanced.cpp
@@ -32,6 +32,7 @@
#include "llfeaturemanager.h"
#include "llfloaterpreference.h"
#include "llfloaterreg.h"
+#include "llnotificationsutil.h"
#include "llsliderctrl.h"
#include "lltextbox.h"
#include "lltrans.h"
@@ -51,11 +52,14 @@ LLFloaterPreferenceGraphicsAdvanced::LLFloaterPreferenceGraphicsAdvanced(const L
mCommitCallbackRegistrar.add("Pref.Cancel", boost::bind(&LLFloaterPreferenceGraphicsAdvanced::onBtnCancel, this, _2));
mCommitCallbackRegistrar.add("Pref.OK", boost::bind(&LLFloaterPreferenceGraphicsAdvanced::onBtnOK, this, _2));
+
+ gSavedSettings.getControl("RenderAvatarMaxNonImpostors")->getSignal()->connect(boost::bind(&LLFloaterPreferenceGraphicsAdvanced::updateIndirectMaxNonImpostors, this, _2));
}
LLFloaterPreferenceGraphicsAdvanced::~LLFloaterPreferenceGraphicsAdvanced()
{
mComplexityChangedSignal.disconnect();
+ mLODFactorChangedSignal.disconnect();
}
BOOL LLFloaterPreferenceGraphicsAdvanced::postBuild()
@@ -75,8 +79,8 @@ BOOL LLFloaterPreferenceGraphicsAdvanced::postBuild()
use_HiDPI->setVisible(FALSE);
#endif
- mComplexityChangedSignal = gSavedSettings.getControl("RenderAvatarMaxComplexity")->getCommitSignal()->connect(boost::bind(&LLFloaterPreferenceGraphicsAdvanced::updateComplexityText, this));
-
+ mComplexityChangedSignal = gSavedSettings.getControl("RenderAvatarMaxComplexity")->getCommitSignal()->connect(boost::bind(&LLFloaterPreferenceGraphicsAdvanced::updateComplexityText, this));
+ mLODFactorChangedSignal = gSavedSettings.getControl("RenderVolumeLODFactor")->getCommitSignal()->connect(boost::bind(&LLFloaterPreferenceGraphicsAdvanced::updateObjectMeshDetailText, this));
return TRUE;
}
@@ -162,6 +166,11 @@ void LLFloaterPreferenceGraphicsAdvanced::updateComplexityText()
getChild("IndirectMaxComplexityText", true));
}
+void LLFloaterPreferenceGraphicsAdvanced::updateObjectMeshDetailText()
+{
+ updateSliderText(getChild("ObjectMeshDetail", true), getChild("ObjectMeshDetailText", true));
+}
+
void LLFloaterPreferenceGraphicsAdvanced::updateSliderText(LLSliderCtrl* ctrl, LLTextBox* text_box)
{
if (text_box == NULL || ctrl== NULL)
@@ -207,6 +216,16 @@ void LLFloaterPreferenceGraphicsAdvanced::updateMaxNonImpostors()
setMaxNonImpostorsText(value, getChild("IndirectMaxNonImpostorsText"));
}
+void LLFloaterPreferenceGraphicsAdvanced::updateIndirectMaxNonImpostors(const LLSD& newvalue)
+{
+ U32 value = newvalue.asInteger();
+ if ((value != 0) && (value != gSavedSettings.getU32("IndirectMaxNonImpostors")))
+ {
+ gSavedSettings.setU32("IndirectMaxNonImpostors", value);
+ setMaxNonImpostorsText(value, getChild("IndirectMaxNonImpostorsText"));
+ }
+}
+
void LLFloaterPreferenceGraphicsAdvanced::setMaxNonImpostorsText(U32 value, LLTextBox* text_box)
{
if (0 == value)
@@ -259,8 +278,7 @@ void LLFloaterPreferenceGraphicsAdvanced::disableUnavailableSettings()
}
// disabled deferred
- if (!LLFeatureManager::getInstance()->isFeatureAvailable("RenderDeferred") ||
- !gGLManager.mHasFramebufferObject)
+ if (!LLFeatureManager::getInstance()->isFeatureAvailable("RenderDeferred"))
{
ctrl_shadows->setEnabled(FALSE);
ctrl_shadows->setValue(0);
@@ -341,9 +359,6 @@ void LLFloaterPreferenceGraphicsAdvanced::refreshEnabledState()
ctrl_reflections->setEnabled(reflections);
reflections_text->setEnabled(reflections);
- // Transparent Water
- LLCheckBoxCtrl* transparent_water_ctrl = getChild("TransparentWater");
-
// Bump & Shiny
LLCheckBoxCtrl* bumpshiny_ctrl = getChild("BumpShiny");
bool bumpshiny = gGLManager.mHasCubeMap && LLCubeMap::sUseCubeMaps && LLFeatureManager::getInstance()->isFeatureAvailable("RenderObjectBump");
@@ -400,9 +415,6 @@ void LLFloaterPreferenceGraphicsAdvanced::refreshEnabledState()
BOOL enabled = LLFeatureManager::getInstance()->isFeatureAvailable("RenderDeferred") &&
((bumpshiny_ctrl && bumpshiny_ctrl->get()) ? TRUE : FALSE) &&
- ((transparent_water_ctrl && transparent_water_ctrl->get()) ? TRUE : FALSE) &&
- gGLManager.mHasFramebufferObject &&
- gSavedSettings.getBOOL("RenderAvatarVP") &&
(ctrl_wind_light->get()) ? TRUE : FALSE;
ctrl_deferred->setEnabled(enabled);
diff --git a/indra/newview/llfloaterpreferencesgraphicsadvanced.h b/indra/newview/llfloaterpreferencesgraphicsadvanced.h
index c5d21ba35b..2c92f3dbf1 100644
--- a/indra/newview/llfloaterpreferencesgraphicsadvanced.h
+++ b/indra/newview/llfloaterpreferencesgraphicsadvanced.h
@@ -45,9 +45,11 @@ public:
void refreshEnabledState();
void updateSliderText(LLSliderCtrl* ctrl, LLTextBox* text_box);
void updateMaxNonImpostors();
+ void updateIndirectMaxNonImpostors(const LLSD& newvalue);
void setMaxNonImpostorsText(U32 value, LLTextBox* text_box);
void updateMaxComplexity();
void updateComplexityText();
+ void updateObjectMeshDetailText();
void refresh();
// callback for when client modifies a render option
void onRenderOptionEnable();
@@ -59,6 +61,7 @@ protected:
void onBtnCancel(const LLSD& userdata);
boost::signals2::connection mComplexityChangedSignal;
+ boost::signals2::connection mLODFactorChangedSignal;
};
#endif //LLFLOATERPREFERENCEGRAPHICSADVANCED_H
diff --git a/indra/newview/llglsandbox.cpp b/indra/newview/llglsandbox.cpp
index fd01c4bf4d..8290b9614e 100644
--- a/indra/newview/llglsandbox.cpp
+++ b/indra/newview/llglsandbox.cpp
@@ -1134,6 +1134,7 @@ private:
//-----------------------------------------------------------------------------
// gpu_benchmark()
+// returns measured memory bandwidth of GPU in gigabytes per second
//-----------------------------------------------------------------------------
F32 gpu_benchmark()
{
diff --git a/indra/newview/llnamelistctrl.h b/indra/newview/llnamelistctrl.h
index 5d88f356db..5051c8b324 100644
--- a/indra/newview/llnamelistctrl.h
+++ b/indra/newview/llnamelistctrl.h
@@ -191,6 +191,7 @@ public:
/*virtual*/ void updateColumns(bool force_update);
/*virtual*/ void mouseOverHighlightNthItem( S32 index );
+
/*virtual*/ BOOL handleRightMouseDown(S32 x, S32 y, MASK mask);
bool isSpecialType() { return (mNameListType == SPECIAL); }
diff --git a/indra/newview/llpanelavatar.cpp b/indra/newview/llpanelavatar.cpp
index 3632d7c631..30c879f8ed 100644
--- a/indra/newview/llpanelavatar.cpp
+++ b/indra/newview/llpanelavatar.cpp
@@ -86,15 +86,18 @@ void LLPanelProfileTab::setAvatarId(const LLUUID& avatar_id)
mSelfProfile = (getAvatarId() == gAgentID);
// FIRE-32179: Make drag-n-drop sharing of items possible again
- LLProfileDropTarget* target = getChild("drop_target");
- if (avatar_id == gAgentID)
+ LLProfileDropTarget* target = findChild("drop_target");
+ if (target)
{
- // hide drop target on own profile
- target->setVisible(false);
- }
- else
- {
- target->setAgentID(avatar_id);
+ if (avatar_id == gAgentID)
+ {
+ // hide drop target on own profile
+ target->setVisible(false);
+ }
+ else
+ {
+ target->setAgentID(avatar_id);
+ }
}
//
}
diff --git a/indra/newview/llpanelface.cpp b/indra/newview/llpanelface.cpp
index c60f57c8d5..4d6bde5430 100644
--- a/indra/newview/llpanelface.cpp
+++ b/indra/newview/llpanelface.cpp
@@ -80,6 +80,8 @@
#include "llpluginclassmedia.h"
#include "llviewertexturelist.h"// Update sel manager as to which channel we're editing so it can reflect the correct overlay UI
+#include // Find all faces with same texture
+
//
// Constant definitions for comboboxes
// Must match the commbobox definitions in panel_tools_texture.xml
@@ -420,6 +422,12 @@ BOOL LLPanelFace::postBuild()
clearCtrls();
+ // Find all faces with same texture
+ getChild("btn_select_same_diff")->setEnabled(false);
+ getChild("btn_select_same_norm")->setEnabled(false);
+ getChild("btn_select_same_spec")->setEnabled(false);
+ //
+
return TRUE;
}
@@ -436,6 +444,10 @@ LLPanelFace::LLPanelFace()
//mCommitCallbackRegistrar.add("PanelFace.menuDoToSelected", boost::bind(&LLPanelFace::menuDoToSelected, this, _2));
//mEnableCallbackRegistrar.add("PanelFace.menuEnable", boost::bind(&LLPanelFace::menuEnableItem, this, _2));
//
+
+ // Find all faces with same texture
+ mCommitCallbackRegistrar.add("BuildTool.SelectSameTexture", boost::bind(&LLPanelFace::onClickBtnSelectSameTexture, this, _1, _2));
+ //
}
LLPanelFace::~LLPanelFace()
@@ -1687,6 +1699,12 @@ void LLPanelFace::updateUI(bool force_set_values /*false*/)
calcp->setVar(LLCalc::TEX_ROTATION, getCurrentTextureRot());
calcp->setVar(LLCalc::TEX_TRANSPARENCY, childGetValue("ColorTrans").asReal());
calcp->setVar(LLCalc::TEX_GLOW, childGetValue("glow").asReal());
+
+ // Find all faces with same texture
+ getChild("btn_select_same_diff")->setEnabled(LLSelectMgr::getInstance()->getTEMode() && mTextureCtrl->getEnabled());
+ getChild("btn_select_same_norm")->setEnabled(LLSelectMgr::getInstance()->getTEMode() && mBumpyTextureCtrl->getEnabled());
+ getChild("btn_select_same_spec")->setEnabled(LLSelectMgr::getInstance()->getTEMode() && mShinyTextureCtrl->getEnabled());
+ //
}
else
{
@@ -2661,6 +2679,11 @@ void LLPanelFace::updateVisibility()
getChildView("bumpyOffsetV")->setVisible(show_bumpiness);
+ // Find all faces with same texture
+ getChild("btn_select_same_diff")->setVisible(mTextureCtrl->getVisible());
+ getChild("btn_select_same_norm")->setVisible(mBumpyTextureCtrl->getVisible());
+ getChild("btn_select_same_spec")->setVisible(mShinyTextureCtrl->getVisible());
+ //
}
// static
@@ -4819,3 +4842,82 @@ void LLPanelFace::changePrecision(S32 decimal_precision)
mCtrlRpt->setPrecision(decimal_precision);
}
//
+
+// Find all faces with same texture
+void LLPanelFace::onClickBtnSelectSameTexture(const LLUICtrl* ctrl, const LLSD& user_data)
+{
+ char channel = user_data.asStringRef()[0];
+
+ std::unordered_set objects;
+
+ // get a list of all linksets where at least one face is selected
+ for (auto iter = LLSelectMgr::getInstance()->getSelection()->valid_begin();
+ iter != LLSelectMgr::getInstance()->getSelection()->valid_end(); iter++)
+ {
+ objects.insert((*iter)->getObject()->getRootEdit());
+ }
+
+ // clean out the selection
+ LLSelectMgr::getInstance()->deselectAll();
+
+ // select all faces of all linksets that were found before
+ LLObjectSelectionHandle handle;
+ for(auto objectp : objects)
+ {
+ handle = LLSelectMgr::getInstance()->selectObjectAndFamily(objectp, true, false);
+ }
+
+ // grab the texture ID from the texture selector
+ LLTextureCtrl* texture_control = mTextureCtrl;
+ if (channel == 'n')
+ {
+ texture_control = mBumpyTextureCtrl;
+ }
+ else if (channel == 's')
+ {
+ texture_control = mShinyTextureCtrl;
+ }
+
+ LLUUID id = texture_control->getImageAssetID();
+
+ // go through all selected links in all selecrted linksets
+ for (auto iter = handle->begin(); iter != handle->end(); iter++)
+ {
+ LLSelectNode* node = *iter;
+ LLViewerObject* objectp = node->getObject();
+
+ U8 te_count = objectp->getNumTEs();
+
+ for (U8 i = 0; i < te_count; i++)
+ {
+ LLUUID image_id;
+ if (channel == 'd')
+ {
+ image_id = objectp->getTEImage(i)->getID();
+ }
+ else
+ {
+ const LLMaterialPtr mat = objectp->getTEref(i).getMaterialParams();
+ if (mat.notNull())
+ {
+ if (channel == 'n')
+ {
+ image_id = mat->getNormalID();
+ }
+ else if (channel == 's')
+ {
+ image_id = mat->getSpecularID();
+ }
+ }
+ }
+
+ // deselect all faces that use a different texture UUID
+ if (image_id != id)
+ {
+ objectp->setTESelected(i, false);
+ node->selectTE(i, false);
+ }
+ }
+ }
+}
+//
diff --git a/indra/newview/llpanelface.h b/indra/newview/llpanelface.h
index 387d182533..5697d57fd5 100644
--- a/indra/newview/llpanelface.h
+++ b/indra/newview/llpanelface.h
@@ -230,6 +230,8 @@ protected:
void onPasteFaces();
//
+ void onClickBtnSelectSameTexture(const LLUICtrl* ctrl, const LLSD& user_data); // Find all faces with same texture
+
public: // needs to be accessible to selection manager
void onCopyColor(); // records all selected faces
void onPasteColor(); // to specific face
diff --git a/indra/newview/llpanelobject.cpp b/indra/newview/llpanelobject.cpp
index 8f9bb63522..39eb6d82eb 100644
--- a/indra/newview/llpanelobject.cpp
+++ b/indra/newview/llpanelobject.cpp
@@ -1561,7 +1561,7 @@ void LLPanelObject::activateMeshFields(LLViewerObject * objectp)
childSetVisible("ObjectLODbehaviourLabel", true);
// Setup the LL defaults
- factor = 1.125f; // LL default for most people http://wiki.firestormviewer.org/support:whirly_fizzle#lod_comparison
+ factor = 1.25f; // LL default for most people http://wiki.firestormviewer.org/support:whirly_fizzle#lod_comparison
args["FACTOR"] = llformat("%.3f", factor);
tb = getChild("LOD_swap_ll_default");
tb->setToolTip(getString("ll_lod_tooltip_msg",args));
diff --git a/indra/newview/llpanelpresetspulldown.cpp b/indra/newview/llpanelpresetspulldown.cpp
index e59ec12529..64580b8490 100644
--- a/indra/newview/llpanelpresetspulldown.cpp
+++ b/indra/newview/llpanelpresetspulldown.cpp
@@ -34,6 +34,8 @@
#include "llbutton.h"
#include "lltabcontainer.h"
#include "llfloater.h"
+//#include "llfloaterperformance.h"
+#include "fsfloaterperformance.h"
#include "llfloaterreg.h"
#include "llpresetsmanager.h"
#include "llsliderctrl.h"
@@ -48,6 +50,7 @@
LLPanelPresetsPulldown::LLPanelPresetsPulldown()
{
mCommitCallbackRegistrar.add("Presets.GoGraphicsPrefs", boost::bind(&LLPanelPresetsPulldown::onGraphicsButtonClick, this, _2));
+ mCommitCallbackRegistrar.add("Presets.GoAutofpsPrefs", boost::bind(&LLPanelPresetsPulldown::onAutofpsButtonClick, this, _2));
mCommitCallbackRegistrar.add("Presets.RowClick", boost::bind(&LLPanelPresetsPulldown::onRowClick, this, _2));
buildFromFile( "panel_presets_pulldown.xml");
@@ -155,3 +158,15 @@ void LLPanelPresetsPulldown::onGraphicsButtonClick(const LLSD& user_data)
}
}
}
+
+void LLPanelPresetsPulldown::onAutofpsButtonClick(const LLSD& user_data)
+{
+ setVisible(FALSE);
+ //LLFloaterPerformance* performance_floater = LLFloaterReg::showTypedInstance("performance");
+ FSFloaterPerformance* performance_floater = LLFloaterReg::showTypedInstance("performance");
+ if (performance_floater)
+ {
+ //performance_floater->showAutoadjustmentsPanel();
+ performance_floater->showMainPanel();
+ }
+}
diff --git a/indra/newview/llpanelpresetspulldown.h b/indra/newview/llpanelpresetspulldown.h
index c0d32b9b21..79bd6886b1 100644
--- a/indra/newview/llpanelpresetspulldown.h
+++ b/indra/newview/llpanelpresetspulldown.h
@@ -41,6 +41,7 @@ class LLPanelPresetsPulldown : public LLPanelPulldown
private:
void onGraphicsButtonClick(const LLSD& user_data);
+ void onAutofpsButtonClick(const LLSD& user_data);
void onRowClick(const LLSD& user_data);
std::list mPresetNames;
diff --git a/indra/newview/llpanelprofile.cpp b/indra/newview/llpanelprofile.cpp
index d213e8e535..d9bc087e83 100644
--- a/indra/newview/llpanelprofile.cpp
+++ b/indra/newview/llpanelprofile.cpp
@@ -1201,7 +1201,9 @@ void LLPanelProfileSecondLife::resetData()
resetLoading();
// Set default image and 1:1 dimensions for it
- mSecondLifePic->setValue("Generic_Person_Large");
+ // Retain texture picker for profile images
+ //mSecondLifePic->setValue("Generic_Person_Large");
+ mSecondLifePic->setImageAssetID(LLUUID::null);
mImageId = LLUUID::null;
// Fix LL UI/UX design accident
@@ -3030,7 +3032,9 @@ void LLPanelProfileFirstLife::apply(LLAvatarData* data)
void LLPanelProfileFirstLife::resetData()
{
setDescriptionText(std::string());
- mPicture->setValue("Generic_Person_Large");
+ // Retain texture picker for profile images
+ //mPicture->setValue("Generic_Person_Large");
+ mPicture->setImageAssetID(LLUUID::null);
mImageId = LLUUID::null;
// remove the buttons and just have click image to update profile
diff --git a/indra/newview/fsperfstats.cpp b/indra/newview/llperfstats.cpp
similarity index 66%
rename from indra/newview/fsperfstats.cpp
rename to indra/newview/llperfstats.cpp
index 9b283feb00..2aedaf7022 100644
--- a/indra/newview/fsperfstats.cpp
+++ b/indra/newview/llperfstats.cpp
@@ -1,43 +1,45 @@
/**
- * @file fsperfstats.cpp
- * @brief Stats collection to support perf floater and auto tune
- *
- * $LicenseInfo:firstyear=2021&license=fsviewerlgpl$
- * Phoenix Firestorm Viewer Source Code
- * Copyright (C) 2021, The Phoenix Firestorm Project, 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.
- *
- * 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.
- *
- * 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
- *
- * The Phoenix Firestorm Project, Inc., 1831 Oakwood Drive, Fairmont, Minnesota 56031-3225 USA
- * http://www.firestormviewer.org
- * $/LicenseInfo$
- */
+* @file llperfstats.cpp
+* @brief Statistics collection to support autotune and perf flaoter.
+*
+* $LicenseInfo:firstyear=2022&license=viewerlgpl$
+* Second Life Viewer Source Code
+* Copyright (C) 2022, 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.
+*
+* 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.
+*
+* 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
+*
+* Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
+* $/LicenseInfo$
+*/
#include "llviewerprecompiledheaders.h"
-#include "fsperfstats.h"
+#include "llperfstats.h"
#include "llcontrol.h"
#include "pipeline.h"
#include "llagentcamera.h"
+#include "llviewerwindow.h"
#include "llvoavatar.h"
+#include "llwindow.h"
#include "llworld.h"
#include
extern LLControlGroup gSavedSettings;
-namespace FSPerfStats
+namespace LLPerfStats
{
+// extra profiling
#ifdef USAGE_TRACKING
std::atomic inUse{0};
std::atomic inUseAvatar{0};
@@ -46,20 +48,24 @@ namespace FSPerfStats
std::atomic inUseAttachmentRigged{0};
std::atomic inUseAttachmentUnRigged{0};
#endif
-
+//
std::atomic tunedAvatars{0};
std::atomic renderAvatarMaxART_ns{(U64)(ART_UNLIMITED_NANOS)}; // highest render time we'll allow without culling features
bool belowTargetFPS{false};
U32 lastGlobalPrefChange{0};
+ U32 lastSleepedFrame{0};
+ U64 meanFrameTime{0};
std::mutex bufferToggleLock{};
F64 cpu_hertz{0.0};
+ U32 vsync_max_fps{60};
Tunables tunables;
std::atomic StatsRecorder::writeBuffer{0};
bool StatsRecorder::collectionEnabled{true};
LLUUID StatsRecorder::focusAv{LLUUID::null};
+ bool StatsRecorder::autotuneInit{false};
std::array StatsRecorder::statsDoubleBuffer{ {} };
std::array StatsRecorder::max{ {} };
std::array StatsRecorder::sum{ {} };
@@ -71,46 +77,46 @@ namespace FSPerfStats
if( tuningFlag & NonImpostors ){ gSavedSettings.setU32("IndirectMaxNonImpostors", nonImpostors); };
if( tuningFlag & ReflectionDetail ){ gSavedSettings.setS32("RenderReflectionDetail", reflectionDetail); };
if( tuningFlag & FarClip ){ gSavedSettings.setF32("RenderFarClip", farClip); };
- if( tuningFlag & UserMinDrawDistance ){ gSavedSettings.setF32("FSAutoTuneRenderFarClipMin", userMinDrawDistance); };
- if( tuningFlag & UserTargetDrawDistance ){ gSavedSettings.setF32("FSAutoTuneRenderFarClipTarget", userTargetDrawDistance); };
- if( tuningFlag & UserImpostorDistance ){ gSavedSettings.setF32("FSAutoTuneImpostorFarAwayDistance", userImpostorDistance); };
- if( tuningFlag & UserImpostorDistanceTuningEnabled ){ gSavedSettings.setBOOL("FSAutoTuneImpostorByDistEnabled", userImpostorDistanceTuningEnabled); };
- if( tuningFlag & UserFPSTuningStrategy ){ gSavedSettings.setU32("FSTuningFPSStrategy", userFPSTuningStrategy); };
- if( tuningFlag & UserAutoTuneEnabled ){ gSavedSettings.setBOOL("FSAutoTuneFPS", userAutoTuneEnabled); };
- if( tuningFlag & UserAutoTuneLock ){ gSavedSettings.setBOOL("FSAutoTuneLock", userAutoTuneLock); };
- if( tuningFlag & UserTargetFPS ){ gSavedSettings.setU32("FSTargetFPS", userTargetFPS); };
- if( tuningFlag & UserTargetReflections ){ gSavedSettings.setS32("FSUserTargetReflections", userTargetReflections); };
+ if( tuningFlag & UserMinDrawDistance ){ gSavedSettings.setF32("AutoTuneRenderFarClipMin", userMinDrawDistance); };
+ if( tuningFlag & UserTargetDrawDistance ){ gSavedSettings.setF32("AutoTuneRenderFarClipTarget", userTargetDrawDistance); };
+ if( tuningFlag & UserImpostorDistance ){ gSavedSettings.setF32("AutoTuneImpostorFarAwayDistance", userImpostorDistance); };
+ if( tuningFlag & UserImpostorDistanceTuningEnabled ){ gSavedSettings.setBOOL("AutoTuneImpostorByDistEnabled", userImpostorDistanceTuningEnabled); };
+ if( tuningFlag & UserFPSTuningStrategy ){ gSavedSettings.setU32("TuningFPSStrategy", userFPSTuningStrategy); };
+ if( tuningFlag & UserAutoTuneEnabled ){ gSavedSettings.setBOOL("AutoTuneFPS", userAutoTuneEnabled); };
+ if( tuningFlag & UserAutoTuneLock ){ gSavedSettings.setBOOL("AutoTuneLock", userAutoTuneLock); };
+ if( tuningFlag & UserTargetFPS ){ gSavedSettings.setU32("TargetFPS", userTargetFPS); };
+ if( tuningFlag & UserTargetReflections ){ gSavedSettings.setS32("UserTargetReflections", userTargetReflections); };
// Note: The Max ART slider is logarithmic and thus we have an intermediate proxy value
- if( tuningFlag & UserARTCutoff ){ gSavedSettings.setF32("FSRenderAvatarMaxART", userARTCutoffSliderValue); };
+ if( tuningFlag & UserARTCutoff ){ gSavedSettings.setF32("RenderAvatarMaxART", userARTCutoffSliderValue); };
resetChanges();
}
void Tunables::updateRenderCostLimitFromSettings()
{
assert_main_thread();
- const auto newval = gSavedSettings.getF32("FSRenderAvatarMaxART");
- if(newval < log10(FSPerfStats::ART_UNLIMITED_NANOS/1000))
- {
- FSPerfStats::renderAvatarMaxART_ns = pow(10,newval)*1000;
- }
- else
- {
- FSPerfStats::renderAvatarMaxART_ns = 0;
- };
+ const auto newval = gSavedSettings.getF32("RenderAvatarMaxART");
+ if(newval < log10(LLPerfStats::ART_UNLIMITED_NANOS/1000))
+ {
+ LLPerfStats::renderAvatarMaxART_ns = pow(10,newval)*1000;
+ }
+ else
+ {
+ LLPerfStats::renderAvatarMaxART_ns = 0;
+ }
}
// static
void Tunables::updateSettingsFromRenderCostLimit()
{
- if( userARTCutoffSliderValue != log10( ( (F32)FSPerfStats::renderAvatarMaxART_ns )/1000 ) )
+ if( userARTCutoffSliderValue != log10( ( (F32)LLPerfStats::renderAvatarMaxART_ns )/1000 ) )
{
- if( FSPerfStats::renderAvatarMaxART_ns != 0 )
+ if( LLPerfStats::renderAvatarMaxART_ns != 0 )
{
- updateUserARTCutoffSlider(log10( ( (F32)FSPerfStats::renderAvatarMaxART_ns )/1000 ) );
+ updateUserARTCutoffSlider(log10( ( (F32)LLPerfStats::renderAvatarMaxART_ns )/1000 ) );
}
else
{
- updateUserARTCutoffSlider(log10( (F32)FSPerfStats::ART_UNLIMITED_NANOS/1000 ) );
+ updateUserARTCutoffSlider(log10( (F32)LLPerfStats::ART_UNLIMITED_NANOS/1000 ) );
}
}
}
@@ -119,15 +125,29 @@ namespace FSPerfStats
{
assert_main_thread();
// the following variables are two way and have "push" in llviewercontrol
- FSPerfStats::tunables.userMinDrawDistance = gSavedSettings.getF32("FSAutoTuneRenderFarClipMin");
- FSPerfStats::tunables.userTargetDrawDistance = gSavedSettings.getF32("FSAutoTuneRenderFarClipTarget");
- FSPerfStats::tunables.userImpostorDistance = gSavedSettings.getF32("FSAutoTuneImpostorFarAwayDistance");
- FSPerfStats::tunables.userImpostorDistanceTuningEnabled = gSavedSettings.getBOOL("FSAutoTuneImpostorByDistEnabled");
- FSPerfStats::tunables.userFPSTuningStrategy = gSavedSettings.getU32("FSTuningFPSStrategy");
- FSPerfStats::tunables.userTargetFPS = gSavedSettings.getU32("FSTargetFPS");
- FSPerfStats::tunables.userTargetReflections = gSavedSettings.getS32("FSUserTargetReflections");
- FSPerfStats::tunables.userAutoTuneEnabled = gSavedSettings.getBOOL("FSAutoTuneFPS");
- FSPerfStats::tunables.userAutoTuneLock = gSavedSettings.getBOOL("FSAutoTuneLock");
+ LLPerfStats::tunables.userMinDrawDistance = gSavedSettings.getF32("AutoTuneRenderFarClipMin");
+ LLPerfStats::tunables.userTargetDrawDistance = gSavedSettings.getF32("AutoTuneRenderFarClipTarget");
+ LLPerfStats::tunables.userImpostorDistance = gSavedSettings.getF32("AutoTuneImpostorFarAwayDistance");
+ LLPerfStats::tunables.userImpostorDistanceTuningEnabled = gSavedSettings.getBOOL("AutoTuneImpostorByDistEnabled");
+ LLPerfStats::tunables.userFPSTuningStrategy = gSavedSettings.getU32("TuningFPSStrategy");
+ LLPerfStats::tunables.userTargetFPS = gSavedSettings.getU32("TargetFPS");
+ LLPerfStats::tunables.vsyncEnabled = gSavedSettings.getBOOL("RenderVSyncEnable");
+ LLPerfStats::tunables.userTargetReflections = gSavedSettings.getS32("UserTargetReflections");
+
+ LLPerfStats::tunables.userAutoTuneLock = gSavedSettings.getBOOL("AutoTuneLock") && gSavedSettings.getU32("KeepAutoTuneLock");
+
+ if(gSavedSettings.getBOOL("AutoTuneLock") && !gSavedSettings.getU32("KeepAutoTuneLock"))
+ {
+ gSavedSettings.setBOOL("AutoTuneLock", FALSE);
+ }
+
+ LLPerfStats::tunables.userAutoTuneEnabled = LLPerfStats::tunables.userAutoTuneLock;
+
+ if (LLPerfStats::tunables.userAutoTuneEnabled && !gSavedSettings.getBOOL("AutoTuneFPS"))
+ {
+ gSavedSettings.setBOOL("AutoTuneFPS", TRUE);
+ }
+
// Note: The Max ART slider is logarithmic and thus we have an intermediate proxy value
updateRenderCostLimitFromSettings();
resetChanges();
@@ -138,8 +158,8 @@ namespace FSPerfStats
// create a queue
// create a thread to consume from the queue
tunables.initialiseFromSettings();
- FSPerfStats::cpu_hertz = (F64)LLTrace::BlockTimer::countsPerSecond();
-
+ LLPerfStats::cpu_hertz = (F64)LLTrace::BlockTimer::countsPerSecond();
+ LLPerfStats::vsync_max_fps = gViewerWindow->getWindow()->getRefreshRate();
t.detach();
}
@@ -150,7 +170,7 @@ namespace FSPerfStats
using ST = StatType_t;
bool unreliable{false};
- FSPerfStats::StatsRecorder::getSceneStat(FSPerfStats::StatType_t::RENDER_FRAME);
+ LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_FRAME);
auto& sceneStats = statsDoubleBuffer[writeBuffer][static_cast(ObjType_t::OT_GENERAL)][LLUUID::null];
auto& lastStats = statsDoubleBuffer[writeBuffer ^ 1][static_cast(ObjType_t::OT_GENERAL)][LLUUID::null];
@@ -170,11 +190,13 @@ namespace FSPerfStats
StatType_t::RENDER_COMBINED,
StatType_t::RENDER_IDLE };
-
+ // restore FPSLimit reporting
+ // if( /*sceneStats[static_cast(StatType_t::RENDER_FPSLIMIT)] != 0 ||*/ sceneStats[static_cast(StatType_t::RENDER_SLEEP)] != 0 )
if( sceneStats[static_cast(StatType_t::RENDER_FPSLIMIT)] != 0 || sceneStats[static_cast(StatType_t::RENDER_SLEEP)] != 0 )
+ //
{
unreliable = true;
- lastStats[static_cast(StatType_t::RENDER_FPSLIMIT)] = sceneStats[static_cast(StatType_t::RENDER_FPSLIMIT)];
+ lastStats[static_cast(StatType_t::RENDER_FPSLIMIT)] = sceneStats[static_cast(StatType_t::RENDER_FPSLIMIT)];// restore FPSLimit reporting
lastStats[static_cast(StatType_t::RENDER_SLEEP)] = sceneStats[static_cast(StatType_t::RENDER_SLEEP)];
lastStats[static_cast(StatType_t::RENDER_FRAME)] = sceneStats[static_cast(StatType_t::RENDER_FRAME)]; // bring over the total frame render time to deal with region crossing overlap issues
}
@@ -243,7 +265,7 @@ namespace FSPerfStats
}
// and now adjust the proxy vars so that the main thread can adjust the visuals.
- if(tunables.userAutoTuneEnabled)
+ if(autotuneInit && tunables.userAutoTuneEnabled)
{
updateAvatarParams();
}
@@ -307,9 +329,69 @@ namespace FSPerfStats
return positions.size();
}
+ const U32 NUM_PERIODS = 50;
+ void StatsRecorder::updateMeanFrameTime(U64 cur_frame_time_raw)
+ {
+ static std::deque frame_time_deque;
+ frame_time_deque.push_front(cur_frame_time_raw);
+ if (frame_time_deque.size() > NUM_PERIODS)
+ {
+ frame_time_deque.pop_back();
+ }
+
+ std::vector buf(frame_time_deque.begin(), frame_time_deque.end());
+ std::sort(buf.begin(), buf.end());
+
+ LLPerfStats::meanFrameTime = (buf.size() % 2 == 0) ? (buf[buf.size() / 2 - 1] + buf[buf.size() / 2]) / 2 : buf[buf.size() / 2];
+ }
+ U64 StatsRecorder::getMeanTotalFrameTime()
+ {
+ return LLPerfStats::meanFrameTime;
+ }
+
// static
void StatsRecorder::updateAvatarParams()
{
+ if(tunables.autoTuneTimeout)
+ {
+ LLPerfStats::lastSleepedFrame = gFrameCount;
+ tunables.autoTuneTimeout = false;
+ return;
+ }
+ // sleep time is basically forced sleep when window out of focus
+ auto tot_sleep_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_SLEEP);
+ // similar to sleep time, induced by FPS limit
+ auto tot_limit_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_FPSLIMIT);// restore FPSLimit reporting
+
+
+ // the time spent this frame on the "doFrame" call. Treated as "tot time for frame"
+ auto tot_frame_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_FRAME);
+
+ if( tot_sleep_time_raw != 0 )
+ {
+ // Note: we do not average sleep
+ // if at some point we need to, the averaging will need to take this into account or
+ // we forever think we're in the background due to residuals.
+ LL_DEBUGS() << "No tuning when not in focus" << LL_ENDL;
+ LLPerfStats::lastSleepedFrame = gFrameCount;
+ return;
+ }
+
+ U32 target_fps = tunables.vsyncEnabled ? std::min(LLPerfStats::vsync_max_fps, tunables.userTargetFPS) : tunables.userTargetFPS;
+
+ if(LLPerfStats::lastSleepedFrame != 0)
+ {
+ // wait a short time after viewer regains focus
+ if((gFrameCount - LLPerfStats::lastSleepedFrame) > target_fps * 5)
+ {
+ LLPerfStats::lastSleepedFrame = 0;
+ }
+ else
+ {
+ return;
+ }
+ }
+ updateMeanFrameTime(tot_frame_time_raw);
if(tunables.userImpostorDistanceTuningEnabled)
{
@@ -323,46 +405,39 @@ namespace FSPerfStats
}
}
- auto av_render_max_raw = FSPerfStats::StatsRecorder::getMax(ObjType_t::OT_AVATAR, FSPerfStats::StatType_t::RENDER_COMBINED);
+ auto av_render_max_raw = LLPerfStats::StatsRecorder::getMax(ObjType_t::OT_AVATAR, LLPerfStats::StatType_t::RENDER_COMBINED);
// Is our target frame time lower than current? If so we need to take action to reduce draw overheads.
// cumulative avatar time (includes idle processing, attachments and base av)
- auto tot_avatar_time_raw = FSPerfStats::StatsRecorder::getSum(ObjType_t::OT_AVATAR, FSPerfStats::StatType_t::RENDER_COMBINED);
- // sleep time is basically forced sleep when window out of focus
- auto tot_sleep_time_raw = FSPerfStats::StatsRecorder::getSceneStat(FSPerfStats::StatType_t::RENDER_SLEEP);
- // similar to sleep time, induced by FPS limit
- auto tot_limit_time_raw = FSPerfStats::StatsRecorder::getSceneStat(FSPerfStats::StatType_t::RENDER_FPSLIMIT);
-
-
- // the time spent this frame on the "doFrame" call. Treated as "tot time for frame"
- auto tot_frame_time_raw = FSPerfStats::StatsRecorder::getSceneStat(FSPerfStats::StatType_t::RENDER_FRAME);
-
- if( tot_sleep_time_raw != 0 )
- {
- // Note: we do not average sleep
- // if at some point we need to, the averaging will need to take this into account or
- // we forever think we're in the background due to residuals.
- LL_DEBUGS() << "No tuning when not in focus" << LL_ENDL;
- return;
- }
+ auto tot_avatar_time_raw = LLPerfStats::StatsRecorder::getSum(ObjType_t::OT_AVATAR, LLPerfStats::StatType_t::RENDER_COMBINED);
// The frametime budget we have based on the target FPS selected
- auto target_frame_time_raw = (U64)llround(FSPerfStats::cpu_hertz/(tunables.userTargetFPS==0?1:tunables.userTargetFPS));
+ auto target_frame_time_raw = (U64)llround(LLPerfStats::cpu_hertz / (target_fps == 0 ? 1 : target_fps));
// LL_INFOS() << "Effective FPS(raw):" << tot_frame_time_raw << " Target:" << target_frame_time_raw << LL_ENDL;
auto inferredFPS{1000/(U32)std::max(raw_to_ms(tot_frame_time_raw),1.0)};
- U32 settingsChangeFrequency{inferredFPS > 25?inferredFPS:25};
- if( tot_limit_time_raw != 0)
+ U32 settingsChangeFrequency{inferredFPS > 50?inferredFPS:50};
+ if( tot_limit_time_raw != 0)// restore FPSLimit reporting
{
// This could be problematic.
tot_frame_time_raw -= tot_limit_time_raw;
- }
+ }// restore FPSLimit reporting
+
+ F64 time_buf = target_frame_time_raw * 0.1;
+
// 1) Is the target frame time lower than current?
- if( target_frame_time_raw <= tot_frame_time_raw )
+ if ((target_frame_time_raw + time_buf) <= tot_frame_time_raw)
{
+ if (target_frame_time_raw - time_buf >= getMeanTotalFrameTime())
+ {
+ belowTargetFPS = false;
+ LLPerfStats::lastGlobalPrefChange = gFrameCount;
+ return;
+ }
+
if(belowTargetFPS == false)
{
// this is the first frame under. hold fire to add a little hysteresis
belowTargetFPS = true;
- FSPerfStats::lastGlobalPrefChange = gFrameCount;
+ LLPerfStats::lastGlobalPrefChange = gFrameCount;
}
// if so we've got work to do
@@ -374,16 +449,16 @@ namespace FSPerfStats
if(target_frame_time_raw < non_avatar_time_raw)
{
// we cannnot do this by avatar adjustment alone.
- if((gFrameCount - FSPerfStats::lastGlobalPrefChange) > settingsChangeFrequency) // give changes a short time to take effect.
+ if((gFrameCount - LLPerfStats::lastGlobalPrefChange) > settingsChangeFrequency) // give changes a short time to take effect.
{
- if(tunables.userFPSTuningStrategy == TUNE_SCENE_AND_AVATARS)
+ if(tunables.userFPSTuningStrategy != TUNE_AVATARS_ONLY)
{
// 1 - hack the water to opaque. all non opaque have a significant hit, this is a big boost for (arguably) a minor visual hit.
// the other reflection options make comparatively little change and if this overshoots we'll be stepping back up later
if(LLPipeline::RenderReflectionDetail != -2)
{
- FSPerfStats::tunables.updateReflectionDetail(-2);
- FSPerfStats::lastGlobalPrefChange = gFrameCount;
+ LLPerfStats::tunables.updateReflectionDetail(-2);
+ LLPerfStats::lastGlobalPrefChange = gFrameCount;
return;
}
else // deliberately "else" here so we only do one of these in any given frame
@@ -392,8 +467,8 @@ namespace FSPerfStats
auto new_dd = (LLPipeline::RenderFarClip - DD_STEP > tunables.userMinDrawDistance)?(LLPipeline::RenderFarClip - DD_STEP) : tunables.userMinDrawDistance;
if(new_dd != LLPipeline::RenderFarClip)
{
- FSPerfStats::tunables.updateFarClip( new_dd );
- FSPerfStats::lastGlobalPrefChange = gFrameCount;
+ LLPerfStats::tunables.updateFarClip( new_dd );
+ LLPerfStats::lastGlobalPrefChange = gFrameCount;
return;
}
}
@@ -414,19 +489,19 @@ namespace FSPerfStats
target_avatar_time_raw = target_frame_time_raw - non_avatar_time_raw;
}
- if( target_avatar_time_raw < tot_avatar_time_raw )
+ if ((target_avatar_time_raw < tot_avatar_time_raw) && (tunables.userFPSTuningStrategy != TUNE_SCENE_ONLY))
{
// we need to spend less time drawing avatars to meet our budget
- auto new_render_limit_ns {FSPerfStats::raw_to_ns(av_render_max_raw)};
+ auto new_render_limit_ns {LLPerfStats::raw_to_ns(av_render_max_raw)};
// max render this frame may be higher than the last (cos new entrants and jitter) so make sure we are heading in the right direction
if( new_render_limit_ns > renderAvatarMaxART_ns )
{
new_render_limit_ns = renderAvatarMaxART_ns;
}
- new_render_limit_ns -= FSPerfStats::ART_MIN_ADJUST_DOWN_NANOS;
+ new_render_limit_ns -= LLPerfStats::ART_MIN_ADJUST_DOWN_NANOS;
// bounce at the bottom to prevent "no limit"
- new_render_limit_ns = std::max((U64)new_render_limit_ns, (U64)FSPerfStats::ART_MINIMUM_NANOS);
+ new_render_limit_ns = std::max((U64)new_render_limit_ns, (U64)LLPerfStats::ART_MINIMUM_NANOS);
// assign the new value
if(renderAvatarMaxART_ns != new_render_limit_ns)
@@ -436,9 +511,10 @@ namespace FSPerfStats
}
// LL_DEBUGS() << "AUTO_TUNE: avatar_budget adjusted to:" << new_render_limit_ns << LL_ENDL;
}
- // LL_DEBUGS() << "AUTO_TUNE: Target frame time:"<< FSPerfStats::raw_to_us(target_frame_time_raw) << "usecs (non_avatar is " << FSPerfStats::raw_to_us(non_avatar_time_raw) << "usecs) Max cost limited=" << renderAvatarMaxART_ns << LL_ENDL;
+ // LL_DEBUGS() << "AUTO_TUNE: Target frame time:"<< LLPerfStats::raw_to_us(target_frame_time_raw) << "usecs (non_avatar is " << LLPerfStats::raw_to_us(non_avatar_time_raw) << "usecs) Max cost limited=" << renderAvatarMaxART_ns << LL_ENDL;
}
- else if( FSPerfStats::raw_to_ns(target_frame_time_raw) > (FSPerfStats::raw_to_ns(tot_frame_time_raw) + renderAvatarMaxART_ns) )
+ else if(( LLPerfStats::raw_to_ns(target_frame_time_raw) > (LLPerfStats::raw_to_ns(tot_frame_time_raw) + renderAvatarMaxART_ns) ) ||
+ (tunables.vsyncEnabled && (target_fps == LLPerfStats::vsync_max_fps) && (target_frame_time_raw > getMeanTotalFrameTime())))
{
if(belowTargetFPS == true)
{
@@ -456,28 +532,29 @@ namespace FSPerfStats
// turn off if we are not locked.
tunables.updateUserAutoTuneEnabled(false);
}
- if( FSPerfStats::tunedAvatars > 0 )
+ if(renderAvatarMaxART_ns != 0 && LLPerfStats::tunedAvatars > 0 && (tunables.userFPSTuningStrategy != TUNE_SCENE_ONLY) )
{
// if we have more time to spare let's shift up little in the hope we'll restore an avatar.
- renderAvatarMaxART_ns += FSPerfStats::ART_MIN_ADJUST_UP_NANOS;
+ U64 up_step = LLPerfStats::tunedAvatars > 2 ? LLPerfStats::ART_MIN_ADJUST_UP_NANOS : LLPerfStats::ART_MIN_ADJUST_UP_NANOS * 2;
+ renderAvatarMaxART_ns += up_step;
tunables.updateSettingsFromRenderCostLimit();
return;
}
- if(tunables.userFPSTuningStrategy == TUNE_SCENE_AND_AVATARS)
+ if(tunables.userFPSTuningStrategy != TUNE_AVATARS_ONLY)
{
if( LLPipeline::RenderFarClip < tunables.userTargetDrawDistance )
{
- FSPerfStats::tunables.updateFarClip( std::min(LLPipeline::RenderFarClip + DD_STEP, tunables.userTargetDrawDistance) );
- FSPerfStats::lastGlobalPrefChange = gFrameCount;
+ LLPerfStats::tunables.updateFarClip( std::min(LLPipeline::RenderFarClip + DD_STEP, tunables.userTargetDrawDistance) );
+ LLPerfStats::lastGlobalPrefChange = gFrameCount;
return;
}
if( (tot_frame_time_raw * 1.5) < target_frame_time_raw )
{
// if everything else is "max" and we have >50% headroom let's knock the water quality up a notch at a time.
- FSPerfStats::tunables.updateReflectionDetail( std::min(LLPipeline::RenderReflectionDetail + 1, tunables.userTargetReflections) );
+ LLPerfStats::tunables.updateReflectionDetail( std::min(LLPipeline::RenderReflectionDetail + 1, tunables.userTargetReflections) );
}
}
}
}
}
-}
\ No newline at end of file
+}
diff --git a/indra/newview/fsperfstats.h b/indra/newview/llperfstats.h
similarity index 75%
rename from indra/newview/fsperfstats.h
rename to indra/newview/llperfstats.h
index 2e610d08c0..706cc94516 100644
--- a/indra/newview/fsperfstats.h
+++ b/indra/newview/llperfstats.h
@@ -1,32 +1,31 @@
-#pragma once
-#ifndef FS_PERFSTATS_H_INCLUDED
-#define FS_PERFSTATS_H_INCLUDED
/**
- * @file fsperfstats.h
- * @brief Statistics collection to support autotune and perf flaoter.
- *
- * $LicenseInfo:firstyear=2021&license=fsviewerlgpl$
- * Phoenix Firestorm Viewer Source Code
- * Copyright (C) 2021, The Phoenix Firestorm Project, 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.
- *
- * 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.
- *
- * 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
- *
- * The Phoenix Firestorm Project, Inc., 1831 Oakwood Drive, Fairmont, Minnesota 56031-3225 USA
- * http://www.firestormviewer.org
- * $/LicenseInfo$
- */
+* @file llperfstats.h
+* @brief Statistics collection to support autotune and perf flaoter.
+*
+* $LicenseInfo:firstyear=2022&license=viewerlgpl$
+* Second Life Viewer Source Code
+* Copyright (C) 2022, 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.
+*
+* 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.
+*
+* 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
+*
+* Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
+* $/LicenseInfo$
+*/
+#pragma once
+#ifndef LL_PERFSTATS_H_INCLUDED
+#define LL_PERFSTATS_H_INCLUDED
#include
#include
@@ -35,12 +34,12 @@
#include
#include "lluuid.h"
#include "llfasttimer.h"
-#include "blockingconcurrentqueue.h"
+#include "blockingconcurrentqueue.h" // reinstate faster queues
#include "llapp.h"
#include "llprofiler.h"
#include "pipeline.h"
-// Additional logging options. These can skew inworld numbers so onyl use for debugging and tracking issues
+// Additional logging options. These can skew inworld numbers so onyl use for debugging and tracking issues
#ifdef TRACY_ENABLE
// USAGE_TRACKING - displays overlapping stats that may imply double counting.
// ATTACHMENT_TRACKING - displays detailed tracking info for Avatar and Attachment. very heavy overhead.
@@ -50,11 +49,12 @@
#undef USAGE_TRACKING
#undef ATTACHMENT_TRACKING
#endif
-
+//
extern U32 gFrameCount;
extern LLUUID gAgentID;
-namespace FSPerfStats
+namespace LLPerfStats
{
+// Additional logging options. These can skew inworld numbers so onyl use for debugging and tracking issues
#ifdef USAGE_TRACKING
extern std::atomic inUse;
extern std::atomic inUseAvatar;
@@ -63,10 +63,11 @@ namespace FSPerfStats
extern std::atomic inUseAttachmentRigged;
extern std::atomic inUseAttachmentUnRigged;
#endif
+//
// Note if changing these, they should correspond with the log range of the correpsonding sliders
static constexpr U64 ART_UNLIMITED_NANOS{50000000};
static constexpr U64 ART_MINIMUM_NANOS{100000};
- static constexpr U64 ART_MIN_ADJUST_UP_NANOS{10000};
+ static constexpr U64 ART_MIN_ADJUST_UP_NANOS{5000};
static constexpr U64 ART_MIN_ADJUST_DOWN_NANOS{10000};
static constexpr F32 PREFERRED_DD{180};
@@ -75,6 +76,7 @@ namespace FSPerfStats
static constexpr U32 TUNE_AVATARS_ONLY{0};
static constexpr U32 TUNE_SCENE_AND_AVATARS{1};
+ static constexpr U32 TUNE_SCENE_ONLY{2};
extern F64 cpu_hertz;
@@ -82,6 +84,8 @@ namespace FSPerfStats
extern std::atomic renderAvatarMaxART_ns;
extern bool belowTargetFPS;
extern U32 lastGlobalPrefChange;
+ extern U32 lastSleepedFrame;
+ extern U64 meanFrameTime;
extern std::mutex bufferToggleLock;
enum class ObjType_t{
@@ -103,7 +107,7 @@ namespace FSPerfStats
RENDER_SLEEP,
RENDER_LFS,
RENDER_MESHREPO,
- RENDER_FPSLIMIT,
+ RENDER_FPSLIMIT,// restore this for FS
RENDER_FPS,
RENDER_IDLE,
RENDER_DONE, // toggle buffer & clearbuffer (see processUpdate for hackery)
@@ -154,6 +158,8 @@ namespace FSPerfStats
U32 userTargetFPS{0};
F32 userARTCutoffSliderValue{0};
S32 userTargetReflections{0};
+ bool autoTuneTimeout{true};
+ bool vsyncEnabled{true};
void updateNonImposters(U32 nv){nonImpostors=nv; tuningFlag |= NonImpostors;};
void updateReflectionDetail(S32 nv){reflectionDetail=nv; tuningFlag |= ReflectionDetail;};
@@ -179,7 +185,10 @@ namespace FSPerfStats
extern Tunables tunables;
class StatsRecorder{
+ // we don't want to be using lock based queues
+ // using Queue = LLThreadSafeQueue;
using Queue = moodycamel::BlockingConcurrentQueue;
+ //
public:
static inline StatsRecorder& getInstance()
@@ -189,10 +198,15 @@ namespace FSPerfStats
}
static inline void setFocusAv(const LLUUID& avID){focusAv = avID;};
static inline const LLUUID& getFocusAv(){return focusAv;};
+ static inline void setAutotuneInit(){autotuneInit = true;};
+ // We do not want to use lock based queues
+ // static inline void send(StatsRecord && upd){StatsRecorder::getInstance().q.pushFront(std::move(upd));};
+ // static void endFrame(){StatsRecorder::getInstance().q.pushFront(StatsRecord{StatType_t::RENDER_DONE, ObjType_t::OT_GENERAL, LLUUID::null, LLUUID::null, 0});};
+ // static void clearStats(){StatsRecorder::getInstance().q.pushFront(StatsRecord{StatType_t::RENDER_DONE, ObjType_t::OT_GENERAL, LLUUID::null, LLUUID::null, 1});};
static inline void send(StatsRecord && upd){StatsRecorder::getInstance().q.enqueue(std::move(upd));};
static void endFrame(){StatsRecorder::getInstance().q.enqueue(StatsRecord{StatType_t::RENDER_DONE, ObjType_t::OT_GENERAL, LLUUID::null, LLUUID::null, 0});};
static void clearStats(){StatsRecorder::getInstance().q.enqueue(StatsRecord{StatType_t::RENDER_DONE, ObjType_t::OT_GENERAL, LLUUID::null, LLUUID::null, 1});};
-
+ //
static inline void setEnabled(bool on_or_off){collectionEnabled=on_or_off;};
static inline void enable() { collectionEnabled=true; };
static inline void disable() { collectionEnabled=false; };
@@ -222,14 +236,17 @@ namespace FSPerfStats
StatsRecorder();
static int countNearbyAvatars(S32 distance);
+ static U64 getMeanTotalFrameTime();
+ static void updateMeanFrameTime(U64 tot_frame_time_raw);
// StatsArray is a uint64_t for each possible statistic type.
- using StatsArray = std::array(FSPerfStats::StatType_t::STATS_COUNT)>;
- using StatsMap = std::unordered_map;
- using StatsTypeMatrix = std::array(FSPerfStats::ObjType_t::OT_COUNT)>;
- using StatsSummaryArray = std::array(FSPerfStats::ObjType_t::OT_COUNT)>;
+ using StatsArray = std::array(LLPerfStats::StatType_t::STATS_COUNT)>;
+ using StatsMap = std::unordered_map; //
+ using StatsTypeMatrix = std::array(LLPerfStats::ObjType_t::OT_COUNT)>;
+ using StatsSummaryArray = std::array(LLPerfStats::ObjType_t::OT_COUNT)>;
static std::atomic writeBuffer;
static LLUUID focusAv;
+ static bool autotuneInit;
static std::array statsDoubleBuffer;
static std::array max;
static std::array sum;
@@ -264,12 +281,13 @@ namespace FSPerfStats
auto& avKey{upd.avID};
auto type {upd.statType};
auto val {upd.time};
-
+ // markup to support coverage testing on stats collection
#ifdef TRACY_ENABLE
LL_PROFILE_ZONE_TEXT(key.toStringFast(obstr), 36);
LL_PROFILE_ZONE_TEXT(avKey.toStringFast(avstr), 36);
LL_PROFILE_ZONE_NUM(val);
#endif
+ //
if (ot == ObjType_t::OT_GENERAL)
{
@@ -346,8 +364,24 @@ namespace FSPerfStats
while( enabled() && !LLApp::isExiting() )
{
+ // We don't want these queues
+ // auto count = 0;
+ // while (count < 10)
+ // {
+ // if (instance.q.tryPopFor(std::chrono::milliseconds(10), upd[count]))
+ // {
+ // count++;
+ // }
+ // else
+ // {
+ // break;
+ // }
+ // }
+ // //LL_PROFILER_THREAD_BEGIN("PerfStats");
+
auto count = instance.q.wait_dequeue_bulk_timed(upd, 10, std::chrono::milliseconds(10));
LL_PROFILER_THREAD_BEGIN("PerfStats");
+ //
if(count)
{
// LL_INFOS("perfstats") << "processing " << count << " updates." << LL_ENDL;
@@ -356,7 +390,7 @@ namespace FSPerfStats
instance.processUpdate(upd[i]);
}
}
- LL_PROFILER_THREAD_END("PerfStats");
+ LL_PROFILER_THREAD_END("PerfStats"); //
}
}
@@ -384,29 +418,35 @@ namespace FSPerfStats
start{LLTrace::BlockTimer::getCPUClockCount64()},
stat{type, ObjTypeDiscriminator, std::move(av), std::move(id), 0, isRiggedAtt, isHUDAtt}
{
+ // extra profiling coverage tracking
+ // LL_PROFILE_ZONE_COLOR(tracy::Color::Orange);
LL_PROFILE_ZONE_COLOR(tracy::Color::Orange);
#ifdef USAGE_TRACKING
if(stat.objType == FSPerfStats::ObjType_t::OT_ATTACHMENT)
{
- if(!stat.isRigged && FSPerfStats::inUseAvatar){LL_PROFILE_ZONE_TEXT("OVERLAP AVATAR",14);}
+ LL_PROFILE_PLOT_CONFIG_SQUARE("InUse");
+ LL_PROFILE_PLOT_CONFIG_SQUARE("InUseAttachment");
+ LL_PROFILE_PLOT_CONFIG_SQUARE("InUseAttachmentRigged");
+ LL_PROFILE_PLOT_CONFIG_SQUARE("InUseAttachmentUnRigged");
- LL_PROFILE_PLOT_SQ("InUse", (int64_t)FSPerfStats::inUse, (int64_t)FSPerfStats::inUse+1);
+ if(!stat.isRigged && FSPerfStats::inUseAvatar){LL_PROFILE_ZONE_TEXT("OVERLAP AVATAR",14);}
FSPerfStats::inUse++;
- LL_PROFILE_PLOT_SQ("InUseAttachment", (int64_t)FSPerfStats::inUseAttachment, (int64_t)FSPerfStats::inUseAttachment+1);
+ LL_PROFILE_PLOT("InUse", (int64_t)FSPerfStats::inUse);
FSPerfStats::inUseAttachment++;
+ LL_PROFILE_PLOT("InUseAttachment", (int64_t)FSPerfStats::inUseAttachment);
if (stat.isRigged)
{
- LL_PROFILE_PLOT_SQ("InUseAttachmentRigged", (int64_t)FSPerfStats::inUseAttachmentRigged,(int64_t)FSPerfStats::inUseAttachmentRigged+1);
FSPerfStats::inUseAttachmentRigged++;
+ LL_PROFILE_PLOT("InUseAttachmentRigged", (int64_t)FSPerfStats::inUseAttachmentRigged);
}
else
{
- LL_PROFILE_PLOT_SQ("InUseAttachmentUnRigged", (int64_t)FSPerfStats::inUseAttachmentUnRigged,(int64_t)FSPerfStats::inUseAttachmentUnRigged+1);
FSPerfStats::inUseAttachmentUnRigged++;
+ LL_PROFILE_PLOT("InUseAttachmentUnRigged", (int64_t)FSPerfStats::inUseAttachmentUnRigged);
}
}
#endif
-
+ //
};
template < ObjType_t OD = ObjTypeDiscriminator,
@@ -414,71 +454,75 @@ namespace FSPerfStats
explicit RecordTime( StatType_t type ):RecordTime(LLUUID::null, LLUUID::null, type )
{
LL_PROFILE_ZONE_SCOPED_CATEGORY_STATS;
+ // extra profiling coverage tracking
#ifdef USAGE_TRACKING
- LL_PROFILE_PLOT_SQ("InUseScene", (int64_t)FSPerfStats::inUseScene, (int64_t)FSPerfStats::inUseScene+1);
- FSPerfStats::inUseScene++;
- LL_PROFILE_PLOT_SQ("InUse", (int64_t)FSPerfStats::inUse, (int64_t)FSPerfStats::inUse+1);
- FSPerfStats::inUse++;
+ LLPerfStats::inUseScene++;
+ LL_PROFILE_PLOT("InUseScene", (int64_t)LLPerfStats::inUseScene);
+ LLPerfStats::inUse++;
+ LL_PROFILE_PLOT("InUse", (int64_t)LLPerfStats::inUse);
#endif
+ //
};
template < ObjType_t OD = ObjTypeDiscriminator,
std::enable_if_t * = nullptr>
RecordTime( const LLUUID & av, StatType_t type ):RecordTime(std::move(av), LLUUID::null, type)
{
+ // extra profiling coverage tracking
+ // LL_PROFILE_ZONE_COLOR(tracy::Color::Purple)
LL_PROFILE_ZONE_COLOR(tracy::Color::Purple);
-
#ifdef USAGE_TRACKING
- if(FSPerfStats::inUseAvatar){LL_PROFILE_ZONE_TEXT("OVERLAP AVATAR",14);}
-
- LL_PROFILE_PLOT_SQ("InUseAv", (int64_t)FSPerfStats::inUseAvatar, (int64_t)FSPerfStats::inUseAvatar+1);
+ if(LLPerfStats::inUseAvatar){LL_PROFILE_ZONE_TEXT("OVERLAP AVATAR",14);}
FSPerfStats::inUseAvatar++;
- LL_PROFILE_PLOT_SQ("InUse", (int64_t)FSPerfStats::inUse, (int64_t)FSPerfStats::inUse+1);
- FSPerfStats::inUse++;
+ LL_PROFILE_PLOT("InUseAv", (int64_t)LLPerfStats::inUseAvatar);
+ LLPerfStats::inUse++;
+ LL_PROFILE_PLOT("InUse", (int64_t)LLPerfStats::inUse);
#endif
-
+ //
};
~RecordTime()
{
- if(!FSPerfStats::StatsRecorder::enabled())
+ if(!LLPerfStats::StatsRecorder::enabled())
{
return;
}
- LL_PROFILE_ZONE_COLOR(tracy::Color::Red);
+ //LL_PROFILE_ZONE_COLOR(tracy::Color::Red);
+ // extra profiling coverage tracking
#ifdef USAGE_TRACKING
- LL_PROFILE_PLOT_SQ("InUse", (int64_t)FSPerfStats::inUse,(int64_t)FSPerfStats::inUse-1);
--FSPerfStats::inUse;
+ LL_PROFILE_PLOT("InUse", (int64_t)FSPerfStats::inUse);
if (stat.objType == FSPerfStats::ObjType_t::OT_ATTACHMENT)
{
- LL_PROFILE_PLOT_SQ("InUseAttachment", (int64_t)FSPerfStats::inUseAttachment,(int64_t)FSPerfStats::inUseAttachment-1);
--FSPerfStats::inUseAttachment;
+ LL_PROFILE_PLOT("InUseAttachment", (int64_t)FSPerfStats::inUseAttachment);
if (stat.isRigged)
{
- LL_PROFILE_PLOT_SQ("InUseAttachmentRigged", (int64_t)FSPerfStats::inUseAttachmentRigged,(int64_t)FSPerfStats::inUseAttachmentRigged-1);
--FSPerfStats::inUseAttachmentRigged;
+ LL_PROFILE_PLOT("InUseAttachmentRigged", (int64_t)FSPerfStats::inUseAttachmentRigged);
}
else
{
- LL_PROFILE_PLOT_SQ("InUseAttachmentUnRigged", (int64_t)FSPerfStats::inUseAttachmentUnRigged,(int64_t)FSPerfStats::inUseAttachmentUnRigged-1);
--FSPerfStats::inUseAttachmentUnRigged;
+ LL_PROFILE_PLOT("InUseAttachmentUnRigged", (int64_t)FSPerfStats::inUseAttachmentUnRigged);
}
}
if (stat.objType == FSPerfStats::ObjType_t::OT_GENERAL)
{
- LL_PROFILE_PLOT_SQ("InUseScene", (int64_t)FSPerfStats::inUseScene,(int64_t)FSPerfStats::inUseScene-1);
--FSPerfStats::inUseScene;
+ LL_PROFILE_PLOT("InUseScene", (int64_t)FSPerfStats::inUseScene);
}
if( stat.objType == FSPerfStats::ObjType_t::OT_AVATAR )
{
- LL_PROFILE_PLOT_SQ("InUseAv", (int64_t)FSPerfStats::inUseAvatar, (int64_t)FSPerfStats::inUseAvatar-1);
--FSPerfStats::inUseAvatar;
+ LL_PROFILE_PLOT("InUseAv", (int64_t)FSPerfStats::inUseAvatar);
}
#endif
+ //
stat.time = LLTrace::BlockTimer::getCPUClockCount64() - start;
-
+ // extra profiling coverage tracking
#ifdef ATTACHMENT_TRACKING
static char obstr[36];
static char avstr[36];
@@ -487,26 +531,25 @@ namespace FSPerfStats
LL_PROFILE_ZONE_TEXT(stat.objID.toStringFast(obstr), 36);
LL_PROFILE_ZONE_NUM(stat.time);
#endif
-
+ //
StatsRecorder::send(std::move(stat));
};
};
-
- inline double raw_to_ns(U64 raw) { return (static_cast(raw) * 1000000000.0) / FSPerfStats::cpu_hertz; };
- inline double raw_to_us(U64 raw) { return (static_cast(raw) * 1000000.0) / FSPerfStats::cpu_hertz; };
- inline double raw_to_ms(U64 raw) { return (static_cast(raw) * 1000.0) / FSPerfStats::cpu_hertz; };
+ inline double raw_to_ns(U64 raw) { return (static_cast(raw) * 1000000000.0) / LLPerfStats::cpu_hertz; };
+ inline double raw_to_us(U64 raw) { return (static_cast(raw) * 1000000.0) / LLPerfStats::cpu_hertz; };
+ inline double raw_to_ms(U64 raw) { return (static_cast(raw) * 1000.0) / LLPerfStats::cpu_hertz; };
using RecordSceneTime = RecordTime;
using RecordAvatarTime = RecordTime;
using RecordAttachmentTime = RecordTime;
using RecordHudAttachmentTime = RecordTime;
-};// namespace FSPerfStats
+};// namespace LLPerfStats
// helper functions
-using RATptr = std::unique_ptr;
-using RSTptr = std::unique_ptr;
+using RATptr = std::unique_ptr;
+using RSTptr = std::unique_ptr;
template
static inline void trackAttachments(const T * vobj, bool isRigged, RATptr* ratPtrp)
@@ -530,6 +573,7 @@ static inline void trackAttachments(const T * vobj, bool isRigged, RATptr* ratPt
auto& obj = rootAtt->getAttachmentItemID();
if (!*ratPtrp || (*ratPtrp)->stat.objID != obj || (*ratPtrp)->stat.avID != av)
{
+ // extra profiling coverage tracking
#if TRACY_ENABLE && defined(ATTACHMENT_TRACKING)
LL_PROFILE_ZONE_NAMED_COLOR( "trackAttachments:new", tracy::Color::Red);
auto& str = rootAtt->getAttachmentItemName();
@@ -542,15 +586,16 @@ static inline void trackAttachments(const T * vobj, bool isRigged, RATptr* ratPt
LL_PROFILE_ZONE_TEXT( avStr, 36);
LL_PROFILE_ZONE_TEXT( obStr, 4);
#endif
+ //
if (*ratPtrp)
{
// deliberately reset to ensure destruction before construction of replacement.
ratPtrp->reset();
};
- *ratPtrp = std::make_unique(
+ *ratPtrp = std::make_unique(
av,
obj,
- ( LLPipeline::sShadowRender?FSPerfStats::StatType_t::RENDER_SHADOWS : FSPerfStats::StatType_t::RENDER_GEOMETRY ),
+ ( LLPipeline::sShadowRender?LLPerfStats::StatType_t::RENDER_SHADOWS : LLPerfStats::StatType_t::RENDER_GEOMETRY ),
isRigged,
rootAtt->isHUDAttachment());
}
@@ -558,4 +603,4 @@ static inline void trackAttachments(const T * vobj, bool isRigged, RATptr* ratPt
return;
};
-#endif
\ No newline at end of file
+#endif
diff --git a/indra/newview/llpresetsmanager.cpp b/indra/newview/llpresetsmanager.cpp
index 800b5b34db..1d21442d89 100644
--- a/indra/newview/llpresetsmanager.cpp
+++ b/indra/newview/llpresetsmanager.cpp
@@ -42,7 +42,7 @@
#include "llagentcamera.h"
#include "llfile.h"
#include "quickprefs.h"
-#include "fsperfstats.h" // avoid triggering reloads while autotuning
+#include "llperfstats.h"
LLPresetsManager::LLPresetsManager()
// Graphic preset controls independent from XUI
@@ -723,7 +723,7 @@ void LLPresetsManager::handleGraphicPresetControlChanged(LLControlVariablePtr co
if (!mIsLoadingPreset &&
(!mIsDrawDistanceSteppingActive || control->getName() != "RenderFarClip") &&
- (!FSPerfStats::tunables.userAutoTuneEnabled) )
+ (!LLPerfStats::tunables.userAutoTuneEnabled) )
{
LL_DEBUGS() << "Trigger graphic preset control changed signal" << LL_ENDL;
diff --git a/indra/newview/llstartup.cpp b/indra/newview/llstartup.cpp
index a91d3d04b6..9c19895390 100644
--- a/indra/newview/llstartup.cpp
+++ b/indra/newview/llstartup.cpp
@@ -212,8 +212,8 @@
#include "llenvironment.h"
#include "llstacktrace.h"
-#include "fsperfstats.h"
#include "threadpool.h"
+#include "llperfstats.h"
#if LL_WINDOWS
@@ -2215,9 +2215,8 @@ bool idle_startup()
update_static_eyes();
//
- //
- gAgent.addRegionChangedCallback(boost::bind(&FSPerfStats::StatsRecorder::clearStats));
- //
+
+ gAgent.addRegionChangedCallback(boost::bind(&LLPerfStats::StatsRecorder::clearStats));
// *Note: this is where gWorldMap used to be initialized.
@@ -3084,7 +3083,7 @@ bool idle_startup()
if (STATE_CLEANUP == LLStartUp::getStartupState())
{
- set_startup_status(1.0, "", "");
+ set_startup_status(1.0, "", "");
display_startup();
if (!mBenefitsSuccessfullyInit)
@@ -3211,6 +3210,8 @@ bool idle_startup()
LLUIUsage::instance().clear();
+ LLPerfStats::StatsRecorder::setAutotuneInit();
+
// FIRE-6643 Display MOTD when login screens are disabled
if (gSavedSettings.getBOOL("FSDisableLoginScreens"))
{
@@ -4387,10 +4388,6 @@ bool process_login_success_response(U32 &first_sim_size_x, U32 &first_sim_size_y
// unpack login data needed by the application
text = response["agent_id"].asString();
if(!text.empty()) gAgentID.set(text);
- // Performance floater initialisation
- FSPerfStats::StatsRecorder::setEnabled(gSavedSettings.getBOOL("FSPerfStatsCaptureEnabled"));
- FSPerfStats::StatsRecorder::setFocusAv(gAgentID);
- //
// gDebugInfo["AgentID"] = text;
// [SL:KB] - Patch: Viewer-CrashReporting | Checked: 2010-11-16 (Catznip-2.6.0a) | Added: Catznip-2.4.0b
if (gCrashSettings.getBOOL("CrashSubmitName"))
@@ -4400,6 +4397,9 @@ bool process_login_success_response(U32 &first_sim_size_x, U32 &first_sim_size_y
}
// [/SL:KB]
+ LLPerfStats::StatsRecorder::setEnabled(gSavedSettings.getBOOL("PerfStatsCaptureEnabled"));
+ LLPerfStats::StatsRecorder::setFocusAv(gAgentID);
+
// Agent id needed for parcel info request in LLUrlEntryParcel
// to resolve parcel name.
LLUrlEntryParcel::setAgentID(gAgentID);
diff --git a/indra/newview/lltoolbarview.cpp b/indra/newview/lltoolbarview.cpp
index 3c73ed7857..bbeab246b6 100644
--- a/indra/newview/lltoolbarview.cpp
+++ b/indra/newview/lltoolbarview.cpp
@@ -44,6 +44,7 @@
#include "llagent.h" // HACK for destinations guide on startup
#include "llfloaterreg.h" // HACK for destinations guide on startup
#include "llviewercontrol.h" // HACK for destinations guide on startup
+#include "llinventorymodel.h" // HACK to disable starter avatars button for NUX
#include
@@ -382,6 +383,25 @@ bool LLToolBarView::loadToolbars(bool force_default)
}
}
}
+
+ // SL-18581: Don't show the starter avatar toolbar button for NUX users
+ LLViewerInventoryCategory* my_outfits_cat = gInventory.getCategory(gInventory.findCategoryUUIDForType(LLFolderType::FT_MY_OUTFITS));
+ if (gAgent.isFirstLogin())
+ {
+ LL_WARNS() << "First login: checking for NUX user." << LL_ENDL;
+ if (my_outfits_cat != NULL && my_outfits_cat->getDescendentCount() > 0)
+ {
+ LL_WARNS() << "First login: My Outfits folder is not empty, removing the avatar picker button." << LL_ENDL;
+ for (S32 i = LLToolBarEnums::TOOLBAR_FIRST; i <= LLToolBarEnums::TOOLBAR_LAST; i++)
+ {
+ if (mToolbars[i])
+ {
+ mToolbars[i]->removeCommand(LLCommandId("avatar"));
+ }
+ }
+ }
+ }
+
mToolbarsLoaded = true;
return true;
}
diff --git a/indra/newview/llviewercontrol.cpp b/indra/newview/llviewercontrol.cpp
index 5c00375a93..85203f2503 100644
--- a/indra/newview/llviewercontrol.cpp
+++ b/indra/newview/llviewercontrol.cpp
@@ -85,6 +85,7 @@
#include "llspellcheck.h"
#include "llslurl.h"
#include "llstartup.h"
+#include "llperfstats.h"
// [RLVa:KB] - Checked: 2015-12-27 (RLVa-1.5.0)
#include "llvisualeffect.h"
#include "rlvactions.h"
@@ -112,7 +113,6 @@
#include "llviewerregion.h"
#include "NACLantispam.h"
#include "nd/ndlogthrottle.h"
-#include "fsperfstats.h"
// Run Prio 0 default bento pose in the background to fix splayed hands, open mouths, etc.
#include "llanimationstates.h"
@@ -259,6 +259,12 @@ bool handleSetShaderChanged(const LLSD& newvalue)
return true;
}
+static bool handleShadowDetailChanged(const LLSD& newvalue)
+{
+ gPipeline.handleShadowDetailChanged();
+ return true;
+}
+
static bool handleRenderPerfTestChanged(const LLSD& newvalue)
{
bool status = !newvalue.asBoolean();
@@ -353,8 +359,15 @@ static bool handleAnisotropicChanged(const LLSD& newvalue)
static bool handleVSyncChanged(const LLSD& newvalue)
{
+ LLPerfStats::tunables.vsyncEnabled = newvalue.asBoolean();
gViewerWindow->getWindow()->toggleVSync(newvalue.asBoolean());
+ if(newvalue.asBoolean() == true)
+ {
+ U32 current_target = gSavedSettings.getU32("TargetFPS");
+ gSavedSettings.setU32("TargetFPS", std::min((U32)gViewerWindow->getWindow()->getRefreshRate(), current_target));
+ }
+
return true;
}
@@ -1074,68 +1087,76 @@ void handleDiskCacheSizeChanged(const LLSD& newValue)
}
//
-// perrf floater stuffs
void handleTargetFPSChanged(const LLSD& newValue)
{
- const auto targetFPS = gSavedSettings.getU32("FSTargetFPS");
- FSPerfStats::tunables.userTargetFPS = targetFPS;
-}
-// perf floater stuffs
-void handleAutoTuneLockChanged(const LLSD& newValue)
-{
- const auto newval = gSavedSettings.getBOOL("FSAutoTuneLock");
- FSPerfStats::tunables.userAutoTuneLock = newval;
+ const auto targetFPS = gSavedSettings.getU32("TargetFPS");
+
+ U32 frame_rate_limit = gViewerWindow->getWindow()->getRefreshRate();
+ if(LLPerfStats::tunables.vsyncEnabled && (targetFPS > frame_rate_limit))
+ {
+ gSavedSettings.setU32("TargetFPS", std::min(frame_rate_limit, targetFPS));
+ }
+ else
+ {
+ LLPerfStats::tunables.userTargetFPS = targetFPS;
+ }
+}
+
+void handleAutoTuneLockChanged(const LLSD& newValue)
+{
+ const auto newval = gSavedSettings.getBOOL("AutoTuneLock");
+ LLPerfStats::tunables.userAutoTuneLock = newval;
+
+ gSavedSettings.setBOOL("AutoTuneFPS", newval);
}
-// perrf floater stuffs
void handleAutoTuneFPSChanged(const LLSD& newValue)
{
- const auto newval = gSavedSettings.getBOOL("FSAutoTuneFPS");
- FSPerfStats::tunables.userAutoTuneEnabled = newval;
- if(newval && FSPerfStats::renderAvatarMaxART_ns == 0) // If we've enabled autotune we override "unlimited" to max
- {
- gSavedSettings.setF32("FSRenderAvatarMaxART",log10(FSPerfStats::ART_UNLIMITED_NANOS-1000));//triggers callback to update static var
- }
+ const auto newval = gSavedSettings.getBOOL("AutoTuneFPS");
+ LLPerfStats::tunables.userAutoTuneEnabled = newval;
+ if(newval && LLPerfStats::renderAvatarMaxART_ns == 0) // If we've enabled autotune we override "unlimited" to max
+ {
+ gSavedSettings.setF32("RenderAvatarMaxART",log10(LLPerfStats::ART_UNLIMITED_NANOS-1000));//triggers callback to update static var
+ }
}
void handleRenderAvatarMaxARTChanged(const LLSD& newValue)
{
- FSPerfStats::tunables.updateRenderCostLimitFromSettings();
+ LLPerfStats::tunables.updateRenderCostLimitFromSettings();
}
void handleUserTargetDrawDistanceChanged(const LLSD& newValue)
{
- const auto newval = gSavedSettings.getF32("FSAutoTuneRenderFarClipTarget");
- FSPerfStats::tunables.userTargetDrawDistance = newval;
+ const auto newval = gSavedSettings.getF32("AutoTuneRenderFarClipTarget");
+ LLPerfStats::tunables.userTargetDrawDistance = newval;
}
void handleUserTargetReflectionsChanged(const LLSD& newValue)
{
- const auto newval = gSavedSettings.getS32("FSUserTargetReflections");
- FSPerfStats::tunables.userTargetReflections = newval;
+ const auto newval = gSavedSettings.getS32("UserTargetReflections");
+ LLPerfStats::tunables.userTargetReflections = newval;
}
void handlePerformanceStatsEnabledChanged(const LLSD& newValue)
{
- const auto newval = gSavedSettings.getBOOL("FSPerfStatsCaptureEnabled");
- FSPerfStats::StatsRecorder::setEnabled(newval);
+ const auto newval = gSavedSettings.getBOOL("PerfStatsCaptureEnabled");
+ LLPerfStats::StatsRecorder::setEnabled(newval);
}
void handleUserImpostorByDistEnabledChanged(const LLSD& newValue)
{
- const auto newval = gSavedSettings.getBOOL("FSAutoTuneImpostorByDistEnabled");
- FSPerfStats::tunables.userImpostorDistanceTuningEnabled = newval;
+ const auto newval = gSavedSettings.getBOOL("AutoTuneImpostorByDistEnabled");
+ LLPerfStats::tunables.userImpostorDistanceTuningEnabled = newval;
}
void handleUserImpostorDistanceChanged(const LLSD& newValue)
{
- const auto newval = gSavedSettings.getF32("FSAutoTuneImpostorFarAwayDistance");
- FSPerfStats::tunables.userImpostorDistance = newval;
+ const auto newval = gSavedSettings.getF32("AutoTuneImpostorFarAwayDistance");
+ LLPerfStats::tunables.userImpostorDistance = newval;
}
void handleFPSTuningStrategyChanged(const LLSD& newValue)
{
- const auto newval = gSavedSettings.getU32("FSTuningFPSStrategy");
- FSPerfStats::tunables.userFPSTuningStrategy = newval;
+ const auto newval = gSavedSettings.getU32("TuningFPSStrategy");
+ LLPerfStats::tunables.userFPSTuningStrategy = newval;
}
-//
// FIRE-6809: Quickly moving the bandwidth slider has no effect
void handleBandwidthChanged(const LLSD& newValue)
@@ -1188,146 +1209,147 @@ void setting_setup_signal_listener(LLControlGroup& group, const std::string& set
void settings_setup_listeners()
{
setting_setup_signal_listener(gSavedSettings, "FirstPersonAvatarVisible", handleRenderAvatarMouselookChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderFarClip", handleRenderFarClipChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderTerrainDetail", handleTerrainDetailChanged);
- setting_setup_signal_listener(gSavedSettings, "OctreeStaticObjectSizeFactor", handleRepartition);
- setting_setup_signal_listener(gSavedSettings, "OctreeDistanceFactor", handleRepartition);
- setting_setup_signal_listener(gSavedSettings, "OctreeMaxNodeCapacity", handleRepartition);
- setting_setup_signal_listener(gSavedSettings, "OctreeAlphaDistanceFactor", handleRepartition);
- setting_setup_signal_listener(gSavedSettings, "OctreeAttachmentSizeFactor", handleRepartition);
- setting_setup_signal_listener(gSavedSettings, "RenderMaxTextureIndex", handleSetShaderChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderUseTriStrips", handleResetVertexBuffersChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderUIBuffer", handleWindowResized);
- setting_setup_signal_listener(gSavedSettings, "RenderDepthOfField", handleReleaseGLBufferChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderFSAASamples", handleReleaseGLBufferChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderSpecularResX", handleLUTBufferChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderSpecularResY", handleLUTBufferChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderSpecularExponent", handleLUTBufferChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderAnisotropic", handleAnisotropicChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderShadowResolutionScale", handleShadowsResized);
- setting_setup_signal_listener(gSavedSettings, "RenderGlow", handleReleaseGLBufferChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderGlow", handleSetShaderChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderGlowResolutionPow", handleReleaseGLBufferChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderAvatarCloth", handleSetShaderChanged);
- setting_setup_signal_listener(gSavedSettings, "WindLightUseAtmosShaders", handleSetShaderChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderGammaFull", handleSetShaderChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderVolumeLODFactor", handleVolumeLODChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderAvatarLODFactor", handleAvatarLODChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderAvatarPhysicsLODFactor", handleAvatarPhysicsLODChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderTerrainLODFactor", handleTerrainLODChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderTreeLODFactor", handleTreeLODChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderFlexTimeFactor", handleFlexLODChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderGamma", handleGammaChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderFogRatio", handleFogRatioChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderMaxPartCount", handleMaxPartCountChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderDynamicLOD", handleRenderDynamicLODChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderLocalLights", handleRenderLocalLightsChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderDebugTextureBind", handleResetVertexBuffersChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderAutoMaskAlphaDeferred", handleResetVertexBuffersChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderAutoMaskAlphaNonDeferred", handleResetVertexBuffersChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderObjectBump", handleRenderBumpChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderMaxVBOSize", handleResetVertexBuffersChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderFarClip", handleRenderFarClipChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderTerrainDetail", handleTerrainDetailChanged);
+ setting_setup_signal_listener(gSavedSettings, "OctreeStaticObjectSizeFactor", handleRepartition);
+ setting_setup_signal_listener(gSavedSettings, "OctreeDistanceFactor", handleRepartition);
+ setting_setup_signal_listener(gSavedSettings, "OctreeMaxNodeCapacity", handleRepartition);
+ setting_setup_signal_listener(gSavedSettings, "OctreeAlphaDistanceFactor", handleRepartition);
+ setting_setup_signal_listener(gSavedSettings, "OctreeAttachmentSizeFactor", handleRepartition);
+ setting_setup_signal_listener(gSavedSettings, "RenderMaxTextureIndex", handleSetShaderChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderUseTriStrips", handleResetVertexBuffersChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderUIBuffer", handleWindowResized);
+ setting_setup_signal_listener(gSavedSettings, "RenderDepthOfField", handleReleaseGLBufferChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderFSAASamples", handleReleaseGLBufferChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderSpecularResX", handleLUTBufferChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderSpecularResY", handleLUTBufferChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderSpecularExponent", handleLUTBufferChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderAnisotropic", handleAnisotropicChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderShadowResolutionScale", handleShadowsResized);
+ setting_setup_signal_listener(gSavedSettings, "RenderGlow", handleReleaseGLBufferChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderGlow", handleSetShaderChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderGlowResolutionPow", handleReleaseGLBufferChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderAvatarCloth", handleSetShaderChanged);
+ setting_setup_signal_listener(gSavedSettings, "WindLightUseAtmosShaders", handleSetShaderChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderGammaFull", handleSetShaderChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderVolumeLODFactor", handleVolumeLODChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderAvatarLODFactor", handleAvatarLODChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderAvatarPhysicsLODFactor", handleAvatarPhysicsLODChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderTerrainLODFactor", handleTerrainLODChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderTreeLODFactor", handleTreeLODChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderFlexTimeFactor", handleFlexLODChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderGamma", handleGammaChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderFogRatio", handleFogRatioChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderMaxPartCount", handleMaxPartCountChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderDynamicLOD", handleRenderDynamicLODChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderLocalLights", handleRenderLocalLightsChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderDebugTextureBind", handleResetVertexBuffersChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderAutoMaskAlphaDeferred", handleResetVertexBuffersChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderAutoMaskAlphaNonDeferred", handleResetVertexBuffersChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderObjectBump", handleRenderBumpChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderMaxVBOSize", handleResetVertexBuffersChanged);
setting_setup_signal_listener(gSavedSettings, "RenderVSyncEnable", handleVSyncChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderDeferredNoise", handleReleaseGLBufferChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderDebugPipeline", handleRenderDebugPipelineChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderResolutionDivisor", handleRenderResolutionDivisorChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderDeferredNoise", handleReleaseGLBufferChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderDebugPipeline", handleRenderDebugPipelineChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderResolutionDivisor", handleRenderResolutionDivisorChanged);
// [SL:KB] - Patch: Settings-RenderResolutionMultiplier | Checked: Catznip-5.4
setting_setup_signal_listener(gSavedSettings, "RenderResolutionMultiplier", handleRenderResolutionDivisorChanged);
// [/SL:KB]
- setting_setup_signal_listener(gSavedSettings, "RenderDeferred", handleRenderDeferredChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderShadowDetail", handleSetShaderChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderDeferredSSAO", handleSetShaderChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderPerformanceTest", handleRenderPerfTestChanged);
- setting_setup_signal_listener(gSavedSettings, "TextureMemory", handleVideoMemoryChanged);
- setting_setup_signal_listener(gSavedSettings, "ChatConsoleFontSize", handleChatFontSizeChanged);
- setting_setup_signal_listener(gSavedSettings, "ChatPersistTime", handleChatPersistTimeChanged);
- setting_setup_signal_listener(gSavedSettings, "ConsoleMaxLines", handleConsoleMaxLinesChanged);
- setting_setup_signal_listener(gSavedSettings, "UploadBakedTexOld", handleUploadBakedTexOldChanged);
- setting_setup_signal_listener(gSavedSettings, "UseOcclusion", handleUseOcclusionChanged);
- setting_setup_signal_listener(gSavedSettings, "AudioLevelMaster", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "AudioLevelSFX", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "AudioLevelUI", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "AudioLevelAmbient", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "AudioLevelMusic", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "AudioLevelMedia", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "AudioLevelVoice", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "AudioLevelDoppler", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "AudioLevelRolloff", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "AudioLevelUnderwaterRolloff", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "MuteAudio", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "MuteMusic", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "MuteMedia", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "MuteVoice", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "MuteAmbient", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "MuteUI", handleAudioVolumeChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderVBOEnable", handleResetVertexBuffersChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderUseVAO", handleResetVertexBuffersChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderVBOMappingDisable", handleResetVertexBuffersChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderUseStreamVBO", handleResetVertexBuffersChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderPreferStreamDraw", handleResetVertexBuffersChanged);
- setting_setup_signal_listener(gSavedSettings, "WLSkyDetail", handleWLSkyDetailChanged);
- setting_setup_signal_listener(gSavedSettings, "JoystickAxis0", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "JoystickAxis1", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "JoystickAxis2", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "JoystickAxis3", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "JoystickAxis4", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "JoystickAxis5", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "JoystickAxis6", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale0", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale1", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale2", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale3", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale4", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale5", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale6", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone0", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone1", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone2", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone3", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone4", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone5", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone6", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "AvatarAxisScale0", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "AvatarAxisScale1", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "AvatarAxisScale2", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "AvatarAxisScale3", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "AvatarAxisScale4", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "AvatarAxisScale5", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "AvatarAxisDeadZone0", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "AvatarAxisDeadZone1", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "AvatarAxisDeadZone2", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "AvatarAxisDeadZone3", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "AvatarAxisDeadZone4", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "AvatarAxisDeadZone5", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "BuildAxisScale0", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "BuildAxisScale1", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "BuildAxisScale2", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "BuildAxisScale3", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "BuildAxisScale4", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "BuildAxisScale5", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "BuildAxisDeadZone0", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "BuildAxisDeadZone1", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "BuildAxisDeadZone2", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "BuildAxisDeadZone3", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "BuildAxisDeadZone4", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "BuildAxisDeadZone5", handleJoystickChanged);
- setting_setup_signal_listener(gSavedSettings, "DebugViews", handleDebugViewsChanged);
- setting_setup_signal_listener(gSavedSettings, "UserLogFile", handleLogFileChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderHideGroupTitle", handleHideGroupTitleChanged);
- setting_setup_signal_listener(gSavedSettings, "HighResSnapshot", handleHighResSnapshotChanged);
- setting_setup_signal_listener(gSavedSettings, "EnableVoiceChat", handleVoiceClientPrefsChanged);
- setting_setup_signal_listener(gSavedSettings, "PTTCurrentlyEnabled", handleVoiceClientPrefsChanged);
- setting_setup_signal_listener(gSavedSettings, "PushToTalkButton", handleVoiceClientPrefsChanged);
- setting_setup_signal_listener(gSavedSettings, "PushToTalkToggle", handleVoiceClientPrefsChanged);
- setting_setup_signal_listener(gSavedSettings, "VoiceEarLocation", handleVoiceClientPrefsChanged);
- setting_setup_signal_listener(gSavedSettings, "VoiceInputAudioDevice", handleVoiceClientPrefsChanged);
- setting_setup_signal_listener(gSavedSettings, "VoiceOutputAudioDevice", handleVoiceClientPrefsChanged);
- setting_setup_signal_listener(gSavedSettings, "AudioLevelMic", handleVoiceClientPrefsChanged);
- setting_setup_signal_listener(gSavedSettings, "LipSyncEnabled", handleVoiceClientPrefsChanged);
- setting_setup_signal_listener(gSavedSettings, "VelocityInterpolate", handleVelocityInterpolate);
- setting_setup_signal_listener(gSavedSettings, "QAMode", show_debug_menus);
- setting_setup_signal_listener(gSavedSettings, "UseDebugMenus", show_debug_menus);
- setting_setup_signal_listener(gSavedSettings, "AgentPause", toggle_agent_pause);
+ setting_setup_signal_listener(gSavedSettings, "RenderDeferred", handleRenderDeferredChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderShadowDetail", handleShadowDetailChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderDeferredSSAO", handleSetShaderChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderPerformanceTest", handleRenderPerfTestChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderHiDPI", handleRenderHiDPIChanged);
+ setting_setup_signal_listener(gSavedSettings, "TextureMemory", handleVideoMemoryChanged);
+ setting_setup_signal_listener(gSavedSettings, "ChatConsoleFontSize", handleChatFontSizeChanged);
+ setting_setup_signal_listener(gSavedSettings, "ChatPersistTime", handleChatPersistTimeChanged);
+ setting_setup_signal_listener(gSavedSettings, "ConsoleMaxLines", handleConsoleMaxLinesChanged);
+ setting_setup_signal_listener(gSavedSettings, "UploadBakedTexOld", handleUploadBakedTexOldChanged);
+ setting_setup_signal_listener(gSavedSettings, "UseOcclusion", handleUseOcclusionChanged);
+ setting_setup_signal_listener(gSavedSettings, "AudioLevelMaster", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "AudioLevelSFX", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "AudioLevelUI", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "AudioLevelAmbient", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "AudioLevelMusic", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "AudioLevelMedia", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "AudioLevelVoice", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "AudioLevelDoppler", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "AudioLevelRolloff", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "AudioLevelUnderwaterRolloff", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "MuteAudio", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "MuteMusic", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "MuteMedia", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "MuteVoice", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "MuteAmbient", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "MuteUI", handleAudioVolumeChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderVBOEnable", handleResetVertexBuffersChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderUseVAO", handleResetVertexBuffersChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderVBOMappingDisable", handleResetVertexBuffersChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderUseStreamVBO", handleResetVertexBuffersChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderPreferStreamDraw", handleResetVertexBuffersChanged);
+ setting_setup_signal_listener(gSavedSettings, "WLSkyDetail", handleWLSkyDetailChanged);
+ setting_setup_signal_listener(gSavedSettings, "JoystickAxis0", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "JoystickAxis1", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "JoystickAxis2", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "JoystickAxis3", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "JoystickAxis4", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "JoystickAxis5", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "JoystickAxis6", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale0", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale1", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale2", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale3", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale4", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale5", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisScale6", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone0", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone1", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone2", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone3", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone4", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone5", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "FlycamAxisDeadZone6", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "AvatarAxisScale0", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "AvatarAxisScale1", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "AvatarAxisScale2", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "AvatarAxisScale3", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "AvatarAxisScale4", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "AvatarAxisScale5", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "AvatarAxisDeadZone0", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "AvatarAxisDeadZone1", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "AvatarAxisDeadZone2", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "AvatarAxisDeadZone3", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "AvatarAxisDeadZone4", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "AvatarAxisDeadZone5", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "BuildAxisScale0", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "BuildAxisScale1", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "BuildAxisScale2", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "BuildAxisScale3", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "BuildAxisScale4", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "BuildAxisScale5", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "BuildAxisDeadZone0", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "BuildAxisDeadZone1", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "BuildAxisDeadZone2", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "BuildAxisDeadZone3", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "BuildAxisDeadZone4", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "BuildAxisDeadZone5", handleJoystickChanged);
+ setting_setup_signal_listener(gSavedSettings, "DebugViews", handleDebugViewsChanged);
+ setting_setup_signal_listener(gSavedSettings, "UserLogFile", handleLogFileChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderHideGroupTitle", handleHideGroupTitleChanged);
+ setting_setup_signal_listener(gSavedSettings, "HighResSnapshot", handleHighResSnapshotChanged);
+ setting_setup_signal_listener(gSavedSettings, "EnableVoiceChat", handleVoiceClientPrefsChanged);
+ setting_setup_signal_listener(gSavedSettings, "PTTCurrentlyEnabled", handleVoiceClientPrefsChanged);
+ setting_setup_signal_listener(gSavedSettings, "PushToTalkButton", handleVoiceClientPrefsChanged);
+ setting_setup_signal_listener(gSavedSettings, "PushToTalkToggle", handleVoiceClientPrefsChanged);
+ setting_setup_signal_listener(gSavedSettings, "VoiceEarLocation", handleVoiceClientPrefsChanged);
+ setting_setup_signal_listener(gSavedSettings, "VoiceInputAudioDevice", handleVoiceClientPrefsChanged);
+ setting_setup_signal_listener(gSavedSettings, "VoiceOutputAudioDevice", handleVoiceClientPrefsChanged);
+ setting_setup_signal_listener(gSavedSettings, "AudioLevelMic", handleVoiceClientPrefsChanged);
+ setting_setup_signal_listener(gSavedSettings, "LipSyncEnabled", handleVoiceClientPrefsChanged);
+ setting_setup_signal_listener(gSavedSettings, "VelocityInterpolate", handleVelocityInterpolate);
+ setting_setup_signal_listener(gSavedSettings, "QAMode", show_debug_menus);
+ setting_setup_signal_listener(gSavedSettings, "UseDebugMenus", show_debug_menus);
+ setting_setup_signal_listener(gSavedSettings, "AgentPause", toggle_agent_pause);
// Is done inside XUI now, using visibility_control
// setting_setup_signal_listener(gSavedSettings, "ShowNavbarNavigationPanel", toggle_show_navigation_panel);
//
@@ -1335,16 +1357,27 @@ void settings_setup_listeners()
// setting_setup_signal_listener(gSavedSettings, "ShowMiniLocationPanel", toggle_show_mini_location_panel);
//
setting_setup_signal_listener(gSavedSettings, "ShowMenuBarLocation", toggle_show_menubar_location_panel);
- setting_setup_signal_listener(gSavedSettings, "ShowObjectRenderingCost", toggle_show_object_render_cost);
- setting_setup_signal_listener(gSavedSettings, "ForceShowGrid", handleForceShowGrid);
+ setting_setup_signal_listener(gSavedSettings, "ShowObjectRenderingCost", toggle_show_object_render_cost);
+ setting_setup_signal_listener(gSavedSettings, "ForceShowGrid", handleForceShowGrid);
// Show start location setting has no effect on login
setting_setup_signal_listener(gSavedSettings, "ShowStartLocation", handleForceShowGrid);
- setting_setup_signal_listener(gSavedSettings, "RenderTransparentWater", handleRenderTransparentWaterChanged);
- setting_setup_signal_listener(gSavedSettings, "SpellCheck", handleSpellCheckChanged);
- setting_setup_signal_listener(gSavedSettings, "SpellCheckDictionary", handleSpellCheckChanged);
- setting_setup_signal_listener(gSavedSettings, "LoginLocation", handleLoginLocationChanged);
- setting_setup_signal_listener(gSavedSettings, "DebugAvatarJoints", handleDebugAvatarJointsChanged);
- setting_setup_signal_listener(gSavedSettings, "RenderAutoMuteByteLimit", handleRenderAutoMuteByteLimitChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderTransparentWater", handleRenderTransparentWaterChanged);
+ setting_setup_signal_listener(gSavedSettings, "SpellCheck", handleSpellCheckChanged);
+ setting_setup_signal_listener(gSavedSettings, "SpellCheckDictionary", handleSpellCheckChanged);
+ setting_setup_signal_listener(gSavedSettings, "LoginLocation", handleLoginLocationChanged);
+ setting_setup_signal_listener(gSavedSettings, "DebugAvatarJoints", handleDebugAvatarJointsChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderAutoMuteByteLimit", handleRenderAutoMuteByteLimitChanged);
+
+ setting_setup_signal_listener(gSavedSettings, "TargetFPS", handleTargetFPSChanged);
+ setting_setup_signal_listener(gSavedSettings, "AutoTuneFPS", handleAutoTuneFPSChanged);
+ setting_setup_signal_listener(gSavedSettings, "AutoTuneLock", handleAutoTuneLockChanged);
+ setting_setup_signal_listener(gSavedSettings, "RenderAvatarMaxART", handleRenderAvatarMaxARTChanged);
+ setting_setup_signal_listener(gSavedSettings, "PerfStatsCaptureEnabled", handlePerformanceStatsEnabledChanged);
+ setting_setup_signal_listener(gSavedSettings, "UserTargetReflections", handleUserTargetReflectionsChanged);
+ setting_setup_signal_listener(gSavedSettings, "AutoTuneRenderFarClipTarget", handleUserTargetDrawDistanceChanged);
+ setting_setup_signal_listener(gSavedSettings, "AutoTuneImpostorFarAwayDistance", handleUserImpostorDistanceChanged);
+ setting_setup_signal_listener(gSavedSettings, "AutoTuneImpostorByDistEnabled", handleUserImpostorByDistEnabledChanged);
+ setting_setup_signal_listener(gSavedSettings, "TuningFPSStrategy", handleFPSTuningStrategyChanged);
setting_setup_signal_listener(gSavedPerAccountSettings, "AvatarHoverOffsetZ", handleAvatarHoverOffsetChanged);
@@ -1432,18 +1465,6 @@ void settings_setup_listeners()
// Better asset cache size control
setting_setup_signal_listener(gSavedSettings, "FSDiskCacheSize", handleDiskCacheSizeChanged);
- // perf floater controls
- setting_setup_signal_listener(gSavedSettings, "FSTargetFPS", handleTargetFPSChanged);
- setting_setup_signal_listener(gSavedSettings, "FSAutoTuneFPS", handleAutoTuneFPSChanged);
- setting_setup_signal_listener(gSavedSettings, "FSAutoTuneLock", handleAutoTuneLockChanged);
- setting_setup_signal_listener(gSavedSettings, "FSRenderAvatarMaxART", handleRenderAvatarMaxARTChanged);
- setting_setup_signal_listener(gSavedSettings, "FSPerfStatsCaptureEnabled", handlePerformanceStatsEnabledChanged);
- setting_setup_signal_listener(gSavedSettings, "FSUserTargetReflections", handleUserTargetReflectionsChanged);
- setting_setup_signal_listener(gSavedSettings, "FSAutoTuneRenderFarClipTarget", handleUserTargetDrawDistanceChanged);
- setting_setup_signal_listener(gSavedSettings, "FSAutoTuneImpostorFarAwayDistance", handleUserImpostorDistanceChanged);
- setting_setup_signal_listener(gSavedSettings, "FSAutoTuneImpostorByDistEnabled", handleUserImpostorByDistEnabledChanged);
- setting_setup_signal_listener(gSavedSettings, "FSTuningFPSStrategy", handleFPSTuningStrategyChanged);
- //
// Handle IME text input getting enabled or disabled
#if LL_SDL2
diff --git a/indra/newview/llviewerdisplay.cpp b/indra/newview/llviewerdisplay.cpp
index d46fbadd34..dcb4a34ccd 100644
--- a/indra/newview/llviewerdisplay.cpp
+++ b/indra/newview/llviewerdisplay.cpp
@@ -78,6 +78,7 @@
#include "llscenemonitor.h"
#include "llenvironment.h"
+#include "llperfstats.h"
// [RLVa:KB] - Checked: 2011-05-22 (RLVa-1.3.1a)
#include "llvisualeffect.h"
#include "rlvactions.h"
@@ -85,7 +86,6 @@
// [/RLVa:KB]
#include "llpresetsmanager.h"
#include "fsdata.h"
-#include "fsperfstats.h" // performance stats support
extern LLPointer gStartTexture;
extern bool gShiftFrame;
@@ -287,8 +287,8 @@ static LLTrace::BlockTimerStatHandle FTM_EEP_UPDATE("Env Update");
// Paint the display!
void display(BOOL rebuild, F32 zoom_factor, int subfield, BOOL for_snapshot)
{
- FSPerfStats::RecordSceneTime T (FSPerfStats::StatType_t::RENDER_DISPLAY); // render time capture - This is the main stat for overall rendering.
- LL_RECORD_BLOCK_TIME(FTM_RENDER);
+ LLPerfStats::RecordSceneTime T (LLPerfStats::StatType_t::RENDER_DISPLAY); // render time capture - This is the main stat for overall rendering.
+ LL_RECORD_BLOCK_TIME(FTM_RENDER);
LLViewerCamera& camera = LLViewerCamera::instance(); // Factor out calls to getInstance
@@ -1194,8 +1194,8 @@ void display(BOOL rebuild, F32 zoom_factor, int subfield, BOOL for_snapshot)
void render_hud_attachments()
{
- FSPerfStats::RecordSceneTime T ( FSPerfStats::StatType_t::RENDER_HUDS); // render time capture - Primary contributor to HUDs (though these end up in render batches)
- gGL.matrixMode(LLRender::MM_PROJECTION);
+ LLPerfStats::RecordSceneTime T ( LLPerfStats::StatType_t::RENDER_HUDS); // render time capture - Primary contributor to HUDs (though these end up in render batches)
+ gGL.matrixMode(LLRender::MM_PROJECTION);
gGL.pushMatrix();
gGL.matrixMode(LLRender::MM_MODELVIEW);
gGL.pushMatrix();
@@ -1402,8 +1402,8 @@ bool setup_hud_matrices(const LLRect& screen_region)
void render_ui(F32 zoom_factor, int subfield)
{
- FSPerfStats::RecordSceneTime T ( FSPerfStats::StatType_t::RENDER_UI ); // render time capture - Primary UI stat can have HUD time overlap (TODO)
- LL_PROFILE_ZONE_SCOPED_CATEGORY_UI; //LL_RECORD_BLOCK_TIME(FTM_RENDER_UI);
+ LLPerfStats::RecordSceneTime T ( LLPerfStats::StatType_t::RENDER_UI ); // render time capture - Primary UI stat can have HUD time overlap (TODO)
+ LL_PROFILE_ZONE_SCOPED_CATEGORY_UI; //LL_RECORD_BLOCK_TIME(FTM_RENDER_UI);
LLGLState::checkStates();
@@ -1492,8 +1492,8 @@ static LLTrace::BlockTimerStatHandle FTM_SWAP("Swap");
void swap()
{
- FSPerfStats::RecordSceneTime T ( FSPerfStats::StatType_t::RENDER_SWAP ); // render time capture - Swap buffer time - can signify excessive data transfer to/from GPU
- LL_RECORD_BLOCK_TIME(FTM_SWAP);
+ LLPerfStats::RecordSceneTime T ( LLPerfStats::StatType_t::RENDER_SWAP ); // render time capture - Swap buffer time - can signify excessive data transfer to/from GPU
+ LL_RECORD_BLOCK_TIME(FTM_SWAP);
if (gDisplaySwapBuffers)
{
diff --git a/indra/newview/llviewerfloaterreg.cpp b/indra/newview/llviewerfloaterreg.cpp
index 63470be5ba..4fdfae515f 100644
--- a/indra/newview/llviewerfloaterreg.cpp
+++ b/indra/newview/llviewerfloaterreg.cpp
@@ -109,7 +109,7 @@
#include "llfloaterpathfindingconsole.h"
#include "llfloaterpathfindinglinksets.h"
#include "llfloaterpay.h"
-// #include "llfloaterperformance.h" rename to fs as ll version no released
+// #include "llfloaterperformance.h" restore fsperf floater
#include "fsfloaterperformance.h"
#include "llfloaterperms.h"
#include "llfloaterpostprocess.h"
@@ -626,7 +626,7 @@ void LLViewerFloaterReg::registerFloaters()
LLFloaterReg::add("media_lists", "floater_media_lists.xml", (LLFloaterBuildFunc)&LLFloaterReg::build);
LLFloaterReg::add("money_tracker", "floater_fs_money_tracker.xml", (LLFloaterBuildFunc)&LLFloaterReg::build);
LLFloaterReg::add("particle_editor","floater_particle_editor.xml", (LLFloaterBuildFunc)&LLFloaterReg::build);
- LLFloaterReg::add("performance", "floater_performance.xml", (LLFloaterBuildFunc)&LLFloaterReg::build);
+ LLFloaterReg::add("performance", "floater_fs_performance.xml", (LLFloaterBuildFunc)&LLFloaterReg::build);
LLFloaterReg::add(PHOTOTOOLS_FLOATER, "floater_phototools.xml", (LLFloaterBuildFunc)&LLFloaterReg::build);
LLFloaterReg::add("phototools_camera", "floater_phototools_camera.xml", (LLFloaterBuildFunc)&LLFloaterReg::build);
LLFloaterReg::add("quickprefs", "floater_quickprefs.xml", (LLFloaterBuildFunc)&LLFloaterReg::build);
diff --git a/indra/newview/llviewerjointmesh.cpp b/indra/newview/llviewerjointmesh.cpp
index fcc770870f..3ec8b2a93b 100644
--- a/indra/newview/llviewerjointmesh.cpp
+++ b/indra/newview/llviewerjointmesh.cpp
@@ -55,7 +55,7 @@
#include "m3math.h"
#include "m4math.h"
#include "llmatrix4a.h"
-#include "fsperfstats.h" // performance stats support
+#include "llperfstats.h"
#if !LL_DARWIN && !LL_LINUX
extern PFNGLWEIGHTPOINTERARBPROC glWeightPointerARB;
@@ -232,15 +232,16 @@ U32 LLViewerJointMesh::drawShape( F32 pixelArea, BOOL first_pass, BOOL is_dummy)
return 0;
}
- // render time capture
- // TODO(Beq) This path does not appear to have attachments. Prove this then remove.
- std::unique_ptr ratPtr{};
- auto vobj = mFace->getViewerObject();
- if( vobj && vobj->isAttachment() )
- {
- trackAttachments( vobj, mFace->isState(LLFace::RIGGED), &ratPtr );
- }
-//
+ // render time capture
+ // This path does not appear to have attachments. Prove this then remove.
+ std::unique_ptr ratPtr{};
+ auto vobj = mFace->getViewerObject();
+ if( vobj && vobj->isAttachment() )
+ {
+ trackAttachments( vobj, mFace->isState(LLFace::RIGGED), &ratPtr );
+ LL_WARNS("trackAttachments") << "Attachment render time is captuted." << LL_ENDL;
+ }
+
U32 triangle_count = 0;
S32 diffuse_channel = LLDrawPoolAvatar::sDiffuseChannel;
diff --git a/indra/newview/llviewerpartsim.cpp b/indra/newview/llviewerpartsim.cpp
index 47715e3708..f77ed8abaf 100644
--- a/indra/newview/llviewerpartsim.cpp
+++ b/indra/newview/llviewerpartsim.cpp
@@ -718,7 +718,7 @@ void LLViewerPartSim::updateSimulation()
if (upd && vobj && (vobj->getPCode() == LL_PCODE_VOLUME))
{
- if(vobj->getAvatar() && vobj->getAvatar()->isTooComplex())
+ if(vobj->getAvatar() && vobj->getAvatar()->isTooComplex() && vobj->getAvatar()->isTooSlow())
{
upd = FALSE;
}
diff --git a/indra/newview/llviewerstats.cpp b/indra/newview/llviewerstats.cpp
index 83ffc540ab..2f588b19ef 100644
--- a/indra/newview/llviewerstats.cpp
+++ b/indra/newview/llviewerstats.cpp
@@ -58,6 +58,7 @@
#include "llfeaturemanager.h"
#include "llviewernetwork.h"
#include "llmeshrepository.h" //for LLMeshRepository::sBytesReceived
+#include "llperfstats.h"
#include "llsdserialize.h"
#include "llsdutil.h"
#include "llcorehttputil.h"
@@ -215,6 +216,13 @@ LLTrace::EventStatHandle AVATAR_EDIT_TIME("avataredittime", "Second
LLTrace::EventStatHandle > OBJECT_CACHE_HIT_RATE("object_cache_hits");
LLTrace::EventStatHandle TEXTURE_FETCH_TIME("texture_fetch_time");
+
+LLTrace::SampleStatHandle > SCENERY_FRAME_PCT("scenery_frame_pct");
+LLTrace::SampleStatHandle > AVATAR_FRAME_PCT("avatar_frame_pct");
+LLTrace::SampleStatHandle > HUDS_FRAME_PCT("huds_frame_pct");
+LLTrace::SampleStatHandle > UI_FRAME_PCT("ui_frame_pct");
+LLTrace::SampleStatHandle > SWAP_FRAME_PCT("swap_frame_pct");
+LLTrace::SampleStatHandle > IDLE_FRAME_PCT("idle_frame_pct");
}
LLViewerStats::LLViewerStats()
@@ -421,6 +429,89 @@ void update_statistics()
texture_stats_timer.reset();
}
}
+
+ if (LLFloaterReg::instanceVisible("scene_load_stats"))
+ {
+ static const F32 perf_stats_freq = 1;
+ static LLFrameTimer perf_stats_timer;
+ if (perf_stats_timer.getElapsedTimeF32() >= perf_stats_freq)
+ {
+ LLStringUtil::format_map_t args;
+ LLPerfStats::bufferToggleLock.lock(); // prevent toggle for a moment
+
+ auto tot_frame_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_FRAME);
+ // cumulative avatar time (includes idle processing, attachments and base av)
+ auto tot_avatar_time_raw = LLPerfStats::StatsRecorder::getSum(LLPerfStats::ObjType_t::OT_AVATAR, LLPerfStats::StatType_t::RENDER_COMBINED);
+ // cumulative avatar render specific time (a bit arbitrary as the processing is too.)
+ // auto tot_av_idle_time_raw = LLPerfStats::StatsRecorder::getSum(AvType, LLPerfStats::StatType_t::RENDER_IDLE);
+ // auto tot_avatar_render_time_raw = tot_avatar_time_raw - tot_av_idle_time_raw;
+ // the time spent this frame on the "display()" call. Treated as "tot time rendering"
+ auto tot_render_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_DISPLAY);
+ // sleep time is basically forced sleep when window out of focus
+ auto tot_sleep_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_SLEEP);
+ // time spent on UI
+ auto tot_ui_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_UI);
+ // cumulative time spent rendering HUDS
+ auto tot_huds_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_HUDS);
+ // "idle" time. This is the time spent in the idle poll section of the main loop
+ auto tot_idle_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_IDLE);
+ // similar to sleep time, induced by FPS limit
+ //auto tot_limit_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_FPSLIMIT);
+ // swap time is time spent in swap buffer
+ auto tot_swap_time_raw = LLPerfStats::StatsRecorder::getSceneStat(LLPerfStats::StatType_t::RENDER_SWAP);
+
+ LLPerfStats::bufferToggleLock.unlock();
+
+ auto tot_frame_time_ns = LLPerfStats::raw_to_ns(tot_frame_time_raw);
+ auto tot_avatar_time_ns = LLPerfStats::raw_to_ns(tot_avatar_time_raw);
+ auto tot_huds_time_ns = LLPerfStats::raw_to_ns(tot_huds_time_raw);
+ // UI time includes HUD time so dedut that before we calc percentages
+ auto tot_ui_time_ns = LLPerfStats::raw_to_ns(tot_ui_time_raw - tot_huds_time_raw);
+
+ // auto tot_sleep_time_ns = LLPerfStats::raw_to_ns( tot_sleep_time_raw );
+ // auto tot_limit_time_ns = LLPerfStats::raw_to_ns( tot_limit_time_raw );
+
+ // auto tot_render_time_ns = LLPerfStats::raw_to_ns( tot_render_time_raw );
+ auto tot_idle_time_ns = LLPerfStats::raw_to_ns(tot_idle_time_raw);
+ auto tot_swap_time_ns = LLPerfStats::raw_to_ns(tot_swap_time_raw);
+ auto tot_scene_time_ns = LLPerfStats::raw_to_ns(tot_render_time_raw - tot_avatar_time_raw - tot_swap_time_raw - tot_ui_time_raw);
+ // auto tot_overhead_time_ns = LLPerfStats::raw_to_ns( tot_frame_time_raw - tot_render_time_raw - tot_idle_time_raw );
+
+ // // remove time spent sleeping for fps limit or out of focus.
+ // tot_frame_time_ns -= tot_limit_time_ns;
+ // tot_frame_time_ns -= tot_sleep_time_ns;
+
+ if (tot_frame_time_ns != 0)
+ {
+ auto pct_avatar_time = (tot_avatar_time_ns * 100) / tot_frame_time_ns;
+ auto pct_huds_time = (tot_huds_time_ns * 100) / tot_frame_time_ns;
+ auto pct_ui_time = (tot_ui_time_ns * 100) / tot_frame_time_ns;
+ auto pct_idle_time = (tot_idle_time_ns * 100) / tot_frame_time_ns;
+ auto pct_swap_time = (tot_swap_time_ns * 100) / tot_frame_time_ns;
+ auto pct_scene_render_time = (tot_scene_time_ns * 100) / tot_frame_time_ns;
+ pct_avatar_time = llclamp(pct_avatar_time, 0., 100.);
+ pct_huds_time = llclamp(pct_huds_time, 0., 100.);
+ pct_ui_time = llclamp(pct_ui_time, 0., 100.);
+ pct_idle_time = llclamp(pct_idle_time, 0., 100.);
+ pct_swap_time = llclamp(pct_swap_time, 0., 100.);
+ pct_scene_render_time = llclamp(pct_scene_render_time, 0., 100.);
+ if (tot_sleep_time_raw == 0)
+ {
+ sample(LLStatViewer::SCENERY_FRAME_PCT, (U32)llround(pct_scene_render_time));
+ sample(LLStatViewer::AVATAR_FRAME_PCT, (U32)llround(pct_avatar_time));
+ sample(LLStatViewer::HUDS_FRAME_PCT, (U32)llround(pct_huds_time));
+ sample(LLStatViewer::UI_FRAME_PCT, (U32)llround(pct_ui_time));
+ sample(LLStatViewer::SWAP_FRAME_PCT, (U32)llround(pct_swap_time));
+ sample(LLStatViewer::IDLE_FRAME_PCT, (U32)llround(pct_idle_time));
+ }
+ }
+ else
+ {
+ LL_WARNS("performance") << "Scene time 0. Skipping til we have data." << LL_ENDL;
+ }
+ perf_stats_timer.reset();
+ }
+ }
}
void update_texture_time()
@@ -533,6 +624,7 @@ void send_viewer_stats(bool include_preferences)
system["gpu"] = gpu_desc;
system["gpu_class"] = (S32)LLFeatureManager::getInstance()->getGPUClass();
+ system["gpu_memory_bandwidth"] = LLFeatureManager::getInstance()->getGPUMemoryBandwidth();
system["gpu_vendor"] = gGLManager.mGLVendorShort;
system["gpu_version"] = gGLManager.mDriverVersionVendorString;
system["opengl_version"] = gGLManager.mGLVersionString;
diff --git a/indra/newview/llviewertexturelist.cpp b/indra/newview/llviewertexturelist.cpp
index 5572e6f9f3..7847b109a7 100644
--- a/indra/newview/llviewertexturelist.cpp
+++ b/indra/newview/llviewertexturelist.cpp
@@ -214,8 +214,8 @@ static std::string get_texture_list_name()
void LLViewerTextureList::doPrefetchImages()
{
LL_PROFILE_ZONE_SCOPED_CATEGORY_TEXTURE;
- gTextureTimer.start();
- gTextureTimer.pause();
+ gTextureTimer.start();
+ gTextureTimer.pause();
// todo: do not load without getViewerAssetUrl()
// either fail login without caps or provide this
diff --git a/indra/newview/llvoavatar.cpp b/indra/newview/llvoavatar.cpp
index 04bf69c768..e76b1d073f 100644
--- a/indra/newview/llvoavatar.cpp
+++ b/indra/newview/llvoavatar.cpp
@@ -119,6 +119,8 @@
#include "llrendersphere.h"
#include "llskinningutil.h"
+#include "llperfstats.h"
+
#include
#include "fscommon.h"
@@ -135,7 +137,6 @@
#include "fslslbridge.h" // Movelock position refresh
#include "fsdiscordconnect.h" // tapping a place that happens on landing in world to start up discord
-#include "fsperfstats.h" // performance stats support
extern F32 SPEED_ADJUST_MAX;
extern F32 SPEED_ADJUST_MAX_SEC;
@@ -226,6 +227,8 @@ const F64 HUD_OVERSIZED_TEXTURE_DATA_SIZE = 1024 * 1024;
const F32 MAX_TEXTURE_WAIT_TIME_SEC = 60.f;
+const S32 MIN_NONTUNED_AVS = 5;
+
enum ERenderName
{
RENDER_NAME_NEVER,
@@ -636,6 +639,8 @@ F32 LLVOAvatar::sUnbakedUpdateTime = 0.f;
F32 LLVOAvatar::sGreyTime = 0.f;
F32 LLVOAvatar::sGreyUpdateTime = 0.f;
LLPointer LLVOAvatar::sCloudTexture = NULL;
+std::vector LLVOAvatar::sAVsIgnoringARTLimit;
+S32 LLVOAvatar::sAvatarsNearby = 0;
//-----------------------------------------------------------------------------
// Helper functions
@@ -890,12 +895,17 @@ LLVOAvatar::~LLVOAvatar()
debugAvatarRezTime("AvatarRezLeftNotification","left sometime after declouding");
}
- // only call logPendingPhases if we're still alive. Otherwise this can lead to shutdown crashes
+ if(mTuned)
+ {
+ LLPerfStats::tunedAvatars--;
+ mTuned = false;
+ }
+ sAVsIgnoringARTLimit.erase(std::remove(sAVsIgnoringARTLimit.begin(), sAVsIgnoringARTLimit.end(), mID), sAVsIgnoringARTLimit.end());
+ // only call logPendingPhases if we're still alive. Otherwise this can lead to shutdown crashes
// logPendingPhases();
if (isAgentAvatarValid())
logPendingPhases();
-
//
LL_DEBUGS("Avatar") << "LLVOAvatar Destructor (0x" << this << ") id:" << mID << LL_ENDL;
@@ -2702,10 +2712,10 @@ void LLVOAvatar::idleUpdate(LLAgent &agent, const F64 &time)
LL_INFOS() << "Warning! Idle on dead avatar" << LL_ENDL;
return;
}
- // record time and refresh "tooSlow" status
- FSPerfStats::RecordAvatarTime T(getID(), FSPerfStats::StatType_t::RENDER_IDLE); // per avatar "idle" time.
- updateTooSlow();
- // ;
+ // record time and refresh "tooSlow" status
+ LLPerfStats::RecordAvatarTime T(getID(), LLPerfStats::StatType_t::RENDER_IDLE); // per avatar "idle" time.
+ updateTooSlow();
+
static LLCachedControl disable_all_render_types(gSavedSettings, "DisableAllRenderTypes");
if (!(gPipeline.hasRenderType(mIsControlAvatar ? LLPipeline::RENDER_TYPE_CONTROL_AV : LLPipeline::RENDER_TYPE_AVATAR))
&& !disable_all_render_types && !isSelf())
@@ -3358,7 +3368,7 @@ void LLVOAvatar::idleUpdateLoadingEffect()
// Firestorm Clouds
// do not generate particles for dummy or overly-complex avatars
- if (!mIsDummy && !isTooComplex())
+ if (!mIsDummy && !isTooComplex() && !isTooSlow())
{
setParticleSource(sCloud, getID());
}
@@ -4307,7 +4317,7 @@ bool LLVOAvatar::isVisuallyMuted()
//
else
{
- muted = isTooComplex();
+ muted = isTooComplex(); // this should not trigger based on perfstats
}
}
@@ -9196,95 +9206,6 @@ BOOL LLVOAvatar::isFullyLoaded() const
// return (mRenderUnloadedAvatar || mFullyLoaded);
}
-// use Avatar Render Time as complexity metric
-// markARTStale - Mark stale and set the frameupdate to now so that we can wait at least one frame to get a revised number.
-void LLVOAvatar::markARTStale()
-{
- mARTStale=true;
- mLastARTUpdateFrame = LLFrameTimer::getFrameCount();
-}
-
-// Udpate Avatar state based on render time
-void LLVOAvatar::updateTooSlow()
-{
- LL_PROFILE_ZONE_SCOPED_CATEGORY_AVATAR;
- static LLCachedControl alwaysRenderFriends(gSavedSettings, "AlwaysRenderFriends");
- static LLCachedControl allowSelfImpostor(gSavedSettings, "FSAllowSelfImpostor");
- const auto id = getID();
-
- // mTooSlow - Is the avatar flagged as being slow (includes shadow time)
- // mTooSlowWithoutShadows - Is the avatar flagged as being slow even with shadows removed.
- // mARTStale - the rendertime we have is stale because of an update. We need to force a re-render to re-assess slowness
-
- if( mARTStale )
- {
- if ( LLFrameTimer::getFrameCount() - mLastARTUpdateFrame < 5 )
- {
- // LL_INFOS() << this->getFullname() << " marked stale " << LL_ENDL;
- // we've not had a chance to update yet (allow a few to be certain a full frame has passed)
- return;
- }
-
- mARTStale = false;
- mTooSlow = false;
- mTooSlowWithoutShadows = false;
- // LL_INFOS() << this->getFullname() << " refreshed ART combined = " << mRenderTime << " @ " << mLastARTUpdateFrame << LL_ENDL;
- }
-
- // Either we're not stale or we've updated.
-
- U64 render_time_raw;
- U64 render_geom_time_raw;
-
- if( !mTooSlow )
- {
- // we are fully rendered, so we use the live values
- std::lock_guard lock{FSPerfStats::bufferToggleLock};
- render_time_raw = FSPerfStats::StatsRecorder::get(FSPerfStats::ObjType_t::OT_AVATAR, id, FSPerfStats::StatType_t::RENDER_COMBINED);
- render_geom_time_raw = FSPerfStats::StatsRecorder::get(FSPerfStats::ObjType_t::OT_AVATAR, id, FSPerfStats::StatType_t::RENDER_GEOMETRY);
- }
- else
- {
- // use the cached values.
- render_time_raw = mRenderTime;
- render_geom_time_raw = mGeomTime;
- }
- if( (FSPerfStats::renderAvatarMaxART_ns > 0) &&
- (FSPerfStats::raw_to_ns(render_time_raw) >= FSPerfStats::renderAvatarMaxART_ns) )
- {
- if( !mTooSlow ) // if we were previously not slow (with or without shadows.)
- {
- // if we weren't capped, we are now
- mLastARTUpdateFrame = LLFrameTimer::getFrameCount();
- mRenderTime = render_time_raw;
- mGeomTime = render_geom_time_raw;
- mARTStale = false;
- mTooSlow = true;
- }
- if(!mTooSlowWithoutShadows) // if we were not previously above the full impostor cap
- {
- bool render_friend_or_exception = ( alwaysRenderFriends && LLAvatarTracker::instance().isBuddy( id ) ) ||
- ( getVisualMuteSettings() == LLVOAvatar::AV_ALWAYS_RENDER );
- if( (!isSelf() || allowSelfImpostor) && !render_friend_or_exception )
- {
- // Note: slow rendering Friends still get their shadows zapped.
- mTooSlowWithoutShadows = (FSPerfStats::raw_to_ns(render_geom_time_raw) >= FSPerfStats::renderAvatarMaxART_ns);
- }
- }
- }
- else
- {
- // LL_INFOS() << this->getFullname() << " ("<< (combined?"combined":"geometry") << ") good render time = " << FSPerfStats::raw_to_ns(render_time_raw) << " vs ("<< LLVOAvatar::sRenderTimeCap_ns << " set @ " << mLastARTUpdateFrame << LL_ENDL;
- mTooSlow = false;
- mTooSlowWithoutShadows = false;
- }
- if(mTooSlow)
- {
- FSPerfStats::tunedAvatars++; // increment the number of avatars that have been tweaked.
- }
-}
-//
-
bool LLVOAvatar::isTooComplex() const
{
bool too_complex;
@@ -9312,6 +9233,182 @@ bool LLVOAvatar::isTooComplex() const
return too_complex;
}
+bool LLVOAvatar::isTooSlow() const
+{
+ static LLCachedControl always_render_friends(gSavedSettings, "AlwaysRenderFriends");
+ bool render_friend = (LLAvatarTracker::instance().isBuddy(getID()) && always_render_friends);
+
+ if (render_friend || mVisuallyMuteSetting == AV_ALWAYS_RENDER)
+ {
+ return false;
+ }
+ return mTooSlow;
+}
+
+// use Avatar Render Time as complexity metric
+// refactor for clarity post LL merge
+void LLVOAvatar::clearSlowARTCache()
+{
+ mARTStale = false;
+ mTooSlow = false;
+ mTooSlowWithoutShadows = false;
+}
+
+void LLVOAvatar::setSlowARTCache(U64 full_render_time, U64 non_shadow_render_time)
+{
+ mLastARTUpdateFrame = LLFrameTimer::getFrameCount();
+ mRenderTime = full_render_time;
+ mRenderTimeNoShadows = non_shadow_render_time;
+ mARTStale = false;
+ mTooSlow = true;
+}
+//
+// markARTStale - Mark stale and set the frameupdate to now so that we can wait at least one frame to get a revised number.
+void LLVOAvatar::markARTStale()
+{
+ mARTStale=true;
+ mLastARTUpdateFrame = LLFrameTimer::getFrameCount();
+}
+
+// Udpate Avatar state based on render time
+void LLVOAvatar::updateTooSlow()
+{
+ LL_PROFILE_ZONE_SCOPED_CATEGORY_AVATAR;
+ static LLCachedControl alwaysRenderFriends(gSavedSettings, "AlwaysRenderFriends");
+ static LLCachedControl allowSelfImpostor(gSavedSettings, "AllowSelfImpostor");
+ const auto id = getID();
+ bool changed_slow_state{false}; // Post LL merge, force dirty when slowness state changes
+
+ // mTooSlow - Is the avatar flagged as being slow (includes shadow time)
+ // mTooSlowWithoutShadows - Is the avatar flagged as being slow even with shadows removed.
+ // mARTStale - the rendertime we have is stale because of an update. We need to force a re-render to re-assess slowness
+
+ if( mARTStale )
+ {
+ if ( LLFrameTimer::getFrameCount() - mLastARTUpdateFrame < 5 )
+ {
+ // LL_INFOS() << this->getFullname() << " marked stale " << LL_ENDL;
+ // we've not had a chance to update yet (allow a few to be certain a full frame has passed)
+ return;
+ }
+ // refactor and work out why shadow derendering is no longer working
+ // mARTStale = false;
+ // mTooSlow = false;
+ // mTooSlowWithoutShadows = false;
+ // LL_INFOS() << this->getFullname() << " refreshed ART combined = " << mRenderTime << " @ " << mLastARTUpdateFrame << LL_ENDL;
+ clearSlowARTCache();
+ changed_slow_state = true;
+ //
+ }
+
+ // Either we're not stale or we've updated.
+
+ U64 render_time_raw;
+ U64 render_time_no_shadows_raw; // rename as we now include idle time
+
+ if( !mTooSlow )
+ {
+ // we are fully rendered, so we use the live values
+ std::lock_guard lock{LLPerfStats::bufferToggleLock};
+ render_time_raw = LLPerfStats::StatsRecorder::get(LLPerfStats::ObjType_t::OT_AVATAR, id, LLPerfStats::StatType_t::RENDER_COMBINED);
+ // include idle time in total render time
+ // render_geom_time_raw = LLPerfStats::StatsRecorder::get(LLPerfStats::ObjType_t::OT_AVATAR, id, LLPerfStats::StatType_t::RENDER_GEOMETRY);
+ render_time_no_shadows_raw = render_time_raw - LLPerfStats::StatsRecorder::get(LLPerfStats::ObjType_t::OT_AVATAR, id, LLPerfStats::StatType_t::RENDER_SHADOWS);
+ //
+ }
+ else
+ {
+ // use the cached values.
+ render_time_raw = mRenderTime;
+ render_time_no_shadows_raw = mRenderTimeNoShadows; // variable name updated to refelect different meaning.
+ }
+
+ bool autotune = LLPerfStats::tunables.userAutoTuneEnabled && !mIsControlAvatar && !isSelf();
+
+ bool ignore_tune = false;
+ if (autotune && sAVsIgnoringARTLimit.size() > 0)
+ {
+ auto it = std::find(sAVsIgnoringARTLimit.begin(), sAVsIgnoringARTLimit.end(), mID);
+ if (it != sAVsIgnoringARTLimit.end())
+ {
+ S32 index = it - sAVsIgnoringARTLimit.begin();
+ ignore_tune = (index < (MIN_NONTUNED_AVS - sAvatarsNearby + 1 + LLPerfStats::tunedAvatars));
+ }
+ }
+
+ bool exceeds_max_ART =
+ ((LLPerfStats::renderAvatarMaxART_ns > 0) && (LLPerfStats::raw_to_ns(render_time_raw) >= LLPerfStats::renderAvatarMaxART_ns));
+
+ if (exceeds_max_ART && !ignore_tune)
+ {
+ if( !mTooSlow ) // if we were previously not slow (with or without shadows.)
+ {
+ // if we weren't capped, we are now
+ // refactored "geom" becomes "no shadow"
+ // mLastARTUpdateFrame = LLFrameTimer::getFrameCount();
+ // mRenderTime = render_time_raw;
+ // mGeomTime = render_geom_time_raw;
+ // mARTStale = false;
+ // mTooSlow = true;
+ setSlowARTCache(render_time_raw, render_time_no_shadows_raw);
+ changed_slow_state = true;
+ //
+ }
+ if(!mTooSlowWithoutShadows) // if we were not previously above the full impostor cap
+ {
+ bool render_friend_or_exception = ( alwaysRenderFriends && LLAvatarTracker::instance().isBuddy( id ) ) ||
+ ( getVisualMuteSettings() == LLVOAvatar::AV_ALWAYS_RENDER );
+ if( (!isSelf() || allowSelfImpostor) && !render_friend_or_exception )
+ {
+ // Note: slow rendering Friends still get their shadows zapped.
+ // changes to support idel and geom in non shadow rendering cost + improved dirty marking
+ // mTooSlowWithoutShadows = (LLPerfStats::raw_to_ns(render_geom_time_raw) >= LLPerfStats::renderAvatarMaxART_ns);
+ mTooSlowWithoutShadows = (LLPerfStats::raw_to_ns(render_time_no_shadows_raw) >= LLPerfStats::renderAvatarMaxART_ns);
+ }
+ if(mTooSlowWithoutShadows)
+ {
+ changed_slow_state = true;
+ //
+ }
+
+ }
+ }
+ else
+ {
+ // better state change flagging
+ // LL_INFOS() << this->getFullname() << " ("<< (combined?"combined":"geometry") << ") good render time = " << LLPerfStats::raw_to_ns(render_time_raw) << " vs ("<< LLVOAvatar::sRenderTimeCap_ns << " set @ " << mLastARTUpdateFrame << LL_ENDL;
+ // LL_INFOS() << this->getFullname() << " good render time = " << render_time_ns << " vs ("<< LLPerfStats::renderAvatarMaxART_ns << " set @ " << mLastARTUpdateFrame << ")" << LL_ENDL;
+ if( mTooSlow || mTooSlowWithoutShadows )
+ {
+ changed_slow_state = true;
+ }
+ //
+ mTooSlow = false;
+ mTooSlowWithoutShadows = false;
+
+ if (ignore_tune)
+ {
+ return;
+ }
+ }
+ if(mTooSlow && !mTuned)
+ {
+ LLPerfStats::tunedAvatars++; // increment the number of avatars that have been tweaked.
+ mTuned = true;
+ }
+ else if(!mTooSlow && mTuned)
+ {
+ LLPerfStats::tunedAvatars--;
+ mTuned = false;
+ }
+ // better state change flagging
+ if( changed_slow_state )
+ {
+ gPipeline.markRebuild(mDrawable, LLDrawable::REBUILD_GEOMETRY, true);
+ }
+ //
+}
+
//-----------------------------------------------------------------------------
// findMotion()
//-----------------------------------------------------------------------------
@@ -11722,6 +11819,64 @@ void LLVOAvatar::idleUpdateRenderComplexity()
// Render Complexity
calculateUpdateRenderComplexity(); // Update mVisualComplexity if needed
+
+ bool autotune = LLPerfStats::tunables.userAutoTuneEnabled && !mIsControlAvatar && !isSelf();
+ if (autotune && !isDead())
+ {
+ static LLCachedControl render_far_clip(gSavedSettings, "RenderFarClip", 64);
+ F32 radius = render_far_clip * render_far_clip;
+
+ bool is_nearby = true;
+ if ((dist_vec_squared(getPositionGlobal(), gAgent.getPositionGlobal()) > radius) &&
+ (dist_vec_squared(getPositionGlobal(), gAgentCamera.getCameraPositionGlobal()) > radius))
+ {
+ is_nearby = false;
+ }
+
+ if (is_nearby && (sAVsIgnoringARTLimit.size() < MIN_NONTUNED_AVS))
+ {
+ if (std::count(sAVsIgnoringARTLimit.begin(), sAVsIgnoringARTLimit.end(), mID) == 0)
+ {
+ sAVsIgnoringARTLimit.push_back(mID);
+ }
+ }
+ else if (!is_nearby)
+ {
+ sAVsIgnoringARTLimit.erase(std::remove(sAVsIgnoringARTLimit.begin(), sAVsIgnoringARTLimit.end(), mID),
+ sAVsIgnoringARTLimit.end());
+ }
+ updateNearbyAvatarCount();
+ }
+}
+
+void LLVOAvatar::updateNearbyAvatarCount()
+{
+ static LLFrameTimer agent_update_timer;
+
+ if (agent_update_timer.getElapsedTimeF32() > 1.0f)
+ {
+ S32 avs_nearby = 0;
+ static LLCachedControl render_far_clip(gSavedSettings, "RenderFarClip", 64);
+ F32 radius = render_far_clip * render_far_clip;
+ std::vector::iterator char_iter = LLCharacter::sInstances.begin();
+ while (char_iter != LLCharacter::sInstances.end())
+ {
+ LLVOAvatar *avatar = dynamic_cast(*char_iter);
+ if (avatar && !avatar->isDead() && !avatar->isControlAvatar())
+ {
+ if ((dist_vec_squared(avatar->getPositionGlobal(), gAgent.getPositionGlobal()) > radius) &&
+ (dist_vec_squared(avatar->getPositionGlobal(), gAgentCamera.getCameraPositionGlobal()) > radius))
+ {
+ char_iter++;
+ continue;
+ }
+ avs_nearby++;
+ }
+ char_iter++;
+ }
+ sAvatarsNearby = avs_nearby;
+ agent_update_timer.reset();
+ }
}
void LLVOAvatar::idleUpdateDebugInfo()
@@ -12151,13 +12306,13 @@ void LLVOAvatar::calculateUpdateRenderComplexity()
mVisualComplexity = cost;
mVisualComplexityStale = false;
- if (isSelf())
+ static LLCachedControl show_my_complexity_changes(gSavedSettings, "ShowMyComplexityChanges", 20);
+
+ if (isSelf() && show_my_complexity_changes)
{
// Avatar complexity
LLAvatarRenderNotifier::getInstance()->updateNotificationAgent(mVisualComplexity);
-
LLAvatarRenderNotifier::getInstance()->setObjectComplexityList(object_complexity_list);
-
// HUD complexity
LLHUDRenderNotifier::getInstance()->updateNotificationHUD(hud_complexity_list);
}
@@ -12342,7 +12497,7 @@ LLVOAvatar::AvatarOverallAppearance LLVOAvatar::getOverallAppearance() const
{ // Always want to see this AV as an impostor
result = AOA_JELLYDOLL;
}
- else if (isTooComplex())
+ else if (isTooComplex() || isTooSlowWithoutShadows()) // correct for misplaced check
{
result = AOA_JELLYDOLL;
}
@@ -12377,7 +12532,10 @@ void LLVOAvatar::calcMutedAVColor()
new_color = LLColor4::grey4;
change_msg = " blocked: color is grey4";
}
+ // we don't want jelly dolls
+ // else if (!isTooComplex() && !isTooSlow())
else if (!isTooComplex())
+ //
{
new_color = LLColor4::white;
change_msg = " simple imposter ";
diff --git a/indra/newview/llvoavatar.h b/indra/newview/llvoavatar.h
index bb9278368c..ecc33c405c 100644
--- a/indra/newview/llvoavatar.h
+++ b/indra/newview/llvoavatar.h
@@ -330,6 +330,8 @@ public:
void idleUpdateBelowWater();
+ static void updateNearbyAvatarCount();
+
//--------------------------------------------------------------------
// Static preferences (controlled by user settings/menus)
//--------------------------------------------------------------------
@@ -351,11 +353,13 @@ public:
static F32 sLODFactor; // user-settable LOD factor
static F32 sPhysicsLODFactor; // user-settable physics LOD factor
static BOOL sJointDebug; // output total number of joints being touched for each avatar
- static U64 sRenderTimeLimit_ns; // nanosecond time limit for avatar rendering 0 is unlimited.
static LLPartSysData sCloud;
static LLPointer sCloudTexture;
+ static std::vector sAVsIgnoringARTLimit;
+ static S32 sAvatarsNearby;
+
//--------------------------------------------------------------------
// Region state
//--------------------------------------------------------------------
@@ -367,17 +371,16 @@ public:
//--------------------------------------------------------------------
public:
BOOL isFullyLoaded() const;
- // check and return current state relative to limits
- // default will test only the geometry (combined=false).
- // this allows us to disable shadows separately on complex avatars.
- inline bool isTooSlowWithShadows() const {return mTooSlow;};
- inline bool isTooSlowWithoutShadows() const {return mTooSlowWithoutShadows;};
- inline bool isTooSlow(bool combined = false) const
- {
- return(combined?mTooSlow:mTooSlowWithoutShadows);
- }
- void updateTooSlow();
- //
+
+ // check and return current state relative to limits
+ // default will test only the geometry (combined=false).
+ // this allows us to disable shadows separately on complex avatars.
+
+ inline bool isTooSlowWithoutShadows() const {return mTooSlowWithoutShadows;};
+ bool isTooSlow() const;
+
+ void updateTooSlow();
+
virtual bool isTooComplex() const; // FIRE-29012: Standalone animesh avatars get affected by complexity limit; changed to virtual
bool visualParamWeightsAreDefault();
virtual bool getIsCloud() const;
@@ -399,7 +402,11 @@ public:
void logMetricsTimerRecord(const std::string& phase_name, F32 elapsed, bool completed);
void calcMutedAVColor();
- void markARTStale();
+ void markARTStale();
+ // refactoring post LL merge
+ void clearSlowARTCache();
+ void setSlowARTCache(U64 full_render_time, U64 geometry_render_time);
+ //
protected:
LLViewerStats::PhaseMap& getPhases() { return mPhases; }
@@ -420,15 +427,17 @@ private:
LLColor4 mMutedAVColor;
LLFrameTimer mFullyLoadedTimer;
LLFrameTimer mRuthTimer;
- U32 mLastARTUpdateFrame{0};
- U64 mRenderTime{0};
- U64 mGeomTime{0};
- bool mARTStale{true};
- bool mARTCapped{false};
- // variables to hold "slowness" status
- bool mTooSlow{false};
- bool mTooSlowWithoutShadows{false};
- //
+
+ U32 mLastARTUpdateFrame{0};
+ U64 mRenderTime{0};
+ U64 mRenderTimeNoShadows{0};
+ bool mARTStale{true};
+ bool mARTCapped{false};
+ // variables to hold "slowness" status
+ bool mTooSlow{false};
+ bool mTooSlowWithoutShadows{false};
+
+ bool mTuned{false};
private:
LLViewerStats::PhaseMap mPhases;
@@ -1233,7 +1242,7 @@ public:
// COF version of last appearance message received for this av.
S32 mLastUpdateReceivedCOFVersion;
- U64 getLastART() const { return mRenderTime; }
+ U64 getLastART() const { return mRenderTime; }
/** Diagnostics
** **
diff --git a/indra/newview/llvovolume.cpp b/indra/newview/llvovolume.cpp
index 551f55681c..170fead89e 100644
--- a/indra/newview/llvovolume.cpp
+++ b/indra/newview/llvovolume.cpp
@@ -88,12 +88,12 @@
#include "llcallstack.h"
#include "llsculptidsize.h"
#include "llavatarappearancedefines.h"
+#include "llperfstats.h"
// [RLVa:KB] - Checked: RLVa-2.0.0
#include "rlvactions.h"
#include "rlvlocks.h"
// [/RLVa:KB]
#include "llviewernetwork.h"
-#include "fsperfstats.h" // performance stats support
const F32 FORCE_SIMPLE_RENDER_AREA = 512.f;
const F32 FORCE_CULL_AREA = 8.f;
@@ -5727,7 +5727,7 @@ void LLVolumeGeometryManager::registerFace(LLSpatialGroup* group, LLFace* facep,
}
}
- // if (type == LLRenderPass::PASS_ALPHA) // always populate the draw_info ptr
+ // if (type == LLRenderPass::PASS_ALPHA) // always populate the draw_info ptr
{ //for alpha sorting
facep->setDrawInfo(draw_info);
}
@@ -5932,7 +5932,7 @@ void LLVolumeGeometryManager::rebuildGeom(LLSpatialGroup* group)
LL_PROFILE_ZONE_NAMED_CATEGORY_VOLUME("rebuildGeom - face list");
//get all the faces into a list
- std::unique_ptr ratPtr{}; // render time capture
+ std::unique_ptr ratPtr{};
for (LLSpatialGroup::element_iter drawable_iter = group->getDataBegin();
drawable_iter != group->getDataEnd(); ++drawable_iter)
{
@@ -5975,6 +5975,11 @@ void LLVolumeGeometryManager::rebuildGeom(LLSpatialGroup* group)
}
//
+ if(vobj->isAttachment())
+ {
+ trackAttachments( vobj, drawablep->isState(LLDrawable::RIGGED),&ratPtr);
+ }
+
LLVolume* volume = vobj->getVolume();
if (volume)
{
@@ -6404,7 +6409,7 @@ void LLVolumeGeometryManager::rebuildMesh(LLSpatialGroup* group)
U32 buffer_count = 0;
- std::unique_ptr ratPtr{}; // capture render times
+ std::unique_ptr ratPtr{};
for (LLSpatialGroup::element_iter drawable_iter = group->getDataBegin(); drawable_iter != group->getDataEnd(); ++drawable_iter)
{
LLDrawable* drawablep = (LLDrawable*)(*drawable_iter)->getDrawable();
@@ -6416,8 +6421,7 @@ void LLVolumeGeometryManager::rebuildMesh(LLSpatialGroup* group)
if (!vobj) continue;
- // capture render times
- if (vobj->isAttachment())
+ if (vobj->isAttachment())
{
trackAttachments( vobj, drawablep->isState(LLDrawable::RIGGED), &ratPtr );
}
@@ -6854,18 +6858,16 @@ U32 LLVolumeGeometryManager::genDrawInfo(LLSpatialGroup* group, U32 mask, LLFace
U32 indices_index = 0;
U16 index_offset = 0;
- std::unique_ptr ratPtr; // capture render times
- while (face_iter < i)
+ std::unique_ptr ratPtr;
+ while (face_iter < i)
{
//update face indices for new buffer
facep = *face_iter;
- LLViewerObject* vobj = facep->getViewerObject();
- // capture render times
- if(vobj && vobj->isAttachment())
- {
- trackAttachments(vobj, LLPipeline::sShadowRender, &ratPtr);
- }
- //
+ LLViewerObject* vobj = facep->getViewerObject();
+ if(vobj && vobj->isAttachment())
+ {
+ trackAttachments(vobj, LLPipeline::sShadowRender, &ratPtr);
+ }
if (buffer.isNull())
{
// Bulk allocation failed
diff --git a/indra/newview/llworld.cpp b/indra/newview/llworld.cpp
index 10373d043e..e554562239 100644
--- a/indra/newview/llworld.cpp
+++ b/indra/newview/llworld.cpp
@@ -33,6 +33,7 @@
#include "llstl.h"
#include "llagent.h"
+#include "llagentcamera.h"
#include "llviewercontrol.h"
#include "lldrawpool.h"
#include "llglheaders.h"
@@ -1935,6 +1936,34 @@ void LLWorld::getAvatars(uuid_vec_t* avatar_ids, std::vector* positi
}
}
+// [FS performance floater]
+//S32 LLWorld::getNearbyAvatarsAndCompl(std::vector &valid_nearby_avs)
+//{
+// static LLCachedControl render_far_clip(gSavedSettings, "RenderFarClip", 64);
+// S32 nearby_max_complexity = 0;
+// F32 radius = render_far_clip * render_far_clip;
+// std::vector::iterator char_iter = LLCharacter::sInstances.begin();
+// while (char_iter != LLCharacter::sInstances.end())
+// {
+// LLVOAvatar* avatar = dynamic_cast(*char_iter);
+// if (avatar && !avatar->isDead() && !avatar->isControlAvatar())
+// {
+// if ((dist_vec_squared(avatar->getPositionGlobal(), gAgent.getPositionGlobal()) > radius) &&
+// (dist_vec_squared(avatar->getPositionGlobal(), gAgentCamera.getCameraPositionGlobal()) > radius))
+// {
+// char_iter++;
+// continue;
+// }
+// avatar->calculateUpdateRenderComplexity();
+// nearby_max_complexity = llmax(nearby_max_complexity, (S32)avatar->getVisualComplexity());
+// valid_nearby_avs.push_back(*char_iter);
+// }
+// char_iter++;
+// }
+// return nearby_max_complexity;
+//}
+// [FS performance floater]
+
// [RLVa:KB] - Checked: RLVa-2.0.1
bool LLWorld::getAvatar(const LLUUID& idAvatar, LLVector3d& posAvatar) const
{
diff --git a/indra/newview/llworld.h b/indra/newview/llworld.h
index 743f792dec..08d8764dcc 100644
--- a/indra/newview/llworld.h
+++ b/indra/newview/llworld.h
@@ -51,6 +51,7 @@ class LLHost;
class LLViewerObject;
class LLSurfacePatch;
+class LLCharacter;
class LLCloudPuff;
class LLCloudGroup;
class LLVOAvatar;
@@ -243,6 +244,9 @@ public:
// or if the circuit to this simulator had been lost.
bool isRegionListed(const LLViewerRegion* region) const;
+ // [FS performance floater]
+ //S32 getNearbyAvatarsAndCompl(std::vector &valid_nearby_avs);
+
private:
void clearHoleWaterObjects();
void clearEdgeWaterObjects();
diff --git a/indra/newview/pipeline.cpp b/indra/newview/pipeline.cpp
index 894f2f67d2..a7a6915146 100644
--- a/indra/newview/pipeline.cpp
+++ b/indra/newview/pipeline.cpp
@@ -43,6 +43,7 @@
#include "llui.h"
#include "llglheaders.h"
#include "llrender.h"
+#include "llstartup.h"
#include "llwindow.h" // swapBuffers()
// newview includes
@@ -160,6 +161,7 @@ F32 LLPipeline::RenderResolutionMultiplier;
// [/SL:KB]
bool LLPipeline::RenderUIBuffer;
S32 LLPipeline::RenderShadowDetail;
+S32 LLPipeline::RenderShadowSplits;
bool LLPipeline::RenderDeferredSSAO;
F32 LLPipeline::RenderShadowResolutionScale;
bool LLPipeline::RenderLocalLights;
@@ -596,6 +598,7 @@ void LLPipeline::init()
// [/SL:KB]
connectRefreshCachedSettingsSafe("RenderUIBuffer");
connectRefreshCachedSettingsSafe("RenderShadowDetail");
+ connectRefreshCachedSettingsSafe("RenderShadowSplits");
connectRefreshCachedSettingsSafe("RenderDeferredSSAO");
connectRefreshCachedSettingsSafe("RenderShadowResolutionScale");
connectRefreshCachedSettingsSafe("RenderLocalLights");
@@ -672,14 +675,13 @@ void LLPipeline::init()
connectRefreshCachedSettingsSafe("RenderAttachedParticles");
//
// FIRE-16728 Add free aim mouse and focus lock
- connectRefreshCachedSettingsSafe("FSFocusPointLocked");
connectRefreshCachedSettingsSafe("FSFocusPointFollowsPointer");
+ connectRefreshCachedSettingsSafe("FSFocusPointLocked");
//
}
LLPipeline::~LLPipeline()
{
-
}
void LLPipeline::cleanup()
@@ -1218,6 +1220,7 @@ void LLPipeline::refreshCachedSettings()
// [/SL:KB]
RenderUIBuffer = gSavedSettings.getBOOL("RenderUIBuffer");
RenderShadowDetail = gSavedSettings.getS32("RenderShadowDetail");
+ RenderShadowSplits = gSavedSettings.getS32("RenderShadowSplits");
RenderDeferredSSAO = gSavedSettings.getBOOL("RenderDeferredSSAO");
RenderShadowResolutionScale = gSavedSettings.getF32("RenderShadowResolutionScale");
RenderLocalLights = gSavedSettings.getBOOL("RenderLocalLights");
@@ -6222,7 +6225,7 @@ void LLPipeline::calcNearbyLights(LLCamera& camera)
LLDrawable* drawable = light->drawable;
const LLViewerObject *vobj = light->drawable->getVObj();
if(vobj && vobj->getAvatar()
- && (vobj->getAvatar()->isTooComplex() || vobj->getAvatar()->isInMuteList())
+ && (vobj->getAvatar()->isTooComplex() || vobj->getAvatar()->isInMuteList() || vobj->getAvatar()->isTooSlow())
)
{
drawable->clearState(LLDrawable::NEARBY_LIGHT);
@@ -6301,7 +6304,7 @@ void LLPipeline::calcNearbyLights(LLCamera& camera)
continue;
}
LLVOAvatar * av = light->getAvatar();
- if (av && (av->isTooComplex() || av->isInMuteList()))
+ if (av && (av->isTooComplex() || av->isInMuteList() || av->isTooSlow()))
{
// avatars that are already in the list will be removed by removeMutedAVsLights
continue;
@@ -10593,14 +10596,7 @@ void LLPipeline::generateSunShadow(LLCamera& camera)
if (mSunDiffuse == LLColor4::black)
{ //sun diffuse is totally black, shadows don't matter
- LLGLDepthTest depth(GL_TRUE);
-
- for (S32 j = 0; j < 4; j++)
- {
- mShadow[j].bindTarget();
- mShadow[j].clear();
- mShadow[j].flush();
- }
+ skipRenderingShadows();
}
else
{
@@ -10655,7 +10651,8 @@ void LLPipeline::generateSunShadow(LLCamera& camera)
std::vector fp;
- if (!gPipeline.getVisiblePointCloud(shadow_cam, min, max, fp, lightDir))
+ if (!gPipeline.getVisiblePointCloud(shadow_cam, min, max, fp, lightDir)
+ || j > RenderShadowSplits)
{
//no possible shadow receivers
if (!gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_SHADOW_FRUSTA))
@@ -11217,12 +11214,10 @@ void LLPipeline::generateImpostor(LLVOAvatar* avatar, bool preview_avatar)
<< " is " << ( too_complex ? "" : "not ") << "too complex"
<< LL_ENDL;
- bool too_slow = avatar->isTooSlowWithoutShadows(); // only if we really have to do we imposter.
+ pushRenderTypeMask();
- pushRenderTypeMask();
-
- if ( !too_slow && ( visually_muted || too_complex ) )
- {
+ if (visually_muted || too_complex)
+ {
// only show jelly doll geometry
andRenderTypeMask(LLPipeline::RENDER_TYPE_AVATAR,
LLPipeline::RENDER_TYPE_CONTROL_AV,
@@ -11937,6 +11932,31 @@ void LLPipeline::restoreHiddenObject( const LLUUID& id )
}
}
+void LLPipeline::skipRenderingShadows()
+{
+ LLGLDepthTest depth(GL_TRUE);
+
+ for (S32 j = 0; j < 4; j++)
+ {
+ mShadow[j].bindTarget();
+ mShadow[j].clear();
+ mShadow[j].flush();
+ }
+}
+
+void LLPipeline::handleShadowDetailChanged()
+{
+ if (RenderShadowDetail > gSavedSettings.getS32("RenderShadowDetail"))
+ {
+ skipRenderingShadows();
+ }
+ else
+ {
+ LLViewerShaderMgr::instance()->setShaders();
+ }
+}
+
+
// Reset VB during TP
void LLPipeline::initDeferredVB()
{
diff --git a/indra/newview/pipeline.h b/indra/newview/pipeline.h
index fd7128e7aa..a26d15a7b0 100644
--- a/indra/newview/pipeline.h
+++ b/indra/newview/pipeline.h
@@ -425,6 +425,7 @@ public:
void skipRenderingOfTerrain( bool flag );
void hideObject( const LLUUID& id );
void restoreHiddenObject( const LLUUID& id );
+ void handleShadowDetailChanged();
private:
void unloadShaders();
@@ -436,6 +437,7 @@ private:
void connectRefreshCachedSettingsSafe(const std::string name);
void hideDrawable( LLDrawable *pDrawable );
void unhideDrawable( LLDrawable *pDrawable );
+ void skipRenderingShadows();
// Reset VB during TP
void initDeferredVB();
@@ -748,7 +750,6 @@ protected:
U64 mOldRenderDebugMask;
std::stack mRenderDebugFeatureStack;
-
/////////////////////////////////////////////
//
//
@@ -949,6 +950,7 @@ public:
// [/SL:KB]
static bool RenderUIBuffer;
static S32 RenderShadowDetail;
+ static S32 RenderShadowSplits;
static bool RenderDeferredSSAO;
static F32 RenderShadowResolutionScale;
static bool RenderLocalLights;
diff --git a/indra/newview/skins/default/colors.xml b/indra/newview/skins/default/colors.xml
index ef0eeab305..a7bda69992 100644
--- a/indra/newview/skins/default/colors.xml
+++ b/indra/newview/skins/default/colors.xml
@@ -1276,15 +1276,15 @@
+
-
-
+