Compare commits
103 Commits
sv-1.8.7.8
...
sv-1.8.9.8
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
dfcdb6ba09 | ||
|
|
ae244983b0 | ||
|
|
8d2bdd4a18 | ||
|
|
246db973b4 | ||
|
|
d49c38bf18 | ||
|
|
c1aa88c720 | ||
|
|
937618b177 | ||
|
|
4a0936a4b5 | ||
|
|
891286c447 | ||
|
|
04db5d1075 | ||
|
|
997037a232 | ||
|
|
f0dfb0b080 | ||
|
|
f9c07b4806 | ||
|
|
9f9a21bb73 | ||
|
|
386528a892 | ||
|
|
4efe28cf52 | ||
|
|
2528f71bbf | ||
|
|
5610eaa839 | ||
|
|
881cc46aa9 | ||
|
|
81f342e9bf | ||
|
|
fe9d670800 | ||
|
|
ffb54802d4 | ||
|
|
518da73ad2 | ||
|
|
3e78b74474 | ||
|
|
34a7ebf53f | ||
|
|
45be739fea | ||
|
|
68ae8afaf9 | ||
|
|
2bdcd9d07f | ||
|
|
24f5457203 | ||
|
|
f941bc4334 | ||
|
|
ab5bce69ee | ||
|
|
050a8c3923 | ||
|
|
8817bf53e3 | ||
|
|
5e21037230 | ||
|
|
cabaf0fd1c | ||
|
|
bd92a09a48 | ||
|
|
61f90c665a | ||
|
|
32dbd40e64 | ||
|
|
a69e04a817 | ||
|
|
159de683e8 | ||
|
|
a9dbaf5e0a | ||
|
|
3c3d8c2400 | ||
|
|
b4080f8e2d | ||
|
|
5de94d6610 | ||
|
|
829045c262 | ||
|
|
b02d70fba0 | ||
|
|
64ed6e99f0 | ||
|
|
33d3bb2870 | ||
|
|
4df2193a4c | ||
|
|
343be08467 | ||
|
|
788b83bff3 | ||
|
|
c201ac90ba | ||
|
|
af3c66ad08 | ||
|
|
9bffc4bb82 | ||
|
|
132db6225e | ||
|
|
257086cbfc | ||
|
|
7755f1ec52 | ||
|
|
c5f1ac808b | ||
|
|
1a8660909d | ||
|
|
e6826a4c7c | ||
|
|
801bb8a075 | ||
|
|
b2c965e22d | ||
|
|
be3cbc642b | ||
|
|
24331d3c90 | ||
|
|
8a16e6c99f | ||
|
|
f36e8fbeca | ||
|
|
718ef09adf | ||
|
|
6443849ea9 | ||
|
|
cbb7e473ba | ||
|
|
118957362f | ||
|
|
ed7f73769f | ||
|
|
ae15dcb318 | ||
|
|
c4af22481c | ||
|
|
ae17f76bb4 | ||
|
|
7e62d17fda | ||
|
|
f9185e8bc8 | ||
|
|
1361f9b57d | ||
|
|
b86eae026b | ||
|
|
79d938a4f4 | ||
|
|
23068a70a2 | ||
|
|
0aa5e0bb88 | ||
|
|
5040275969 | ||
|
|
1daccf40ee | ||
|
|
4fd302286b | ||
|
|
18f9f19e61 | ||
|
|
1de6d4461a | ||
|
|
4198f47ab6 | ||
|
|
d9049ba342 | ||
|
|
f75ac3e4c2 | ||
|
|
06698deaca | ||
|
|
445eb29bd3 | ||
|
|
cc034f6841 | ||
|
|
3c368651f1 | ||
|
|
321730e384 | ||
|
|
c2fd88670f | ||
|
|
7b03103a1f | ||
|
|
ac3e19c91a | ||
|
|
4c7d2224e3 | ||
|
|
3ab800d99e | ||
|
|
332cef0f84 | ||
|
|
9de6d7627b | ||
|
|
98b42e88c1 | ||
|
|
e642e9561a |
344
.gitlab-ci.yml
344
.gitlab-ci.yml
@@ -1,166 +1,282 @@
|
||||
stages:
|
||||
- build
|
||||
- deploy
|
||||
- upload
|
||||
|
||||
default:
|
||||
interruptible: true
|
||||
timeout: 4h
|
||||
|
||||
variables:
|
||||
AUTOBUILD_BUILD_ID: $CI_PIPELINE_ID
|
||||
AUTOBUILD_INSTALLABLE_CACHE: "$CI_PROJECT_DIR/.cache/autobuild"
|
||||
PIP_CACHE_DIR: "$CI_PROJECT_DIR/.cache/pip"
|
||||
VIEWER_USE_CRASHPAD: "TRUE"
|
||||
VIEWER_CRASHPAD_URL: $SENTRY_DSN
|
||||
|
||||
.win_build: &win_build
|
||||
.win_build:
|
||||
stage: build
|
||||
tags:
|
||||
- autobuild
|
||||
- windows
|
||||
cache:
|
||||
key:
|
||||
files:
|
||||
- autobuild.xml
|
||||
prefix: ${CI_JOB_NAME}
|
||||
paths:
|
||||
- .cache/autobuild
|
||||
- .cache/pip
|
||||
- .venv/
|
||||
when: 'always'
|
||||
before_script:
|
||||
- pipenv install
|
||||
- virtualenv .venv
|
||||
- .\.venv\Scripts\activate.ps1
|
||||
- pip install --upgrade autobuild -i https://pkg.alchemyviewer.org/repository/autobuild/simple --extra-index-url https://pypi.org/simple
|
||||
script:
|
||||
- If ($env:VIEWER_CHANNEL_TYPE -eq 'Project')
|
||||
{
|
||||
$env:VIEWER_CHANNEL_CODENAME = $env:CI_COMMIT_REF_NAME[8..100] -join ''
|
||||
}
|
||||
- pipenv run autobuild configure -c Release -- -DUSE_FMODSTUDIO=ON -DUSE_NVAPI=ON -DUSE_LTO=ON -DVS_DISABLE_FATAL_WARNINGS=ON
|
||||
- pipenv run autobuild build -c Release --no-configure
|
||||
- If ($env:VIEWER_USE_CRASHPAD -eq 'TRUE') {
|
||||
- Push-Location .\build-vc-*\newview\Release\
|
||||
- sentry-cli upload-dif --include-sources singularity-bin.exe singularity-bin.pdb crashpad_handler.exe crashpad_handler.pdb fmod.dll libcrypto-1_1.dll libcrypto-1_1.pdb libssl-1_1.dll libssl-1_1.pdb libcrypto-1_1-x64.dll libcrypto-1_1-x64.pdb libssl-1_1-x64.dll libssl-1_1-x64.pdb vcruntime140.dll msvcp140.dll libhunspell.dll libhunspell.pdb glod.dll
|
||||
- Pop-Location }
|
||||
- |
|
||||
autobuild configure -c Release -- -DUSE_FMODSTUDIO=ON -DUSE_NVAPI=ON -DUSE_LTO=ON -DVS_DISABLE_FATAL_WARNINGS=ON -DREVISION_FROM_VCS=FALSE
|
||||
autobuild build -c Release --no-configure
|
||||
artifacts:
|
||||
name: "$env:CI_COMMIT_REF_NAME-$env:CI_COMMIT_SHORT_SHA"
|
||||
expire_in: 2 week
|
||||
expire_in: 1 week
|
||||
paths:
|
||||
- build-vc-*/newview/Release/build_data.json
|
||||
- build-vc-*/newview/Release/singularity-bin.pdb
|
||||
- build-vc-*/newview/Release/singularity-bin.exe
|
||||
- build-vc-*/newview/Release/*.pdb
|
||||
- build-vc-*/newview/Release/*.dll
|
||||
- build-vc-*/newview/Release/Singularity_*_Setup.exe
|
||||
|
||||
.beta_rules: &beta_rules
|
||||
only:
|
||||
- /^.*-beta$/
|
||||
except:
|
||||
- branches
|
||||
.linux_build:
|
||||
stage: build
|
||||
image: r.alchemyviewer.org/singularity/infrastructure/debian-build-image:latest
|
||||
tags:
|
||||
- linux
|
||||
- docker
|
||||
cache:
|
||||
key:
|
||||
files:
|
||||
- autobuild.xml
|
||||
prefix: ${CI_JOB_NAME}
|
||||
paths:
|
||||
- .cache/autobuild
|
||||
- .cache/pip
|
||||
- .venv
|
||||
when: 'always'
|
||||
before_script:
|
||||
- virtualenv .venv -p python2
|
||||
- source .venv/bin/activate
|
||||
- pip install --upgrade autobuild -i https://pkg.alchemyviewer.org/repository/autobuild/simple --extra-index-url https://pypi.org/simple
|
||||
script:
|
||||
- |
|
||||
autobuild configure -c Release -- -DUSE_FMODSTUDIO=ON -DUSE_NVAPI=ON -DUSE_LTO=ON -DUNIX_DISABLE_FATAL_WARNINGS=ON -DREVISION_FROM_VCS=FALSE
|
||||
autobuild build -c Release --no-configure
|
||||
artifacts:
|
||||
name: "$env:CI_COMMIT_REF_NAME-$env:CI_COMMIT_SHORT_SHA"
|
||||
expire_in: 1 week
|
||||
paths:
|
||||
- build-linux-*/build_data.json
|
||||
- build-linux-*/newview/Singularity_*.tar.xz
|
||||
|
||||
.release_rules: &release_rules
|
||||
only:
|
||||
- /^.*-release$/
|
||||
except:
|
||||
- branches
|
||||
.win32_build:
|
||||
extends: .win_build
|
||||
variables:
|
||||
AUTOBUILD_ADDRSIZE: 32
|
||||
VIEWER_USE_CRASHPAD: "FALSE"
|
||||
cache:
|
||||
key:
|
||||
prefix: windows32
|
||||
|
||||
.win64_build:
|
||||
extends: .win_build
|
||||
variables:
|
||||
AUTOBUILD_ADDRSIZE: 64
|
||||
cache:
|
||||
key:
|
||||
prefix: windows64
|
||||
|
||||
.linux32_build:
|
||||
extends: .linux_build
|
||||
variables:
|
||||
AUTOBUILD_ADDRSIZE: 32
|
||||
cache:
|
||||
key:
|
||||
prefix: linux32
|
||||
|
||||
.linux64_build:
|
||||
extends: .linux_build
|
||||
variables:
|
||||
AUTOBUILD_ADDRSIZE: 64
|
||||
cache:
|
||||
key:
|
||||
prefix: linux64
|
||||
|
||||
.master_rules:
|
||||
rules:
|
||||
- if: $BUILD_CHANNEL || $CI_COMMIT_TAG
|
||||
when: never
|
||||
- if: '$CI_PIPELINE_SOURCE == "web"'
|
||||
- if: '$CI_PIPELINE_SOURCE == "schedule"'
|
||||
#- if: '$CI_COMMIT_BRANCH == "master" && $CI_PIPELINE_SOURCE == "push"'
|
||||
# when: delayed
|
||||
# start_in: '12 hours'
|
||||
variables:
|
||||
VIEWER_CHANNEL_TYPE: Test
|
||||
VIEWER_USE_CRASHPAD: "FALSE"
|
||||
|
||||
.project_rules:
|
||||
rules:
|
||||
- if: '$BUILD_CHANNEL == "Project" && ($CI_PIPELINE_SOURCE == "web" || $CI_PIPELINE_SOURCE == "schedule")'
|
||||
- if: '$CI_COMMIT_TAG =~ /.*-project/'
|
||||
variables:
|
||||
VIEWER_CHANNEL_TYPE: Project
|
||||
|
||||
.beta_rules:
|
||||
rules:
|
||||
- if: '$BUILD_CHANNEL == "Beta" && ($CI_PIPELINE_SOURCE == "web" || $CI_PIPELINE_SOURCE == "schedule")'
|
||||
- if: '$CI_COMMIT_TAG =~ /.*-beta/'
|
||||
variables:
|
||||
VIEWER_CHANNEL_TYPE: Beta
|
||||
|
||||
.release_rules:
|
||||
rules:
|
||||
- if: '$BUILD_CHANNEL == "Release" && ($CI_PIPELINE_SOURCE == "web" || $CI_PIPELINE_SOURCE == "schedule")'
|
||||
- if: '$CI_COMMIT_TAG =~ /.*-release/'
|
||||
variables:
|
||||
VIEWER_CHANNEL_TYPE: Release
|
||||
|
||||
.build:master:linux64:
|
||||
extends:
|
||||
- .linux64_build
|
||||
- .master_rules
|
||||
|
||||
build:master:windows32:
|
||||
<<: *win_build
|
||||
interruptible: true
|
||||
variables:
|
||||
AUTOBUILD_ADDRSIZE: 32
|
||||
VIEWER_CHANNEL_TYPE: Test
|
||||
VIEWER_USE_CRASHPAD: "FALSE"
|
||||
only:
|
||||
- schedules
|
||||
extends:
|
||||
- .win32_build
|
||||
- .master_rules
|
||||
|
||||
build:master:windows64:
|
||||
<<: *win_build
|
||||
interruptible: true
|
||||
variables:
|
||||
AUTOBUILD_ADDRSIZE: 64
|
||||
VIEWER_CHANNEL_TYPE: Test
|
||||
VIEWER_USE_CRASHPAD: "FALSE"
|
||||
only:
|
||||
- schedules
|
||||
extends:
|
||||
- .win64_build
|
||||
- .master_rules
|
||||
|
||||
.build:project:linux64:
|
||||
extends:
|
||||
- .linux64_build
|
||||
- .project_rules
|
||||
|
||||
build:project:windows32:
|
||||
<<: *win_build
|
||||
interruptible: true
|
||||
variables:
|
||||
AUTOBUILD_ADDRSIZE: 32
|
||||
VIEWER_CHANNEL_TYPE: Project
|
||||
VIEWER_USE_CRASHPAD: "FALSE"
|
||||
only:
|
||||
- /^project-.*$/
|
||||
extends:
|
||||
- .win32_build
|
||||
- .project_rules
|
||||
|
||||
build:project:windows64:
|
||||
<<: *win_build
|
||||
interruptible: true
|
||||
variables:
|
||||
AUTOBUILD_ADDRSIZE: 64
|
||||
VIEWER_CHANNEL_TYPE: Project
|
||||
only:
|
||||
- /^project-.*$/
|
||||
extends:
|
||||
- .win64_build
|
||||
- .project_rules
|
||||
|
||||
.build:beta:linux64:
|
||||
extends:
|
||||
- .linux64_build
|
||||
- .beta_rules
|
||||
|
||||
build:beta:windows32:
|
||||
<<: *win_build
|
||||
variables:
|
||||
AUTOBUILD_ADDRSIZE: 32
|
||||
VIEWER_CHANNEL_TYPE: Beta
|
||||
VIEWER_USE_CRASHPAD: "FALSE"
|
||||
<<: *beta_rules
|
||||
extends:
|
||||
- .win32_build
|
||||
- .beta_rules
|
||||
|
||||
build:beta:windows64:
|
||||
<<: *win_build
|
||||
variables:
|
||||
AUTOBUILD_ADDRSIZE: 64
|
||||
VIEWER_CHANNEL_TYPE: Beta
|
||||
<<: *beta_rules
|
||||
extends:
|
||||
- .win64_build
|
||||
- .beta_rules
|
||||
|
||||
.build:release:linux64:
|
||||
extends:
|
||||
- .linux64_build
|
||||
- .release_rules
|
||||
|
||||
build:release:windows32:
|
||||
<<: *win_build
|
||||
variables:
|
||||
AUTOBUILD_ADDRSIZE: 32
|
||||
VIEWER_CHANNEL_TYPE: Release
|
||||
VIEWER_USE_CRASHPAD: "FALSE"
|
||||
<<: *release_rules
|
||||
extends:
|
||||
- .win32_build
|
||||
- .release_rules
|
||||
|
||||
build:release:windows64:
|
||||
<<: *win_build
|
||||
variables:
|
||||
AUTOBUILD_ADDRSIZE: 64
|
||||
VIEWER_CHANNEL_TYPE: Release
|
||||
<<: *release_rules
|
||||
extends:
|
||||
- .win64_build
|
||||
- .release_rules
|
||||
|
||||
.deploy_template: &deploy_template
|
||||
stage: deploy
|
||||
.upload_template:
|
||||
stage: upload
|
||||
tags:
|
||||
- autobuild
|
||||
- windows
|
||||
allow_failure: false
|
||||
script:
|
||||
- $BuildData = Get-Content .\build-vc-64\newview\Release\build_data.json | ConvertFrom-Json
|
||||
- $BuildChannelVersion = $BuildData."Channel" + ' ' + $BuildData."Version"
|
||||
- $UploadDestViewerDir = $BuildChannelVersion.ToLower().Replace(" ", "/")
|
||||
- $UploadDestURL = "https://pkg.alchemyviewer.org/repository/viewer/${UploadDestViewerDir}"
|
||||
- |
|
||||
$BuildData = Get-Content .\build-vc-64\newview\Release\build_data.json | ConvertFrom-Json
|
||||
$BuildChannelVersion = $BuildData."Channel" + ' ' + $BuildData."Version"
|
||||
$UploadDestViewerDir = $BuildChannelVersion.ToLower().Replace(" ", "/")
|
||||
$UploadDestURL = "https://pkg.alchemyviewer.org/repository/viewer/${UploadDestViewerDir}"
|
||||
|
||||
- $UploadParams = @{ UseBasicParsing = $true;
|
||||
Method = "PUT";
|
||||
Headers = @{
|
||||
ContentType = "application/x-executable";
|
||||
Authorization = "Basic $([System.Convert]::ToBase64String([System.Text.Encoding]::ASCII.GetBytes("$env:AUTOBUILD_HTTP_USER`:$env:AUTOBUILD_HTTP_PASS")))"; };
|
||||
Verbose = $true; };
|
||||
$UploadParams = @{ UseBasicParsing = $true;
|
||||
Method = "PUT";
|
||||
Headers = @{
|
||||
ContentType = "application/x-executable";
|
||||
Authorization = "Basic $([System.Convert]::ToBase64String([System.Text.Encoding]::ASCII.GetBytes("$env:AUTOBUILD_HTTP_USER`:$env:AUTOBUILD_HTTP_PASS")))"; };
|
||||
Verbose = $true; };
|
||||
|
||||
- Push-Location .\build-vc-32\newview\Release\
|
||||
- $FileNameWin32 = Get-ChildItem -Path . -Name -Include Singularity_*_Setup.exe
|
||||
- Invoke-WebRequest @UploadParams -InFile .\$FileNameWin32 -Uri "${UploadDestURL}/${FileNameWin32}"
|
||||
- Pop-Location
|
||||
If (Test-Path -LiteralPath ".\build-linux-64\newview\")
|
||||
{
|
||||
Push-Location .\build-linux-64\newview\
|
||||
$FileNameLnx64 = Get-ChildItem -Path . -Name -Include Singularity_*.tar.xz
|
||||
Invoke-WebRequest @UploadParams -InFile .\$FileNameLnx64 -Uri "${UploadDestURL}/${FileNameLnx64}"
|
||||
Pop-Location
|
||||
}
|
||||
|
||||
- Push-Location .\build-vc-64\newview\Release\
|
||||
- $FileNameWin64 = Get-ChildItem -Path . -Name -Include Singularity_*_Setup.exe
|
||||
- Invoke-WebRequest @UploadParams -InFile .\$FileNameWin64 -Uri "${UploadDestURL}/${FileNameWin64}"
|
||||
- Pop-Location
|
||||
Push-Location .\build-vc-64\newview\Release\
|
||||
$FileNameWin64 = Get-ChildItem -Path . -Name -Include Singularity_*_Setup.exe
|
||||
Invoke-WebRequest @UploadParams -InFile .\$FileNameWin64 -Uri "${UploadDestURL}/${FileNameWin64}"
|
||||
|
||||
- sentry-cli releases new $BuildChannelVersion
|
||||
- sentry-cli releases set-commits --auto $BuildChannelVersion
|
||||
- sentry-cli releases finalize $BuildChannelVersion
|
||||
when: manual
|
||||
If ($env:VIEWER_USE_CRASHPAD -eq 'TRUE')
|
||||
{
|
||||
sentry-cli upload-dif --include-sources singularity-bin.exe singularity-bin.pdb crashpad_handler.exe crashpad_handler.pdb fmod.dll libcrypto-1_1.dll libcrypto-1_1.pdb libssl-1_1.dll libssl-1_1.pdb libcrypto-1_1-x64.dll libcrypto-1_1-x64.pdb libssl-1_1-x64.dll libssl-1_1-x64.pdb vcruntime140.dll msvcp140.dll libhunspell.dll libhunspell.pdb glod.dll
|
||||
}
|
||||
Pop-Location
|
||||
If ($env:VIEWER_USE_CRASHPAD -eq 'TRUE')
|
||||
{
|
||||
sentry-cli releases new $BuildChannelVersion
|
||||
sentry-cli releases set-commits --auto $BuildChannelVersion
|
||||
sentry-cli releases finalize $BuildChannelVersion
|
||||
}
|
||||
|
||||
deploy_project:
|
||||
<<: *deploy_template
|
||||
upload:project:
|
||||
extends:
|
||||
- .upload_template
|
||||
rules:
|
||||
- if: '$BUILD_CHANNEL == "Project" && ($CI_PIPELINE_SOURCE == "web" || $CI_PIPELINE_SOURCE == "schedule")'
|
||||
when: manual
|
||||
- if: '$CI_COMMIT_TAG =~ /.*-project/'
|
||||
when: manual
|
||||
environment:
|
||||
name: qa
|
||||
only:
|
||||
- /^project-.*$/
|
||||
|
||||
deploy_beta:
|
||||
<<: *deploy_template
|
||||
upload:beta:
|
||||
extends:
|
||||
- .upload_template
|
||||
rules:
|
||||
- if: '$BUILD_CHANNEL == "Beta" && ($CI_PIPELINE_SOURCE == "web" || $CI_PIPELINE_SOURCE == "schedule")'
|
||||
when: manual
|
||||
- if: '$CI_COMMIT_TAG =~ /.*-beta/'
|
||||
when: manual
|
||||
environment:
|
||||
name: staging
|
||||
<<: *beta_rules
|
||||
name: beta
|
||||
|
||||
deploy_release:
|
||||
<<: *deploy_template
|
||||
upload:release:
|
||||
extends:
|
||||
- .upload_template
|
||||
rules:
|
||||
- if: '$BUILD_CHANNEL == "Release" && ($CI_PIPELINE_SOURCE == "web" || $CI_PIPELINE_SOURCE == "schedule")'
|
||||
when: manual
|
||||
- if: '$CI_COMMIT_TAG =~ /.*-release/'
|
||||
when: manual
|
||||
environment:
|
||||
name: production
|
||||
<<: *release_rules
|
||||
name: release
|
||||
|
||||
@@ -410,11 +410,11 @@
|
||||
<key>archive</key>
|
||||
<map>
|
||||
<key>hash</key>
|
||||
<string>4614b29cc98021cf1770a8290171602b</string>
|
||||
<string>a96fda7ad5cee967823f5c94390ba35b</string>
|
||||
<key>hash_algorithm</key>
|
||||
<string>md5</string>
|
||||
<key>url</key>
|
||||
<string>https://pkg.alchemyviewer.org/repository/autobuild-external/crashpad/windows/crashpad-ce32d093.7-windows-7.tar.bz2</string>
|
||||
<string>https://pkg.alchemyviewer.org/repository/autobuild-external/crashpad/windows/crashpad-c6d76a90.194-windows-194.tar.bz2</string>
|
||||
</map>
|
||||
<key>name</key>
|
||||
<string>windows</string>
|
||||
@@ -424,18 +424,18 @@
|
||||
<key>archive</key>
|
||||
<map>
|
||||
<key>hash</key>
|
||||
<string>d801461b7a6a40fffab828aa1e01e3e6</string>
|
||||
<string>5ff95ca1007ed2dc300b59de17453201</string>
|
||||
<key>hash_algorithm</key>
|
||||
<string>md5</string>
|
||||
<key>url</key>
|
||||
<string>https://pkg.alchemyviewer.org/repository/autobuild-external/crashpad/windows64/crashpad-ce32d093.7-windows64-7.tar.bz2</string>
|
||||
<string>https://pkg.alchemyviewer.org/repository/autobuild-external/crashpad/windows64/crashpad-c6d76a90.194-windows64-194.tar.bz2</string>
|
||||
</map>
|
||||
<key>name</key>
|
||||
<string>windows64</string>
|
||||
</map>
|
||||
</map>
|
||||
<key>version</key>
|
||||
<string>ce32d093.7</string>
|
||||
<string>c6d76a90.194</string>
|
||||
</map>
|
||||
<key>curl</key>
|
||||
<map>
|
||||
@@ -876,11 +876,11 @@
|
||||
<key>archive</key>
|
||||
<map>
|
||||
<key>hash</key>
|
||||
<string>ccd495598894c8e2e541a348015ee3f0</string>
|
||||
<string>7f631a7f1742a5786e1f9de1d2424350</string>
|
||||
<key>hash_algorithm</key>
|
||||
<string>md5</string>
|
||||
<key>url</key>
|
||||
<string>/opt/devel/fmodstudio-2.00.07.200182252-linux64-200182252.tar.bz2</string>
|
||||
<string>https://pkg.alchemyviewer.org/repository/autobuild-internal/fmodstudio/linux64/fmodstudio-2.01.04.417-linux64-417.tar.bz2</string>
|
||||
</map>
|
||||
<key>name</key>
|
||||
<string>linux64</string>
|
||||
@@ -890,11 +890,11 @@
|
||||
<key>archive</key>
|
||||
<map>
|
||||
<key>hash</key>
|
||||
<string>d32efb193ffcd73bcba4875ddfd17bf0</string>
|
||||
<string>50ce25e855c10d3b39f5461f34661c7f</string>
|
||||
<key>hash_algorithm</key>
|
||||
<string>md5</string>
|
||||
<key>url</key>
|
||||
<string>https://pkg.alchemyviewer.org/repository/autobuild-internal/fmodstudio/windows/fmodstudio-2.00.07.4-windows-4.tar.bz2</string>
|
||||
<string>https://pkg.alchemyviewer.org/repository/autobuild-internal/fmodstudio/windows/fmodstudio-2.01.04.417-windows-417.tar.bz2</string>
|
||||
</map>
|
||||
<key>name</key>
|
||||
<string>windows</string>
|
||||
@@ -904,18 +904,18 @@
|
||||
<key>archive</key>
|
||||
<map>
|
||||
<key>hash</key>
|
||||
<string>0604fd6b53ceaf14ce04d0de1bea51b8</string>
|
||||
<string>e13b156ca861c36b388e18df0e8e20fb</string>
|
||||
<key>hash_algorithm</key>
|
||||
<string>md5</string>
|
||||
<key>url</key>
|
||||
<string>https://pkg.alchemyviewer.org/repository/autobuild-internal/fmodstudio/windows64/fmodstudio-2.00.07.4-windows64-4.tar.bz2</string>
|
||||
<string>https://pkg.alchemyviewer.org/repository/autobuild-internal/fmodstudio/windows64/fmodstudio-2.01.04.417-windows64-417.tar.bz2</string>
|
||||
</map>
|
||||
<key>name</key>
|
||||
<string>windows64</string>
|
||||
</map>
|
||||
</map>
|
||||
<key>version</key>
|
||||
<string>2.00.07.4</string>
|
||||
<string>2.01.04.417</string>
|
||||
</map>
|
||||
<key>fonts</key>
|
||||
<map>
|
||||
|
||||
@@ -85,6 +85,7 @@ if (WINDOWS)
|
||||
/TP
|
||||
/W3
|
||||
/c
|
||||
/Zc:__cplusplus
|
||||
/Zc:forScope
|
||||
/Zc:rvalueCast
|
||||
/Zc:wchar_t
|
||||
@@ -135,6 +136,10 @@ if (LINUX)
|
||||
-DLL_LINUX=1
|
||||
-DAPPID=secondlife
|
||||
-D_REENTRANT
|
||||
-DGDK_DISABLE_DEPRECATED
|
||||
-DGTK_DISABLE_DEPRECATED
|
||||
-DGSEAL_ENABLE
|
||||
-DGTK_DISABLE_SINGLE_INCLUDES
|
||||
)
|
||||
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -std=c99")
|
||||
@@ -204,10 +209,10 @@ if (LINUX)
|
||||
|
||||
if (${ARCH} STREQUAL "x86_64")
|
||||
add_definitions(-pipe)
|
||||
set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE} -ffast-math")
|
||||
set(CMAKE_C_FLAGS_RELEASE "${CMAKE_C_FLAGS_RELEASE} -ffast-math")
|
||||
set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "${CMAKE_CXX_FLAGS_RELWITHDEBINFO} -ffast-math")
|
||||
set(CMAKE_C_FLAGS_RELWITHDEBINFO "${CMAKE_C_FLAGS_RELWITHDEBINFO} -ffast-math")
|
||||
set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE} -ffast-math -msse4.1")
|
||||
set(CMAKE_C_FLAGS_RELEASE "${CMAKE_C_FLAGS_RELEASE} -ffast-math -msse4.1")
|
||||
set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "${CMAKE_CXX_FLAGS_RELWITHDEBINFO} -ffast-math -msse4.1")
|
||||
set(CMAKE_C_FLAGS_RELWITHDEBINFO "${CMAKE_C_FLAGS_RELWITHDEBINFO} -ffast-math -msse4.1")
|
||||
else (${ARCH} STREQUAL "x86_64")
|
||||
if (NOT STANDALONE)
|
||||
set(MARCH_FLAG " -march=pentium4")
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
include(APR)
|
||||
include(Boost)
|
||||
include(EXPAT)
|
||||
include(Linking)
|
||||
include(ZLIB)
|
||||
|
||||
if (DARWIN)
|
||||
@@ -18,7 +19,9 @@ set(LLCOMMON_INCLUDE_DIRS
|
||||
${Boost_INCLUDE_DIRS}
|
||||
)
|
||||
|
||||
set(LLCOMMON_LIBRARIES llcommon)
|
||||
set(LLCOMMON_LIBRARIES llcommon
|
||||
fmt::fmt
|
||||
)
|
||||
|
||||
set(LLCOMMON_LINK_SHARED OFF CACHE BOOL "Build the llcommon target as a shared library.")
|
||||
if(LLCOMMON_LINK_SHARED)
|
||||
|
||||
@@ -1,9 +1,8 @@
|
||||
# -*- cmake -*-
|
||||
|
||||
include(OpenGL)
|
||||
include(Prebuilt)
|
||||
|
||||
if (STANDALONE)
|
||||
if (LINUX)
|
||||
include(FindSDL)
|
||||
|
||||
# This should be done by FindSDL. Sigh.
|
||||
@@ -12,14 +11,7 @@ if (STANDALONE)
|
||||
SDL_INCLUDE_DIR
|
||||
SDL_LIBRARY
|
||||
)
|
||||
else (STANDALONE)
|
||||
if (LINUX)
|
||||
use_prebuilt_binary(SDL)
|
||||
set (SDL_FOUND TRUE)
|
||||
set (SDL_INCLUDE_DIR ${LIBS_PREBUILT_DIR}/include)
|
||||
set (SDL_LIBRARY SDL)
|
||||
endif (LINUX)
|
||||
endif (STANDALONE)
|
||||
endif (LINUX)
|
||||
|
||||
if (SDL_FOUND)
|
||||
add_definitions(-DLL_SDL=1)
|
||||
|
||||
@@ -50,12 +50,10 @@ if (LINUX)
|
||||
set(DL_LIBRARY dl)
|
||||
set(RT_LIBRARY rt)
|
||||
set(PTHREAD_LIBRARY pthread)
|
||||
set(FMT_LIBRARY "")
|
||||
else (LINUX)
|
||||
set(DL_LIBRARY "")
|
||||
set(RT_LIBRARY "")
|
||||
set(PTHREAD_LIBRARY "")
|
||||
set(FMT_LIBRARY fmt::fmt)
|
||||
endif (LINUX)
|
||||
|
||||
if (WINDOWS)
|
||||
@@ -77,6 +75,6 @@ else (WINDOWS)
|
||||
set(WINDOWS_LIBRARIES "")
|
||||
endif (WINDOWS)
|
||||
|
||||
mark_as_advanced(DL_LIBRARY RT_LIBRARY PTHREAD_LIBRARY FMT_LIBRARY WINDOWS_LIBRARIES)
|
||||
mark_as_advanced(DL_LIBRARY RT_LIBRARY PTHREAD_LIBRARY WINDOWS_LIBRARIES)
|
||||
|
||||
endif(NOT DEFINED ${CMAKE_CURRENT_LIST_FILE}_INCLUDED)
|
||||
|
||||
@@ -270,6 +270,8 @@ if (NOT VIEWER_CHANNEL_GRK)
|
||||
set(VIEWER_CHANNEL_GRK "\\u03B1") # "α"
|
||||
elseif (VIEWER_CHANNEL_TYPE MATCHES "Beta")
|
||||
set(VIEWER_CHANNEL_GRK "\\u03B2") # "β"
|
||||
else()
|
||||
set(VIEWER_CHANNEL_GRK "")
|
||||
endif ()
|
||||
endif (NOT VIEWER_CHANNEL_GRK)
|
||||
|
||||
|
||||
@@ -9,21 +9,23 @@ FetchContent_Declare(
|
||||
Catch2
|
||||
GIT_REPOSITORY https://github.com/catchorg/Catch2.git
|
||||
GIT_TAG v2.11.0
|
||||
GIT_SHALLOW TRUE
|
||||
)
|
||||
FetchContent_Declare(
|
||||
fmt
|
||||
GIT_REPOSITORY https://github.com/fmtlib/fmt.git
|
||||
GIT_TAG 6.1.2
|
||||
GIT_TAG 8d78045e7cb44d39ad4cd95dd27816b8749e1944
|
||||
)
|
||||
FetchContent_Declare(
|
||||
nlohmann_json
|
||||
GIT_REPOSITORY https://github.com/nlohmann/json.git
|
||||
GIT_TAG v3.7.3
|
||||
GIT_SHALLOW TRUE
|
||||
)
|
||||
FetchContent_Declare(
|
||||
absl
|
||||
GIT_REPOSITORY https://github.com/abseil/abseil-cpp.git
|
||||
GIT_TAG 0033c9ea91a52ade7c6b725aa2ef3cbe15463421
|
||||
GIT_TAG 768eb2ca2857342673fcd462792ce04b8bac3fa3
|
||||
)
|
||||
|
||||
# This is a hack because absl has dumb cmake
|
||||
@@ -45,9 +47,7 @@ if (BUILD_TESTING)
|
||||
endif()
|
||||
|
||||
#Download the rest of the libraries
|
||||
if(WINDOWS)
|
||||
FetchContent_MakeAvailable(fmt)
|
||||
endif()
|
||||
|
||||
# Typically you don't care so much for a third party library's tests to be
|
||||
# run from your own project's code.
|
||||
|
||||
@@ -26,6 +26,7 @@ set(openjpeg_SOURCE_FILES
|
||||
mct.c
|
||||
mqc.c
|
||||
openjpeg.c
|
||||
opj_malloc.c
|
||||
phix_manager.c
|
||||
pi.c
|
||||
ppix_manager.c
|
||||
|
||||
@@ -31,11 +31,16 @@
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#define OPJ_SKIP_POISON
|
||||
#include "opj_includes.h"
|
||||
|
||||
#ifdef __SSE__
|
||||
#include <xmmintrin.h>
|
||||
#endif
|
||||
|
||||
#include "opj_includes.h"
|
||||
#if defined(__GNUC__)
|
||||
#pragma GCC poison malloc calloc realloc free
|
||||
#endif
|
||||
|
||||
/** @defgroup DWT DWT - Implementation of a discrete wavelet transform */
|
||||
/*@{*/
|
||||
@@ -499,7 +504,7 @@ void dwt_calc_explicit_stepsizes(opj_tccp_t * tccp, int prec) {
|
||||
/* <summary> */
|
||||
/* Determine maximum computed resolution level for inverse wavelet transform */
|
||||
/* </summary> */
|
||||
static int dwt_decode_max_resolution(opj_tcd_resolution_t* restrict r, int i) {
|
||||
static int dwt_decode_max_resolution(opj_tcd_resolution_t* OPJ_RESTRICT r, int i) {
|
||||
int mr = 1;
|
||||
int w;
|
||||
while( --i ) {
|
||||
@@ -531,7 +536,7 @@ static void dwt_decode_tile(opj_tcd_tilecomp_t* tilec, int numres, DWT1DFN dwt_1
|
||||
v.mem = h.mem;
|
||||
|
||||
while( --numres) {
|
||||
int * restrict tiledp = tilec->data;
|
||||
int * OPJ_RESTRICT tiledp = tilec->data;
|
||||
int j;
|
||||
|
||||
++tr;
|
||||
@@ -565,48 +570,49 @@ static void dwt_decode_tile(opj_tcd_tilecomp_t* tilec, int numres, DWT1DFN dwt_1
|
||||
opj_aligned_free(h.mem);
|
||||
}
|
||||
|
||||
static void v4dwt_interleave_h(v4dwt_t* restrict w, float* restrict a, int x, int size){
|
||||
float* restrict bi = (float*) (w->wavelet + w->cas);
|
||||
static void v4dwt_interleave_h(v4dwt_t* OPJ_RESTRICT w, float* OPJ_RESTRICT a, int x, int size) {
|
||||
float* OPJ_RESTRICT bi = (float*)(w->wavelet + w->cas);
|
||||
int count = w->sn;
|
||||
int i, k;
|
||||
for(k = 0; k < 2; ++k){
|
||||
if (count + 3 * x < size && ((size_t) a & 0x0f) == 0 && ((size_t) bi & 0x0f) == 0 && (x & 0x0f) == 0) {
|
||||
for (k = 0; k < 2; ++k) {
|
||||
if (count + 3 * x < size && ((size_t)a & 0x0f) == 0 && ((size_t)bi & 0x0f) == 0 && (x & 0x0f) == 0) {
|
||||
/* Fast code path */
|
||||
for(i = 0; i < count; ++i){
|
||||
for (i = 0; i < count; ++i) {
|
||||
int j = i;
|
||||
bi[i*8 ] = a[j];
|
||||
bi[i * 8] = a[j];
|
||||
j += x;
|
||||
bi[i*8 + 1] = a[j];
|
||||
bi[i * 8 + 1] = a[j];
|
||||
j += x;
|
||||
bi[i*8 + 2] = a[j];
|
||||
bi[i * 8 + 2] = a[j];
|
||||
j += x;
|
||||
bi[i*8 + 3] = a[j];
|
||||
bi[i * 8 + 3] = a[j];
|
||||
}
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
/* Slow code path */
|
||||
for(i = 0; i < count; ++i){
|
||||
int j = i;
|
||||
bi[i*8 ] = a[j];
|
||||
j += x;
|
||||
if(j > size) continue;
|
||||
bi[i*8 + 1] = a[j];
|
||||
j += x;
|
||||
if(j > size) continue;
|
||||
bi[i*8 + 2] = a[j];
|
||||
j += x;
|
||||
if(j > size) continue;
|
||||
bi[i*8 + 3] = a[j];
|
||||
for (i = 0; i < count; ++i) {
|
||||
int j = i;
|
||||
bi[i * 8] = a[j];
|
||||
j += x;
|
||||
if (j > size) continue;
|
||||
bi[i * 8 + 1] = a[j];
|
||||
j += x;
|
||||
if (j > size) continue;
|
||||
bi[i * 8 + 2] = a[j];
|
||||
j += x;
|
||||
if (j > size) continue;
|
||||
bi[i * 8 + 3] = a[j];
|
||||
}
|
||||
}
|
||||
}
|
||||
bi = (float*) (w->wavelet + 1 - w->cas);
|
||||
bi = (float*)(w->wavelet + 1 - w->cas);
|
||||
a += w->sn;
|
||||
size -= w->sn;
|
||||
count = w->dn;
|
||||
}
|
||||
}
|
||||
|
||||
static void v4dwt_interleave_v(v4dwt_t* restrict v , float* restrict a , int x){
|
||||
v4* restrict bi = v->wavelet + v->cas;
|
||||
static void v4dwt_interleave_v(v4dwt_t* OPJ_RESTRICT v , float* OPJ_RESTRICT a , int x){
|
||||
v4* OPJ_RESTRICT bi = v->wavelet + v->cas;
|
||||
int i;
|
||||
for(i = 0; i < v->sn; ++i){
|
||||
memcpy(&bi[i*2], &a[i*x], 4 * sizeof(float));
|
||||
@@ -621,7 +627,7 @@ static void v4dwt_interleave_v(v4dwt_t* restrict v , float* restrict a , int x){
|
||||
#ifdef __SSE__
|
||||
|
||||
static void v4dwt_decode_step1_sse(v4* w, int count, const __m128 c){
|
||||
__m128* restrict vw = (__m128*) w;
|
||||
__m128* OPJ_RESTRICT vw = (__m128*) w;
|
||||
int i;
|
||||
/* 4x unrolled loop */
|
||||
for(i = 0; i < count >> 2; ++i){
|
||||
@@ -642,22 +648,39 @@ static void v4dwt_decode_step1_sse(v4* w, int count, const __m128 c){
|
||||
}
|
||||
|
||||
static void v4dwt_decode_step2_sse(v4* l, v4* w, int k, int m, __m128 c){
|
||||
__m128* restrict vl = (__m128*) l;
|
||||
__m128* restrict vw = (__m128*) w;
|
||||
__m128* OPJ_RESTRICT vl = (__m128*) l;
|
||||
__m128* OPJ_RESTRICT vw = (__m128*) w;
|
||||
int i;
|
||||
__m128 tmp1, tmp2, tmp3;
|
||||
tmp1 = vl[0];
|
||||
for(i = 0; i < m; ++i){
|
||||
for (i = 0; i < m - 3; i += 4) {
|
||||
__m128 tmp4, tmp5, tmp6, tmp7, tmp8, tmp9;
|
||||
tmp2 = vw[-1];
|
||||
tmp3 = vw[0];
|
||||
tmp4 = vw[1];
|
||||
tmp5 = vw[2];
|
||||
tmp6 = vw[3];
|
||||
tmp7 = vw[4];
|
||||
tmp8 = vw[5];
|
||||
tmp9 = vw[6];
|
||||
vw[-1] = _mm_add_ps(tmp2, _mm_mul_ps(_mm_add_ps(tmp1, tmp3), c));
|
||||
vw[1] = _mm_add_ps(tmp4, _mm_mul_ps(_mm_add_ps(tmp3, tmp5), c));
|
||||
vw[3] = _mm_add_ps(tmp6, _mm_mul_ps(_mm_add_ps(tmp5, tmp7), c));
|
||||
vw[5] = _mm_add_ps(tmp8, _mm_mul_ps(_mm_add_ps(tmp7, tmp9), c));
|
||||
tmp1 = tmp9;
|
||||
vw += 8;
|
||||
}
|
||||
for ( ; i < m; ++i) {
|
||||
tmp2 = vw[-1];
|
||||
tmp3 = vw[ 0];
|
||||
vw[-1] = _mm_add_ps(tmp2, _mm_mul_ps(_mm_add_ps(tmp1, tmp3), c));
|
||||
tmp1 = tmp3;
|
||||
vw += 2;
|
||||
}
|
||||
vl = vw - 2;
|
||||
if(m >= k){
|
||||
return;
|
||||
}
|
||||
vl = vw - 2;
|
||||
c = _mm_add_ps(c, c);
|
||||
c = _mm_mul_ps(c, vl[0]);
|
||||
for(; m < k; ++m){
|
||||
@@ -670,7 +693,7 @@ static void v4dwt_decode_step2_sse(v4* l, v4* w, int k, int m, __m128 c){
|
||||
#else
|
||||
|
||||
static void v4dwt_decode_step1(v4* w, int count, const float c){
|
||||
float* restrict fw = (float*) w;
|
||||
float* OPJ_RESTRICT fw = (float*) w;
|
||||
int i;
|
||||
for(i = 0; i < count; ++i){
|
||||
float tmp1 = fw[i*8 ];
|
||||
@@ -685,8 +708,8 @@ static void v4dwt_decode_step1(v4* w, int count, const float c){
|
||||
}
|
||||
|
||||
static void v4dwt_decode_step2(v4* l, v4* w, int k, int m, float c){
|
||||
float* restrict fl = (float*) l;
|
||||
float* restrict fw = (float*) w;
|
||||
float* OPJ_RESTRICT fl = (float*) l;
|
||||
float* OPJ_RESTRICT fw = (float*) w;
|
||||
int i;
|
||||
for(i = 0; i < m; ++i){
|
||||
float tmp1_1 = fl[0];
|
||||
@@ -737,42 +760,44 @@ static void v4dwt_decode_step2(v4* l, v4* w, int k, int m, float c){
|
||||
/* <summary> */
|
||||
/* Inverse 9-7 wavelet transform in 1-D. */
|
||||
/* </summary> */
|
||||
static void v4dwt_decode(v4dwt_t* restrict dwt){
|
||||
static void v4dwt_decode(v4dwt_t* OPJ_RESTRICT dwt){
|
||||
int a, b;
|
||||
if(dwt->cas == 0) {
|
||||
if(!((dwt->dn > 0) || (dwt->sn > 1))){
|
||||
if (dwt->dn <= 0 && dwt->sn <= 1) {
|
||||
return;
|
||||
}
|
||||
a = 0;
|
||||
b = 1;
|
||||
}else{
|
||||
if(!((dwt->sn > 0) || (dwt->dn > 1))) {
|
||||
if (dwt->sn <= 0 && dwt->dn <= 1) {
|
||||
return;
|
||||
}
|
||||
a = 1;
|
||||
b = 0;
|
||||
}
|
||||
v4* OPJ_RESTRICT waveleta = dwt->wavelet + a;
|
||||
v4* OPJ_RESTRICT waveletb = dwt->wavelet + b;
|
||||
#ifdef __SSE__
|
||||
v4dwt_decode_step1_sse(dwt->wavelet+a, dwt->sn, _mm_set1_ps(K));
|
||||
v4dwt_decode_step1_sse(dwt->wavelet+b, dwt->dn, _mm_set1_ps(c13318));
|
||||
v4dwt_decode_step2_sse(dwt->wavelet+b, dwt->wavelet+a+1, dwt->sn, int_min(dwt->sn, dwt->dn-a), _mm_set1_ps(dwt_delta));
|
||||
v4dwt_decode_step2_sse(dwt->wavelet+a, dwt->wavelet+b+1, dwt->dn, int_min(dwt->dn, dwt->sn-b), _mm_set1_ps(dwt_gamma));
|
||||
v4dwt_decode_step2_sse(dwt->wavelet+b, dwt->wavelet+a+1, dwt->sn, int_min(dwt->sn, dwt->dn-a), _mm_set1_ps(dwt_beta));
|
||||
v4dwt_decode_step2_sse(dwt->wavelet+a, dwt->wavelet+b+1, dwt->dn, int_min(dwt->dn, dwt->sn-b), _mm_set1_ps(dwt_alpha));
|
||||
v4dwt_decode_step1_sse(waveleta, dwt->sn, _mm_set1_ps(K));
|
||||
v4dwt_decode_step1_sse(waveletb, dwt->dn, _mm_set1_ps(c13318));
|
||||
v4dwt_decode_step2_sse(waveletb, waveleta + 1, dwt->sn, int_min(dwt->sn, dwt->dn-a), _mm_set1_ps(dwt_delta));
|
||||
v4dwt_decode_step2_sse(waveleta, waveletb + 1, dwt->dn, int_min(dwt->dn, dwt->sn-b), _mm_set1_ps(dwt_gamma));
|
||||
v4dwt_decode_step2_sse(waveletb, waveleta + 1, dwt->sn, int_min(dwt->sn, dwt->dn-a), _mm_set1_ps(dwt_beta));
|
||||
v4dwt_decode_step2_sse(waveleta, waveletb + 1, dwt->dn, int_min(dwt->dn, dwt->sn-b), _mm_set1_ps(dwt_alpha));
|
||||
#else
|
||||
v4dwt_decode_step1(dwt->wavelet+a, dwt->sn, K);
|
||||
v4dwt_decode_step1(dwt->wavelet+b, dwt->dn, c13318);
|
||||
v4dwt_decode_step2(dwt->wavelet+b, dwt->wavelet+a+1, dwt->sn, int_min(dwt->sn, dwt->dn-a), dwt_delta);
|
||||
v4dwt_decode_step2(dwt->wavelet+a, dwt->wavelet+b+1, dwt->dn, int_min(dwt->dn, dwt->sn-b), dwt_gamma);
|
||||
v4dwt_decode_step2(dwt->wavelet+b, dwt->wavelet+a+1, dwt->sn, int_min(dwt->sn, dwt->dn-a), dwt_beta);
|
||||
v4dwt_decode_step2(dwt->wavelet+a, dwt->wavelet+b+1, dwt->dn, int_min(dwt->dn, dwt->sn-b), dwt_alpha);
|
||||
v4dwt_decode_step1(waveleta, dwt->sn, K);
|
||||
v4dwt_decode_step1(waveletb, dwt->dn, c13318);
|
||||
v4dwt_decode_step2(waveletb, waveleta + 1, dwt->sn, int_min(dwt->sn, dwt->dn-a), dwt_delta);
|
||||
v4dwt_decode_step2(waveleta, waveletb + 1, dwt->dn, int_min(dwt->dn, dwt->sn-b), dwt_gamma);
|
||||
v4dwt_decode_step2(waveletb, waveleta + 1, dwt->sn, int_min(dwt->sn, dwt->dn-a), dwt_beta);
|
||||
v4dwt_decode_step2(waveleta, waveletb + 1, dwt->dn, int_min(dwt->dn, dwt->sn-b), dwt_alpha);
|
||||
#endif
|
||||
}
|
||||
|
||||
/* <summary> */
|
||||
/* Inverse 9-7 wavelet transform in 2-D. */
|
||||
/* </summary> */
|
||||
void dwt_decode_real(opj_tcd_tilecomp_t* restrict tilec, int numres){
|
||||
void dwt_decode_real(opj_tcd_tilecomp_t* OPJ_RESTRICT tilec, int numres){
|
||||
v4dwt_t h;
|
||||
v4dwt_t v;
|
||||
|
||||
@@ -787,7 +812,7 @@ void dwt_decode_real(opj_tcd_tilecomp_t* restrict tilec, int numres){
|
||||
v.wavelet = h.wavelet;
|
||||
|
||||
while( --numres) {
|
||||
float * restrict aj = (float*) tilec->data;
|
||||
float * OPJ_RESTRICT aj = (float*) tilec->data;
|
||||
int bufsize = (tilec->x1 - tilec->x0) * (tilec->y1 - tilec->y0);
|
||||
int j;
|
||||
|
||||
|
||||
@@ -29,11 +29,16 @@
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#define OPJ_SKIP_POISON
|
||||
#include "opj_includes.h"
|
||||
|
||||
#ifdef __SSE__
|
||||
#include <xmmintrin.h>
|
||||
#endif
|
||||
|
||||
#include "opj_includes.h"
|
||||
#if defined(__GNUC__)
|
||||
#pragma GCC poison malloc calloc realloc free
|
||||
#endif
|
||||
|
||||
/* <summary> */
|
||||
/* This table contains the norms of the basis function of the reversible MCT. */
|
||||
@@ -49,17 +54,38 @@ static const double mct_norms_real[3] = { 1.732, 1.805, 1.573 };
|
||||
/* Foward reversible MCT. */
|
||||
/* </summary> */
|
||||
void mct_encode(
|
||||
int* restrict c0,
|
||||
int* restrict c1,
|
||||
int* restrict c2,
|
||||
int* OPJ_RESTRICT c0,
|
||||
int* OPJ_RESTRICT c1,
|
||||
int* OPJ_RESTRICT c2,
|
||||
int n)
|
||||
{
|
||||
int i;
|
||||
for(i = 0; i < n; ++i) {
|
||||
int i = 0;
|
||||
#ifdef __SSE2__
|
||||
/* Buffers are normally aligned on 16 bytes... */
|
||||
if (((size_t)c0 & 0xf) == 0 && ((size_t)c1 & 0xf) == 0 && ((size_t)c2 & 0xf) == 0) {
|
||||
const int cnt = n & ~3U;
|
||||
for (; i < cnt; i += 4) {
|
||||
__m128i y, u, v;
|
||||
__m128i r = _mm_load_si128((const __m128i*) & (c0[i]));
|
||||
__m128i g = _mm_load_si128((const __m128i*) & (c1[i]));
|
||||
__m128i b = _mm_load_si128((const __m128i*) & (c2[i]));
|
||||
y = _mm_add_epi32(g, g);
|
||||
y = _mm_add_epi32(y, b);
|
||||
y = _mm_add_epi32(y, r);
|
||||
y = _mm_srai_epi32(y, 2);
|
||||
u = _mm_sub_epi32(b, g);
|
||||
v = _mm_sub_epi32(r, g);
|
||||
_mm_store_si128((__m128i*) & (c0[i]), y);
|
||||
_mm_store_si128((__m128i*) & (c1[i]), u);
|
||||
_mm_store_si128((__m128i*) & (c2[i]), v);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
for (; i < n; ++i) {
|
||||
int r = c0[i];
|
||||
int g = c1[i];
|
||||
int b = c2[i];
|
||||
int y = (r + (g * 2) + b) >> 2;
|
||||
int y = (r + g + g + b) >> 2;
|
||||
int u = b - g;
|
||||
int v = r - g;
|
||||
c0[i] = y;
|
||||
@@ -72,13 +98,32 @@ void mct_encode(
|
||||
/* Inverse reversible MCT. */
|
||||
/* </summary> */
|
||||
void mct_decode(
|
||||
int* restrict c0,
|
||||
int* restrict c1,
|
||||
int* restrict c2,
|
||||
int* OPJ_RESTRICT c0,
|
||||
int* OPJ_RESTRICT c1,
|
||||
int* OPJ_RESTRICT c2,
|
||||
int n)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < n; ++i) {
|
||||
int i = 0;
|
||||
#ifdef __SSE2__
|
||||
/* Buffers are normally aligned on 16 bytes... */
|
||||
if (((size_t)c0 & 0xf) == 0 && ((size_t)c1 & 0xf) == 0 && ((size_t)c2 & 0xf) == 0) {
|
||||
const int cnt = n & ~3U;
|
||||
for (; i < cnt; i += 4) {
|
||||
__m128i r, g, b;
|
||||
__m128i y = _mm_load_si128((const __m128i*) & (c0[i]));
|
||||
__m128i u = _mm_load_si128((const __m128i*) & (c1[i]));
|
||||
__m128i v = _mm_load_si128((const __m128i*) & (c2[i]));
|
||||
g = y;
|
||||
g = _mm_sub_epi32(g, _mm_srai_epi32(_mm_add_epi32(u, v), 2));
|
||||
r = _mm_add_epi32(v, g);
|
||||
b = _mm_add_epi32(u, g);
|
||||
_mm_store_si128((__m128i*) & (c0[i]), r);
|
||||
_mm_store_si128((__m128i*) & (c1[i]), g);
|
||||
_mm_store_si128((__m128i*) & (c2[i]), b);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
for (; i < n; ++i) {
|
||||
int y = c0[i];
|
||||
int u = c1[i];
|
||||
int v = c2[i];
|
||||
@@ -102,13 +147,119 @@ double mct_getnorm(int compno) {
|
||||
/* Foward irreversible MCT. */
|
||||
/* </summary> */
|
||||
void mct_encode_real(
|
||||
int* restrict c0,
|
||||
int* restrict c1,
|
||||
int* restrict c2,
|
||||
int* OPJ_RESTRICT c0,
|
||||
int* OPJ_RESTRICT c1,
|
||||
int* OPJ_RESTRICT c2,
|
||||
int n)
|
||||
{
|
||||
int i;
|
||||
for(i = 0; i < n; ++i) {
|
||||
int i = 0;
|
||||
#ifdef __SSE4_1__
|
||||
/* Buffers are normally aligned on 16 bytes... */
|
||||
if (((size_t)c0 & 0xf) == 0 && ((size_t)c1 & 0xf) == 0 && ((size_t)c2 & 0xf) == 0) {
|
||||
const int cnt = n & ~3U;
|
||||
const __m128i ry = _mm_set1_epi32(2449);
|
||||
const __m128i gy = _mm_set1_epi32(4809);
|
||||
const __m128i by = _mm_set1_epi32(934);
|
||||
const __m128i ru = _mm_set1_epi32(1382);
|
||||
const __m128i gu = _mm_set1_epi32(2714);
|
||||
const __m128i gv = _mm_set1_epi32(3430);
|
||||
const __m128i bv = _mm_set1_epi32(666);
|
||||
const __m128i mulround = _mm_shuffle_epi32(_mm_cvtsi32_si128(4096), _MM_SHUFFLE(1, 0, 1, 0));
|
||||
for (; i < cnt; i += 4) {
|
||||
__m128i lo, hi, y, u, v;
|
||||
__m128i r = _mm_load_si128((const __m128i*) & (c0[i]));
|
||||
__m128i g = _mm_load_si128((const __m128i*) & (c1[i]));
|
||||
__m128i b = _mm_load_si128((const __m128i*) & (c2[i]));
|
||||
|
||||
hi = _mm_shuffle_epi32(r, _MM_SHUFFLE(3, 3, 1, 1));
|
||||
lo = _mm_mul_epi32(r, ry);
|
||||
hi = _mm_mul_epi32(hi, ry);
|
||||
lo = _mm_add_epi64(lo, mulround);
|
||||
hi = _mm_add_epi64(hi, mulround);
|
||||
lo = _mm_srli_epi64(lo, 13);
|
||||
hi = _mm_slli_epi64(hi, 32 - 13);
|
||||
y = _mm_blend_epi16(lo, hi, 0xCC);
|
||||
|
||||
hi = _mm_shuffle_epi32(g, _MM_SHUFFLE(3, 3, 1, 1));
|
||||
lo = _mm_mul_epi32(g, gy);
|
||||
hi = _mm_mul_epi32(hi, gy);
|
||||
lo = _mm_add_epi64(lo, mulround);
|
||||
hi = _mm_add_epi64(hi, mulround);
|
||||
lo = _mm_srli_epi64(lo, 13);
|
||||
hi = _mm_slli_epi64(hi, 32 - 13);
|
||||
y = _mm_add_epi32(y, _mm_blend_epi16(lo, hi, 0xCC));
|
||||
|
||||
hi = _mm_shuffle_epi32(b, _MM_SHUFFLE(3, 3, 1, 1));
|
||||
lo = _mm_mul_epi32(b, by);
|
||||
hi = _mm_mul_epi32(hi, by);
|
||||
lo = _mm_add_epi64(lo, mulround);
|
||||
hi = _mm_add_epi64(hi, mulround);
|
||||
lo = _mm_srli_epi64(lo, 13);
|
||||
hi = _mm_slli_epi64(hi, 32 - 13);
|
||||
y = _mm_add_epi32(y, _mm_blend_epi16(lo, hi, 0xCC));
|
||||
_mm_store_si128((__m128i*) & (c0[i]), y);
|
||||
|
||||
lo = _mm_cvtepi32_epi64(_mm_shuffle_epi32(b, _MM_SHUFFLE(3, 2, 2, 0)));
|
||||
hi = _mm_cvtepi32_epi64(_mm_shuffle_epi32(b, _MM_SHUFFLE(3, 2, 3, 1)));
|
||||
lo = _mm_slli_epi64(lo, 12);
|
||||
hi = _mm_slli_epi64(hi, 12);
|
||||
lo = _mm_add_epi64(lo, mulround);
|
||||
hi = _mm_add_epi64(hi, mulround);
|
||||
lo = _mm_srli_epi64(lo, 13);
|
||||
hi = _mm_slli_epi64(hi, 32 - 13);
|
||||
u = _mm_blend_epi16(lo, hi, 0xCC);
|
||||
|
||||
hi = _mm_shuffle_epi32(r, _MM_SHUFFLE(3, 3, 1, 1));
|
||||
lo = _mm_mul_epi32(r, ru);
|
||||
hi = _mm_mul_epi32(hi, ru);
|
||||
lo = _mm_add_epi64(lo, mulround);
|
||||
hi = _mm_add_epi64(hi, mulround);
|
||||
lo = _mm_srli_epi64(lo, 13);
|
||||
hi = _mm_slli_epi64(hi, 32 - 13);
|
||||
u = _mm_sub_epi32(u, _mm_blend_epi16(lo, hi, 0xCC));
|
||||
|
||||
hi = _mm_shuffle_epi32(g, _MM_SHUFFLE(3, 3, 1, 1));
|
||||
lo = _mm_mul_epi32(g, gu);
|
||||
hi = _mm_mul_epi32(hi, gu);
|
||||
lo = _mm_add_epi64(lo, mulround);
|
||||
hi = _mm_add_epi64(hi, mulround);
|
||||
lo = _mm_srli_epi64(lo, 13);
|
||||
hi = _mm_slli_epi64(hi, 32 - 13);
|
||||
u = _mm_sub_epi32(u, _mm_blend_epi16(lo, hi, 0xCC));
|
||||
_mm_store_si128((__m128i*) & (c1[i]), u);
|
||||
|
||||
lo = _mm_cvtepi32_epi64(_mm_shuffle_epi32(r, _MM_SHUFFLE(3, 2, 2, 0)));
|
||||
hi = _mm_cvtepi32_epi64(_mm_shuffle_epi32(r, _MM_SHUFFLE(3, 2, 3, 1)));
|
||||
lo = _mm_slli_epi64(lo, 12);
|
||||
hi = _mm_slli_epi64(hi, 12);
|
||||
lo = _mm_add_epi64(lo, mulround);
|
||||
hi = _mm_add_epi64(hi, mulround);
|
||||
lo = _mm_srli_epi64(lo, 13);
|
||||
hi = _mm_slli_epi64(hi, 32 - 13);
|
||||
v = _mm_blend_epi16(lo, hi, 0xCC);
|
||||
|
||||
hi = _mm_shuffle_epi32(g, _MM_SHUFFLE(3, 3, 1, 1));
|
||||
lo = _mm_mul_epi32(g, gv);
|
||||
hi = _mm_mul_epi32(hi, gv);
|
||||
lo = _mm_add_epi64(lo, mulround);
|
||||
hi = _mm_add_epi64(hi, mulround);
|
||||
lo = _mm_srli_epi64(lo, 13);
|
||||
hi = _mm_slli_epi64(hi, 32 - 13);
|
||||
v = _mm_sub_epi32(v, _mm_blend_epi16(lo, hi, 0xCC));
|
||||
|
||||
hi = _mm_shuffle_epi32(b, _MM_SHUFFLE(3, 3, 1, 1));
|
||||
lo = _mm_mul_epi32(b, bv);
|
||||
hi = _mm_mul_epi32(hi, bv);
|
||||
lo = _mm_add_epi64(lo, mulround);
|
||||
hi = _mm_add_epi64(hi, mulround);
|
||||
lo = _mm_srli_epi64(lo, 13);
|
||||
hi = _mm_slli_epi64(hi, 32 - 13);
|
||||
v = _mm_sub_epi32(v, _mm_blend_epi16(lo, hi, 0xCC));
|
||||
_mm_store_si128((__m128i*) & (c2[i]), v);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
for (; i < n; ++i) {
|
||||
int r = c0[i];
|
||||
int g = c1[i];
|
||||
int b = c2[i];
|
||||
@@ -125,19 +276,21 @@ void mct_encode_real(
|
||||
/* Inverse irreversible MCT. */
|
||||
/* </summary> */
|
||||
void mct_decode_real(
|
||||
float* restrict c0,
|
||||
float* restrict c1,
|
||||
float* restrict c2,
|
||||
float* OPJ_RESTRICT c0,
|
||||
float* OPJ_RESTRICT c1,
|
||||
float* OPJ_RESTRICT c2,
|
||||
int n)
|
||||
{
|
||||
int i;
|
||||
#ifdef __SSE__
|
||||
int count;
|
||||
__m128 vrv, vgu, vgv, vbu;
|
||||
vrv = _mm_set1_ps(1.402f);
|
||||
vgu = _mm_set1_ps(0.34413f);
|
||||
vgv = _mm_set1_ps(0.71414f);
|
||||
vbu = _mm_set1_ps(1.772f);
|
||||
for (i = 0; i < (n >> 3); ++i) {
|
||||
count = n >> 3;
|
||||
for (i = 0; i < count; ++i) {
|
||||
__m128 vy, vu, vv;
|
||||
__m128 vr, vg, vb;
|
||||
|
||||
@@ -174,7 +327,7 @@ void mct_decode_real(
|
||||
float u = c1[i];
|
||||
float v = c2[i];
|
||||
float r = y + (v * 1.402f);
|
||||
float g = y - (u * 0.34413f) - (v * (0.71414f));
|
||||
float g = y - (u * 0.34413f) - (v * 0.71414f);
|
||||
float b = y + (u * 1.772f);
|
||||
c0[i] = r;
|
||||
c1[i] = g;
|
||||
|
||||
@@ -40,33 +40,71 @@
|
||||
==========================================================
|
||||
*/
|
||||
|
||||
/*
|
||||
The inline keyword is supported by C99 but not by C90.
|
||||
Most compilers implement their own version of this keyword ...
|
||||
*/
|
||||
#ifndef INLINE
|
||||
#if defined(_MSC_VER)
|
||||
#define INLINE __forceinline
|
||||
#elif defined(__GNUC__)
|
||||
#define INLINE __inline__
|
||||
#elif defined(__MWERKS__)
|
||||
#define INLINE inline
|
||||
#else
|
||||
/* add other compilers here ... */
|
||||
#define INLINE
|
||||
#endif /* defined(<Compiler>) */
|
||||
#endif /* INLINE */
|
||||
#if defined(OPJ_STATIC) || !defined(_WIN32)
|
||||
#define OPJ_API
|
||||
#define OPJ_CALLCONV
|
||||
#else
|
||||
#define OPJ_CALLCONV __stdcall
|
||||
/*
|
||||
The following ifdef block is the standard way of creating macros which make exporting
|
||||
The following ifdef block is the standard way of creating macros which make exporting
|
||||
from a DLL simpler. All files within this DLL are compiled with the OPJ_EXPORTS
|
||||
symbol defined on the command line. this symbol should not be defined on any project
|
||||
that uses this DLL. This way any other project whose source files include this file see
|
||||
OPJ_API functions as being imported from a DLL, wheras this DLL sees symbols
|
||||
that uses this DLL. This way any other project whose source files include this file see
|
||||
OPJ_API functions as being imported from a DLL, whereas this DLL sees symbols
|
||||
defined with this macro as being exported.
|
||||
*/
|
||||
#if defined(OPJ_EXPORTS) || defined(DLL_EXPORT)
|
||||
#define OPJ_API __declspec(dllexport)
|
||||
#else
|
||||
#define OPJ_API __declspec(dllimport)
|
||||
#endif /* OPJ_EXPORTS */
|
||||
# if defined(OPJ_EXPORTS) || defined(DLL_EXPORT)
|
||||
# define OPJ_API __declspec(dllexport)
|
||||
# else
|
||||
# define OPJ_API __declspec(dllimport)
|
||||
# endif /* OPJ_EXPORTS */
|
||||
#endif /* !OPJ_STATIC || !_WIN32 */
|
||||
|
||||
typedef int opj_bool;
|
||||
#define OPJ_TRUE 1
|
||||
#define OPJ_FALSE 0
|
||||
|
||||
typedef char OPJ_CHAR;
|
||||
typedef float OPJ_FLOAT32;
|
||||
typedef double OPJ_FLOAT64;
|
||||
typedef unsigned char OPJ_BYTE;
|
||||
|
||||
#include "opj_stdint.h"
|
||||
|
||||
typedef int8_t OPJ_INT8;
|
||||
typedef uint8_t OPJ_UINT8;
|
||||
typedef int16_t OPJ_INT16;
|
||||
typedef uint16_t OPJ_UINT16;
|
||||
typedef int32_t OPJ_INT32;
|
||||
typedef uint32_t OPJ_UINT32;
|
||||
typedef int64_t OPJ_INT64;
|
||||
typedef uint64_t OPJ_UINT64;
|
||||
|
||||
typedef int64_t OPJ_OFF_T; /* 64-bit file offset type */
|
||||
|
||||
#include <stdio.h>
|
||||
typedef size_t OPJ_SIZE_T;
|
||||
|
||||
/* Avoid compile-time warning because parameter is not used */
|
||||
#define OPJ_ARG_NOT_USED(x) (void)(x)
|
||||
/*
|
||||
|
||||
/*
|
||||
==========================================================
|
||||
Useful constant definitions
|
||||
==========================================================
|
||||
|
||||
@@ -40,6 +40,8 @@
|
||||
#include <stdio.h>
|
||||
#include <stdarg.h>
|
||||
#include <ctype.h>
|
||||
#include <assert.h>
|
||||
#include <limits.h>
|
||||
|
||||
/*
|
||||
==========================================================
|
||||
@@ -54,56 +56,115 @@
|
||||
==========================================================
|
||||
*/
|
||||
|
||||
/* Are restricted pointers available? (C99) */
|
||||
#if (__STDC_VERSION__ >= 199901L)
|
||||
#define OPJ_RESTRICT restrict
|
||||
#else
|
||||
/* Not a C99 compiler */
|
||||
#if defined(__GNUC__)
|
||||
#define OPJ_RESTRICT __restrict__
|
||||
#elif defined(_MSC_VER) && (_MSC_VER >= 1400)
|
||||
#define OPJ_RESTRICT __restrict
|
||||
#else
|
||||
#define OPJ_RESTRICT /* restrict */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
/* Ignore GCC attributes if this is not GCC */
|
||||
#ifndef __GNUC__
|
||||
#define __attribute__(x) /* __attribute__(x) */
|
||||
#endif
|
||||
|
||||
/*
|
||||
The inline keyword is supported by C99 but not by C90.
|
||||
Most compilers implement their own version of this keyword ...
|
||||
*/
|
||||
#ifndef INLINE
|
||||
#if defined(_MSC_VER)
|
||||
#define INLINE __forceinline
|
||||
#elif defined(__GNUC__)
|
||||
#define INLINE __inline__
|
||||
#elif defined(__MWERKS__)
|
||||
#define INLINE inline
|
||||
#else
|
||||
/* add other compilers here ... */
|
||||
#define INLINE
|
||||
#endif /* defined(<Compiler>) */
|
||||
#endif /* INLINE */
|
||||
|
||||
/* Are restricted pointers available? (C99) */
|
||||
#if (__STDC_VERSION__ != 199901L)
|
||||
/* Not a C99 compiler */
|
||||
#ifdef __GNUC__
|
||||
#define restrict __restrict__
|
||||
#else
|
||||
#define restrict /* restrict */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
/* MSVC and Borland C do not have lrintf */
|
||||
#if defined(_MSC_VER) || defined(__BORLANDC__)
|
||||
static INLINE long lrintf(float f){
|
||||
/* MSVC before 2013 and Borland C do not have lrintf */
|
||||
#if defined(_MSC_VER)
|
||||
#include <intrin.h>
|
||||
static INLINE long opj_lrintf(float f)
|
||||
{
|
||||
#ifdef _M_X64
|
||||
return (long)((f>0.0f) ? (f + 0.5f):(f -0.5f));
|
||||
#else
|
||||
return _mm_cvt_ss2si(_mm_load_ss(&f));
|
||||
|
||||
/* commented out line breaks many tests */
|
||||
/* return (long)((f>0.0f) ? (f + 0.5f):(f -0.5f)); */
|
||||
#elif defined(_M_IX86)
|
||||
int i;
|
||||
|
||||
_asm{
|
||||
fld f
|
||||
fistp i
|
||||
};
|
||||
|
||||
|
||||
return i;
|
||||
#else
|
||||
return (long)((f>0.0f) ? (f + 0.5f) : (f - 0.5f));
|
||||
#endif
|
||||
}
|
||||
#elif defined(__BORLANDC__)
|
||||
static INLINE long opj_lrintf(float f)
|
||||
{
|
||||
#ifdef _M_X64
|
||||
return (long)((f > 0.0f) ? (f + 0.5f) : (f - 0.5f));
|
||||
#else
|
||||
int i;
|
||||
|
||||
_asm {
|
||||
fld f
|
||||
fistp i
|
||||
};
|
||||
|
||||
return i;
|
||||
#endif
|
||||
}
|
||||
#else
|
||||
static INLINE long opj_lrintf(float f)
|
||||
{
|
||||
return lrintf(f);
|
||||
}
|
||||
#endif
|
||||
|
||||
#if defined(_MSC_VER) && (_MSC_VER < 1400)
|
||||
#define vsnprintf _vsnprintf
|
||||
#endif
|
||||
|
||||
/* MSVC x86 is really bad at doing int64 = int32 * int32 on its own. Use intrinsic. */
|
||||
#if defined(_MSC_VER) && (_MSC_VER >= 1400) && !defined(__INTEL_COMPILER) && defined(_M_IX86)
|
||||
# include <intrin.h>
|
||||
# pragma intrinsic(__emul)
|
||||
#endif
|
||||
|
||||
/* Apparently Visual Studio doesn't define __SSE__ / __SSE2__ macros */
|
||||
#if defined(_M_X64)
|
||||
/* Intel 64bit support SSE and SSE2 */
|
||||
# ifndef __SSE__
|
||||
# define __SSE__ 1
|
||||
# endif
|
||||
# ifndef __SSE2__
|
||||
# define __SSE2__ 1
|
||||
# endif
|
||||
# if !defined(__SSE4_1__) && defined(__AVX__)
|
||||
# define __SSE4_1__ 1
|
||||
# endif
|
||||
#endif
|
||||
|
||||
/* For x86, test the value of the _M_IX86_FP macro. */
|
||||
/* See https://msdn.microsoft.com/en-us/library/b0084kay.aspx */
|
||||
#if defined(_M_IX86_FP)
|
||||
# if _M_IX86_FP >= 1
|
||||
# ifndef __SSE__
|
||||
# define __SSE__ 1
|
||||
# endif
|
||||
# endif
|
||||
# if _M_IX86_FP >= 2
|
||||
# ifndef __SSE2__
|
||||
# define __SSE2__ 1
|
||||
# endif
|
||||
# endif
|
||||
#endif
|
||||
|
||||
/* Type to use for bit-fields in internal headers */
|
||||
typedef unsigned int OPJ_BITFIELD;
|
||||
|
||||
#define OPJ_UNUSED(x) (void)x
|
||||
|
||||
#include "j2k_lib.h"
|
||||
#include "opj_malloc.h"
|
||||
#include "event.h"
|
||||
|
||||
249
indra/libopenjpeg/opj_malloc.c
Normal file
249
indra/libopenjpeg/opj_malloc.c
Normal file
@@ -0,0 +1,249 @@
|
||||
/*
|
||||
* The copyright in this software is being made available under the 2-clauses
|
||||
* BSD License, included below. This software may be subject to other third
|
||||
* party and contributor rights, including patent rights, and no such rights
|
||||
* are granted under this license.
|
||||
*
|
||||
* Copyright (c) 2015, Mathieu Malaterre <mathieu.malaterre@gmail.com>
|
||||
* Copyright (c) 2015, Matthieu Darbois
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS `AS IS'
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
#define OPJ_SKIP_POISON
|
||||
#include "opj_includes.h"
|
||||
|
||||
#if defined(OPJ_HAVE_MALLOC_H) && defined(OPJ_HAVE_MEMALIGN)
|
||||
# include <malloc.h>
|
||||
#endif
|
||||
|
||||
#ifndef SIZE_MAX
|
||||
# define SIZE_MAX ((size_t) -1)
|
||||
#endif
|
||||
|
||||
static INLINE void *opj_aligned_alloc_n(size_t alignment, size_t size)
|
||||
{
|
||||
void* ptr;
|
||||
|
||||
/* alignment shall be power of 2 */
|
||||
assert((alignment != 0U) && ((alignment & (alignment - 1U)) == 0U));
|
||||
/* alignment shall be at least sizeof(void*) */
|
||||
assert(alignment >= sizeof(void*));
|
||||
|
||||
if (size == 0U) { /* prevent implementation defined behavior of realloc */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
#if defined(OPJ_HAVE_POSIX_MEMALIGN)
|
||||
/* aligned_alloc requires c11, restrict to posix_memalign for now. Quote:
|
||||
* This function was introduced in POSIX 1003.1d. Although this function is
|
||||
* superseded by aligned_alloc, it is more portable to older POSIX systems
|
||||
* that do not support ISO C11. */
|
||||
if (posix_memalign(&ptr, alignment, size)) {
|
||||
ptr = NULL;
|
||||
}
|
||||
/* older linux */
|
||||
#elif defined(OPJ_HAVE_MEMALIGN)
|
||||
ptr = memalign(alignment, size);
|
||||
/* _MSC_VER */
|
||||
#elif defined(OPJ_HAVE__ALIGNED_MALLOC)
|
||||
ptr = _aligned_malloc(size, alignment);
|
||||
#else
|
||||
/*
|
||||
* Generic aligned malloc implementation.
|
||||
* Uses size_t offset for the integer manipulation of the pointer,
|
||||
* as uintptr_t is not available in C89 to do
|
||||
* bitwise operations on the pointer itself.
|
||||
*/
|
||||
alignment--;
|
||||
{
|
||||
size_t offset;
|
||||
OPJ_UINT8 *mem;
|
||||
|
||||
/* Room for padding and extra pointer stored in front of allocated area */
|
||||
size_t overhead = alignment + sizeof(void *);
|
||||
|
||||
/* let's be extra careful */
|
||||
assert(alignment <= (SIZE_MAX - sizeof(void *)));
|
||||
|
||||
/* Avoid integer overflow */
|
||||
if (size > (SIZE_MAX - overhead)) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
mem = (OPJ_UINT8*)malloc(size + overhead);
|
||||
if (mem == NULL) {
|
||||
return mem;
|
||||
}
|
||||
/* offset = ((alignment + 1U) - ((size_t)(mem + sizeof(void*)) & alignment)) & alignment; */
|
||||
/* Use the fact that alignment + 1U is a power of 2 */
|
||||
offset = ((alignment ^ ((size_t)(mem + sizeof(void*)) & alignment)) + 1U) &
|
||||
alignment;
|
||||
ptr = (void *)(mem + sizeof(void*) + offset);
|
||||
((void**) ptr)[-1] = mem;
|
||||
}
|
||||
#endif
|
||||
return ptr;
|
||||
}
|
||||
static INLINE void *opj_aligned_realloc_n(void *ptr, size_t alignment,
|
||||
size_t new_size)
|
||||
{
|
||||
void *r_ptr;
|
||||
|
||||
/* alignment shall be power of 2 */
|
||||
assert((alignment != 0U) && ((alignment & (alignment - 1U)) == 0U));
|
||||
/* alignment shall be at least sizeof(void*) */
|
||||
assert(alignment >= sizeof(void*));
|
||||
|
||||
if (new_size == 0U) { /* prevent implementation defined behavior of realloc */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* no portable aligned realloc */
|
||||
#if defined(OPJ_HAVE_POSIX_MEMALIGN) || defined(OPJ_HAVE_MEMALIGN)
|
||||
/* glibc doc states one can mix aligned malloc with realloc */
|
||||
r_ptr = realloc(ptr, new_size); /* fast path */
|
||||
/* we simply use `size_t` to cast, since we are only interest in binary AND
|
||||
* operator */
|
||||
if (((size_t)r_ptr & (alignment - 1U)) != 0U) {
|
||||
/* this is non-trivial to implement a portable aligned realloc, so use a
|
||||
* simple approach where we do not need a function that return the size of an
|
||||
* allocated array (eg. _msize on Windows, malloc_size on MacOS,
|
||||
* malloc_usable_size on systems with glibc) */
|
||||
void *a_ptr = opj_aligned_alloc_n(alignment, new_size);
|
||||
if (a_ptr != NULL) {
|
||||
memcpy(a_ptr, r_ptr, new_size);
|
||||
}
|
||||
free(r_ptr);
|
||||
r_ptr = a_ptr;
|
||||
}
|
||||
/* _MSC_VER */
|
||||
#elif defined(OPJ_HAVE__ALIGNED_MALLOC)
|
||||
r_ptr = _aligned_realloc(ptr, new_size, alignment);
|
||||
#else
|
||||
if (ptr == NULL) {
|
||||
return opj_aligned_alloc_n(alignment, new_size);
|
||||
}
|
||||
alignment--;
|
||||
{
|
||||
void *oldmem;
|
||||
OPJ_UINT8 *newmem;
|
||||
size_t overhead = alignment + sizeof(void *);
|
||||
|
||||
/* let's be extra careful */
|
||||
assert(alignment <= (SIZE_MAX - sizeof(void *)));
|
||||
|
||||
/* Avoid integer overflow */
|
||||
if (new_size > SIZE_MAX - overhead) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
oldmem = ((void**) ptr)[-1];
|
||||
newmem = (OPJ_UINT8*)realloc(oldmem, new_size + overhead);
|
||||
if (newmem == NULL) {
|
||||
return newmem;
|
||||
}
|
||||
|
||||
if (newmem == oldmem) {
|
||||
r_ptr = ptr;
|
||||
} else {
|
||||
size_t old_offset;
|
||||
size_t new_offset;
|
||||
|
||||
/* realloc created a new copy, realign the copied memory block */
|
||||
old_offset = (size_t)((OPJ_UINT8*)ptr - (OPJ_UINT8*)oldmem);
|
||||
|
||||
/* offset = ((alignment + 1U) - ((size_t)(mem + sizeof(void*)) & alignment)) & alignment; */
|
||||
/* Use the fact that alignment + 1U is a power of 2 */
|
||||
new_offset = ((alignment ^ ((size_t)(newmem + sizeof(void*)) & alignment)) +
|
||||
1U) & alignment;
|
||||
new_offset += sizeof(void*);
|
||||
r_ptr = (void *)(newmem + new_offset);
|
||||
|
||||
if (new_offset != old_offset) {
|
||||
memmove(newmem + new_offset, newmem + old_offset, new_size);
|
||||
}
|
||||
((void**) r_ptr)[-1] = newmem;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
return r_ptr;
|
||||
}
|
||||
void * opj_malloc(size_t size)
|
||||
{
|
||||
if (size == 0U) { /* prevent implementation defined behavior of realloc */
|
||||
return NULL;
|
||||
}
|
||||
return malloc(size);
|
||||
}
|
||||
void * opj_calloc(size_t num, size_t size)
|
||||
{
|
||||
if (num == 0 || size == 0) {
|
||||
/* prevent implementation defined behavior of realloc */
|
||||
return NULL;
|
||||
}
|
||||
return calloc(num, size);
|
||||
}
|
||||
|
||||
void *opj_aligned_malloc(size_t size)
|
||||
{
|
||||
return opj_aligned_alloc_n(16U, size);
|
||||
}
|
||||
void * opj_aligned_realloc(void *ptr, size_t size)
|
||||
{
|
||||
return opj_aligned_realloc_n(ptr, 16U, size);
|
||||
}
|
||||
|
||||
void *opj_aligned_32_malloc(size_t size)
|
||||
{
|
||||
return opj_aligned_alloc_n(32U, size);
|
||||
}
|
||||
void * opj_aligned_32_realloc(void *ptr, size_t size)
|
||||
{
|
||||
return opj_aligned_realloc_n(ptr, 32U, size);
|
||||
}
|
||||
|
||||
void opj_aligned_free(void* ptr)
|
||||
{
|
||||
#if defined(OPJ_HAVE_POSIX_MEMALIGN) || defined(OPJ_HAVE_MEMALIGN)
|
||||
free(ptr);
|
||||
#elif defined(OPJ_HAVE__ALIGNED_MALLOC)
|
||||
_aligned_free(ptr);
|
||||
#else
|
||||
/* Generic implementation has malloced pointer stored in front of used area */
|
||||
if (ptr != NULL) {
|
||||
free(((void**) ptr)[-1]);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void * opj_realloc(void *ptr, size_t new_size)
|
||||
{
|
||||
if (new_size == 0U) { /* prevent implementation defined behavior of realloc */
|
||||
return NULL;
|
||||
}
|
||||
return realloc(ptr, new_size);
|
||||
}
|
||||
void opj_free(void *ptr)
|
||||
{
|
||||
free(ptr);
|
||||
}
|
||||
@@ -1,4 +1,9 @@
|
||||
/*
|
||||
* The copyright in this software is being made available under the 2-clauses
|
||||
* BSD License, included below. This software may be subject to other third
|
||||
* party and contributor rights, including patent rights, and no such rights
|
||||
* are granted under this license.
|
||||
*
|
||||
* Copyright (c) 2005, Herve Drolon, FreeImage Team
|
||||
* Copyright (c) 2007, Callum Lerwick <seg@haxxed.com>
|
||||
* All rights reserved.
|
||||
@@ -24,8 +29,10 @@
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
#ifndef __OPJ_MALLOC_H
|
||||
#define __OPJ_MALLOC_H
|
||||
#ifndef OPJ_MALLOC_H
|
||||
#define OPJ_MALLOC_H
|
||||
|
||||
#include <stddef.h>
|
||||
/**
|
||||
@file opj_malloc.h
|
||||
@brief Internal functions
|
||||
@@ -36,6 +43,17 @@ The functions in opj_malloc.h are internal utilities used for memory management.
|
||||
/** @defgroup MISC MISC - Miscellaneous internal functions */
|
||||
/*@{*/
|
||||
|
||||
/* FIXME: These should be set with cmake tests, but we're currently not requiring use of cmake */
|
||||
#ifdef _WIN32
|
||||
#define OPJ_HAVE__ALIGNED_MALLOC
|
||||
#else /* Not _WIN32 */
|
||||
#if defined(__sun)
|
||||
#define OPJ_HAVE_MEMALIGN
|
||||
#elif defined(__linux__) || defined(__APPLE__) || defined(__FreeBSD__)
|
||||
#define OPJ_HAVE_POSIX_MEMALIGN
|
||||
#endif
|
||||
#endif
|
||||
|
||||
/** @name Exported functions */
|
||||
/*@{*/
|
||||
/* ----------------------------------------------------------------------- */
|
||||
@@ -45,90 +63,32 @@ Allocate an uninitialized memory block
|
||||
@param size Bytes to allocate
|
||||
@return Returns a void pointer to the allocated space, or NULL if there is insufficient memory available
|
||||
*/
|
||||
#ifdef ALLOC_PERF_OPT
|
||||
void * OPJ_CALLCONV opj_malloc(size_t size);
|
||||
#else
|
||||
#define opj_malloc(size) malloc(size)
|
||||
#endif
|
||||
void * opj_malloc(size_t size);
|
||||
|
||||
/**
|
||||
Allocate a memory block with elements initialized to 0
|
||||
@param num Blocks to allocate
|
||||
@param size Bytes per block to allocate
|
||||
@param numOfElements Blocks to allocate
|
||||
@param sizeOfElements Bytes per block to allocate
|
||||
@return Returns a void pointer to the allocated space, or NULL if there is insufficient memory available
|
||||
*/
|
||||
#ifdef ALLOC_PERF_OPT
|
||||
void * OPJ_CALLCONV opj_calloc(size_t _NumOfElements, size_t _SizeOfElements);
|
||||
#else
|
||||
#define opj_calloc(num, size) calloc(num, size)
|
||||
#endif
|
||||
void * opj_calloc(size_t numOfElements, size_t sizeOfElements);
|
||||
|
||||
/**
|
||||
Allocate memory aligned to a 16 byte boundry
|
||||
Allocate memory aligned to a 16 byte boundary
|
||||
@param size Bytes to allocate
|
||||
@return Returns a void pointer to the allocated space, or NULL if there is insufficient memory available
|
||||
*/
|
||||
/* FIXME: These should be set with cmake tests, but we're currently not requiring use of cmake */
|
||||
#ifdef _WIN32
|
||||
/* Someone should tell the mingw people that their malloc.h ought to provide _mm_malloc() */
|
||||
#ifdef __GNUC__
|
||||
#include <mm_malloc.h>
|
||||
#define HAVE_MM_MALLOC
|
||||
#else /* MSVC, Intel C++ */
|
||||
#include <malloc.h>
|
||||
#ifdef _mm_malloc
|
||||
#define HAVE_MM_MALLOC
|
||||
#endif
|
||||
#endif
|
||||
#else /* Not _WIN32 */
|
||||
#if defined(__sun)
|
||||
#define HAVE_MEMALIGN
|
||||
#elif defined(__FreeBSD__)
|
||||
#define HAVE_POSIX_MEMALIGN
|
||||
/* Linux x86_64 and OSX always align allocations to 16 bytes */
|
||||
#elif !defined(__amd64__) && !defined(__APPLE__) && !defined(_AIX)
|
||||
#define HAVE_MEMALIGN
|
||||
#include <malloc.h>
|
||||
#endif
|
||||
#endif
|
||||
void * opj_aligned_malloc(size_t size);
|
||||
void * opj_aligned_realloc(void *ptr, size_t size);
|
||||
void opj_aligned_free(void* ptr);
|
||||
|
||||
#define opj_aligned_malloc(size) malloc(size)
|
||||
#define opj_aligned_free(m) free(m)
|
||||
|
||||
#ifdef HAVE_MM_MALLOC
|
||||
#undef opj_aligned_malloc
|
||||
#define opj_aligned_malloc(size) _mm_malloc(size, 16)
|
||||
#undef opj_aligned_free
|
||||
#define opj_aligned_free(m) _mm_free(m)
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_MEMALIGN
|
||||
extern void* memalign(size_t, size_t);
|
||||
#undef opj_aligned_malloc
|
||||
#define opj_aligned_malloc(size) memalign(16, (size))
|
||||
#undef opj_aligned_free
|
||||
#define opj_aligned_free(m) free(m)
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_POSIX_MEMALIGN
|
||||
#undef opj_aligned_malloc
|
||||
extern int posix_memalign(void**, size_t, size_t);
|
||||
|
||||
static INLINE void* __attribute__ ((malloc)) opj_aligned_malloc(size_t size){
|
||||
void* mem = NULL;
|
||||
posix_memalign(&mem, 16, size);
|
||||
return mem;
|
||||
}
|
||||
#undef opj_aligned_free
|
||||
#define opj_aligned_free(m) free(m)
|
||||
#endif
|
||||
|
||||
#ifdef ALLOC_PERF_OPT
|
||||
#undef opj_aligned_malloc
|
||||
#define opj_aligned_malloc(size) opj_malloc(size)
|
||||
#undef opj_aligned_free
|
||||
#define opj_aligned_free(m) opj_free(m)
|
||||
#endif
|
||||
/**
|
||||
Allocate memory aligned to a 32 byte boundary
|
||||
@param size Bytes to allocate
|
||||
@return Returns a void pointer to the allocated space, or NULL if there is insufficient memory available
|
||||
*/
|
||||
void * opj_aligned_32_malloc(size_t size);
|
||||
void * opj_aligned_32_realloc(void *ptr, size_t size);
|
||||
|
||||
/**
|
||||
Reallocate memory blocks.
|
||||
@@ -136,23 +96,15 @@ Reallocate memory blocks.
|
||||
@param s New size in bytes
|
||||
@return Returns a void pointer to the reallocated (and possibly moved) memory block
|
||||
*/
|
||||
#ifdef ALLOC_PERF_OPT
|
||||
void * OPJ_CALLCONV opj_realloc(void * m, size_t s);
|
||||
#else
|
||||
#define opj_realloc(m, s) realloc(m, s)
|
||||
#endif
|
||||
void * opj_realloc(void * m, size_t s);
|
||||
|
||||
/**
|
||||
Deallocates or frees a memory block.
|
||||
@param m Previously allocated memory block to be freed
|
||||
*/
|
||||
#ifdef ALLOC_PERF_OPT
|
||||
void OPJ_CALLCONV opj_free(void * m);
|
||||
#else
|
||||
#define opj_free(m) free(m)
|
||||
#endif
|
||||
void opj_free(void * m);
|
||||
|
||||
#ifdef __GNUC__
|
||||
#if defined(__GNUC__) && !defined(OPJ_SKIP_POISON)
|
||||
#pragma GCC poison malloc calloc realloc free
|
||||
#endif
|
||||
|
||||
@@ -161,5 +113,5 @@ void OPJ_CALLCONV opj_free(void * m);
|
||||
|
||||
/*@}*/
|
||||
|
||||
#endif /* __OPJ_MALLOC_H */
|
||||
#endif /* OPJ_MALLOC_H */
|
||||
|
||||
|
||||
51
indra/libopenjpeg/opj_stdint.h
Normal file
51
indra/libopenjpeg/opj_stdint.h
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* The copyright in this software is being made available under the 2-clauses
|
||||
* BSD License, included below. This software may be subject to other third
|
||||
* party and contributor rights, including patent rights, and no such rights
|
||||
* are granted under this license.
|
||||
*
|
||||
* Copyright (c) 2012, Mathieu Malaterre <mathieu.malaterre@gmail.com>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS `AS IS'
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
#ifndef OPJ_STDINT_H
|
||||
#define OPJ_STDINT_H
|
||||
|
||||
#if defined(__linux__) || defined(__APPLE__) || defined(__FreeBSD__) || _MSC_VER >= 1900
|
||||
#include <stdint.h>
|
||||
#else
|
||||
#if defined(_WIN32)
|
||||
typedef signed __int8 int8_t;
|
||||
typedef unsigned __int8 uint8_t;
|
||||
typedef signed __int16 int16_t;
|
||||
typedef unsigned __int16 uint16_t;
|
||||
typedef signed __int32 int32_t;
|
||||
typedef unsigned __int32 uint32_t;
|
||||
typedef signed __int64 int64_t;
|
||||
typedef unsigned __int64 uint64_t;
|
||||
#else
|
||||
#error unsupported platform
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#endif /* OPJ_STDINT_H */
|
||||
@@ -1427,7 +1427,7 @@ void t1_encode_cblks(
|
||||
opj_tcd_resolution_t *res = &tilec->resolutions[resno];
|
||||
|
||||
for (bandno = 0; bandno < res->numbands; ++bandno) {
|
||||
opj_tcd_band_t* restrict band = &res->bands[bandno];
|
||||
opj_tcd_band_t* OPJ_RESTRICT band = &res->bands[bandno];
|
||||
int bandconst = 8192 * 8192 / ((int) floor(band->stepsize * 8192));
|
||||
|
||||
for (precno = 0; precno < res->pw * res->ph; ++precno) {
|
||||
@@ -1435,8 +1435,8 @@ void t1_encode_cblks(
|
||||
|
||||
for (cblkno = 0; cblkno < prc->cw * prc->ch; ++cblkno) {
|
||||
opj_tcd_cblk_enc_t* cblk = &prc->cblks.enc[cblkno];
|
||||
int* restrict datap;
|
||||
int* restrict tiledp;
|
||||
int* OPJ_RESTRICT datap;
|
||||
int* OPJ_RESTRICT tiledp;
|
||||
int cblk_w;
|
||||
int cblk_h;
|
||||
int i, j;
|
||||
@@ -1517,14 +1517,14 @@ void t1_decode_cblks(
|
||||
opj_tcd_resolution_t* res = &tilec->resolutions[resno];
|
||||
|
||||
for (bandno = 0; bandno < res->numbands; ++bandno) {
|
||||
opj_tcd_band_t* restrict band = &res->bands[bandno];
|
||||
opj_tcd_band_t* OPJ_RESTRICT band = &res->bands[bandno];
|
||||
|
||||
for (precno = 0; precno < res->pw * res->ph; ++precno) {
|
||||
opj_tcd_precinct_t* precinct = &band->precincts[precno];
|
||||
|
||||
for (cblkno = 0; cblkno < precinct->cw * precinct->ch; ++cblkno) {
|
||||
opj_tcd_cblk_dec_t* cblk = &precinct->cblks.dec[cblkno];
|
||||
int* restrict datap;
|
||||
int* OPJ_RESTRICT datap;
|
||||
int cblk_w, cblk_h;
|
||||
int x, y;
|
||||
int i, j;
|
||||
@@ -1566,7 +1566,7 @@ void t1_decode_cblks(
|
||||
}
|
||||
|
||||
if (tccp->qmfbid == 1) {
|
||||
int* restrict tiledp = &tilec->data[(y * tile_w) + x];
|
||||
int* OPJ_RESTRICT tiledp = &tilec->data[(y * tile_w) + x];
|
||||
for (j = 0; j < cblk_h; ++j) {
|
||||
for (i = 0; i < cblk_w; ++i) {
|
||||
int tmp = datap[(j * cblk_w) + i];
|
||||
@@ -1574,9 +1574,9 @@ void t1_decode_cblks(
|
||||
}
|
||||
}
|
||||
} else { /* if (tccp->qmfbid == 0) */
|
||||
float* restrict tiledp = (float*) &tilec->data[(y * tile_w) + x];
|
||||
float* OPJ_RESTRICT tiledp = (float*) &tilec->data[(y * tile_w) + x];
|
||||
for (j = 0; j < cblk_h; ++j) {
|
||||
float* restrict tiledp2 = tiledp;
|
||||
float* OPJ_RESTRICT tiledp2 = tiledp;
|
||||
for (i = 0; i < cblk_w; ++i) {
|
||||
float tmp = *datap * band->stepsize;
|
||||
*tiledp2 = tmp;
|
||||
|
||||
@@ -194,7 +194,7 @@ int main(){
|
||||
|
||||
printf("/* This file was automatically generated by t1_generate_luts.c */\n\n");
|
||||
|
||||
// lut_ctxno_zc
|
||||
/* lut_ctxno_zc */
|
||||
for (j = 0; j < 4; ++j) {
|
||||
for (i = 0; i < 256; ++i) {
|
||||
int orient = j;
|
||||
@@ -215,7 +215,7 @@ int main(){
|
||||
}
|
||||
printf("%i\n};\n\n", lut_ctxno_zc[1023]);
|
||||
|
||||
// lut_ctxno_sc
|
||||
/* lut_ctxno_sc */
|
||||
printf("static char lut_ctxno_sc[256] = {\n ");
|
||||
for (i = 0; i < 255; ++i) {
|
||||
printf("0x%x, ", t1_init_ctxno_sc(i << 4));
|
||||
@@ -224,7 +224,7 @@ int main(){
|
||||
}
|
||||
printf("0x%x\n};\n\n", t1_init_ctxno_sc(255 << 4));
|
||||
|
||||
// lut_spb
|
||||
/* lut_spb */
|
||||
printf("static char lut_spb[256] = {\n ");
|
||||
for (i = 0; i < 255; ++i) {
|
||||
printf("%i, ", t1_init_spb(i << 4));
|
||||
|
||||
@@ -30,6 +30,7 @@
|
||||
*/
|
||||
|
||||
#include "opj_includes.h"
|
||||
#include <assert.h>
|
||||
|
||||
/** @defgroup T2 T2 - Implementation of a tier-2 coding */
|
||||
/*@{*/
|
||||
@@ -340,13 +341,15 @@ static int t2_decode_packet(opj_t2_t* t2, unsigned char *src, int len, opj_tcd_t
|
||||
int precno = pi->precno; /* precinct value */
|
||||
int layno = pi->layno; /* quality layer value */
|
||||
|
||||
opj_tcd_resolution_t* res = &tile->comps[compno].resolutions[resno];
|
||||
|
||||
unsigned char *hd = NULL;
|
||||
int present;
|
||||
|
||||
opj_bio_t *bio = NULL; /* BIO component */
|
||||
|
||||
|
||||
opj_tcd_resolution_t* res;
|
||||
assert(&tile->comps[compno] != NULL);
|
||||
res = &tile->comps[compno].resolutions[resno];
|
||||
|
||||
if (layno == 0) {
|
||||
for (bandno = 0; bandno < res->numbands; bandno++) {
|
||||
opj_tcd_band_t *band = &res->bands[bandno];
|
||||
|
||||
@@ -1507,7 +1507,7 @@ opj_bool tcd_decode_tile(opj_tcd_t *tcd, unsigned char *src, int len, int tileno
|
||||
for(j = res->y0; j < res->y1; ++j) {
|
||||
for(i = res->x0; i < res->x1; ++i) {
|
||||
float tmp = ((float*)tilec->data)[i - res->x0 + (j - res->y0) * tw];
|
||||
int v = lrintf(tmp);
|
||||
int v = opj_lrintf(tmp);
|
||||
v += adjust;
|
||||
imagec->data[(i - offset_x) + (j - offset_y) * w] = int_clamp(v, min, max);
|
||||
}
|
||||
|
||||
@@ -24,11 +24,6 @@
|
||||
* $/LicenseInfo$
|
||||
*/
|
||||
|
||||
#if LL_MSVC
|
||||
// disable warning about boost::lexical_cast returning uninitialized data
|
||||
// when it fails to parse the string
|
||||
#pragma warning (disable:4701)
|
||||
#endif
|
||||
|
||||
#include "linden_common.h"
|
||||
|
||||
@@ -230,7 +225,7 @@ void LLAvatarAppearance::initInstance()
|
||||
for (U32 lod = 0; lod < mesh_dict->mLOD; lod++)
|
||||
{
|
||||
LLAvatarJointMesh* mesh = createAvatarJointMesh();
|
||||
std::string mesh_name = "m" + mesh_dict->mName + std::to_string(lod);
|
||||
std::string mesh_name = fmt::format(FMT_STRING("m{:s}{:d}"), mesh_dict->mName, lod);
|
||||
// We pre-pended an m - need to capitalize first character for camelCase
|
||||
mesh_name[1] = toupper(mesh_name[1]);
|
||||
mesh->setName(mesh_name);
|
||||
|
||||
@@ -299,7 +299,9 @@ target_link_libraries(
|
||||
${Boost_SYSTEM_LIBRARY}
|
||||
${CORESERVICES_LIBRARY}
|
||||
${URIPARSER_LIBRARY}
|
||||
fmt::fmt
|
||||
nlohmann_json::nlohmann_json
|
||||
absl::strings
|
||||
${RT_LIBRARY}
|
||||
)
|
||||
|
||||
|
||||
@@ -353,8 +353,14 @@ typedef LLError::NoClassInfo _LL_CLASS_TO_LOG;
|
||||
|
||||
// NEW Macros for debugging, allow the passing of a string tag
|
||||
|
||||
#ifdef SHOW_DEBUG
|
||||
#define DO_DEBUG_LOG
|
||||
#else
|
||||
#define DO_DEBUG_LOG if (false)
|
||||
#endif
|
||||
|
||||
// Pass comma separated list of tags (currently only supports up to 0, 1, or 2)
|
||||
#define LL_DEBUGS(...) lllog(LLError::LEVEL_DEBUG, false, false, ##__VA_ARGS__)
|
||||
#define LL_DEBUGS(...) DO_DEBUG_LOG lllog(LLError::LEVEL_DEBUG, false, false, ##__VA_ARGS__)
|
||||
#define LL_INFOS(...) lllog(LLError::LEVEL_INFO, false, false, ##__VA_ARGS__)
|
||||
#define LL_WARNS(...) lllog(LLError::LEVEL_WARN, false, false, ##__VA_ARGS__)
|
||||
#define LL_ERRS(...) lllog(LLError::LEVEL_ERROR, false, false, ##__VA_ARGS__)
|
||||
@@ -363,12 +369,12 @@ typedef LLError::NoClassInfo _LL_CLASS_TO_LOG;
|
||||
|
||||
// Only print the log message once (good for warnings or infos that would otherwise
|
||||
// spam the log file over and over, such as tighter loops).
|
||||
#define LL_DEBUGS_ONCE(...) lllog(LLError::LEVEL_DEBUG, true, false, ##__VA_ARGS__)
|
||||
#define LL_DEBUGS_ONCE(...) DO_DEBUG_LOG lllog(LLError::LEVEL_DEBUG, true, false, ##__VA_ARGS__)
|
||||
#define LL_INFOS_ONCE(...) lllog(LLError::LEVEL_INFO, true, false, ##__VA_ARGS__)
|
||||
#define LL_WARNS_ONCE(...) lllog(LLError::LEVEL_WARN, true, false, ##__VA_ARGS__)
|
||||
|
||||
// No function name
|
||||
#define LL_DEBUGS_NF(...) lllog(LLError::LEVEL_DEBUG, false, true, ##__VA_ARGS__)
|
||||
#define LL_DEBUGS_NF(...) DO_DEBUG_LOG {lllog(LLError::LEVEL_DEBUG, false, true, ##__VA_ARGS__)
|
||||
#define LL_INFOS_NF(...) lllog(LLError::LEVEL_INFO, false, true, ##__VA_ARGS__)
|
||||
#define LL_WARNS_NF(...) lllog(LLError::LEVEL_WARN, false, true, ##__VA_ARGS__)
|
||||
#define LL_ERRS_NF(...) lllog(LLError::LEVEL_ERROR, false, true, ##__VA_ARGS__)
|
||||
|
||||
@@ -34,6 +34,16 @@
|
||||
#ifndef LL_LLFORMAT_H
|
||||
#define LL_LLFORMAT_H
|
||||
|
||||
#if defined(LL_CLANG)
|
||||
#pragma clang diagnostic push
|
||||
#pragma clang diagnostic ignored "-Wdeprecated"
|
||||
#endif
|
||||
#include <fmt/format.h>
|
||||
#include <fmt/printf.h>
|
||||
#if defined(LL_CLANG)
|
||||
#pragma clang diagnostic pop
|
||||
#endif
|
||||
|
||||
// Use as follows:
|
||||
// LL_INFOS() << llformat("Test:%d (%.2f %.2f)", idx, x, y) << LL_ENDL;
|
||||
//
|
||||
|
||||
@@ -1072,8 +1072,8 @@ S32 LLSDBinaryParser::doParse(std::istream& istr, LLSD& data) const
|
||||
// the size, and read it.
|
||||
U32 size_nbo = 0;
|
||||
read(istr, (char*)&size_nbo, sizeof(U32)); /*Flawfinder: ignore*/
|
||||
S32 size = (S32)ntohl(size_nbo);
|
||||
if(mCheckLimits && (size > mMaxBytesLeft))
|
||||
S32 size = (S32)ntohl(size_nbo); // Can return negative size if > 2^31.
|
||||
if(size < 0 || mCheckLimits && (size > mMaxBytesLeft))
|
||||
{
|
||||
parse_count = PARSE_FAILURE;
|
||||
}
|
||||
@@ -1113,7 +1113,11 @@ S32 LLSDBinaryParser::parseMap(std::istream& istr, LLSD& map) const
|
||||
map = LLSD::emptyMap();
|
||||
U32 value_nbo = 0;
|
||||
read(istr, (char*)&value_nbo, sizeof(U32)); /*Flawfinder: ignore*/
|
||||
S32 size = (S32)ntohl(value_nbo);
|
||||
S32 size = (S32)ntohl(value_nbo); // Can return negative size if > 2^31.
|
||||
if (size < 0)
|
||||
{
|
||||
return PARSE_FAILURE;
|
||||
}
|
||||
S32 parse_count = 0;
|
||||
S32 count = 0;
|
||||
char c = get(istr);
|
||||
@@ -1167,7 +1171,11 @@ S32 LLSDBinaryParser::parseArray(std::istream& istr, LLSD& array) const
|
||||
array = LLSD::emptyArray();
|
||||
U32 value_nbo = 0;
|
||||
read(istr, (char*)&value_nbo, sizeof(U32)); /*Flawfinder: ignore*/
|
||||
S32 size = (S32)ntohl(value_nbo);
|
||||
S32 size = (S32)ntohl(value_nbo); // Can return negative size if > 2^31.
|
||||
if (size < 0)
|
||||
{
|
||||
return PARSE_FAILURE;
|
||||
}
|
||||
|
||||
// *FIX: This would be a good place to reserve some space in the
|
||||
// array...
|
||||
@@ -1208,8 +1216,8 @@ bool LLSDBinaryParser::parseString(
|
||||
// *FIX: This is memory inefficient.
|
||||
U32 value_nbo = 0;
|
||||
read(istr, (char*)&value_nbo, sizeof(U32)); /*Flawfinder: ignore*/
|
||||
S32 size = (S32)ntohl(value_nbo);
|
||||
if(mCheckLimits && (size > mMaxBytesLeft)) return false;
|
||||
S32 size = (S32)ntohl(value_nbo); // Can return negative size if > 2^31.
|
||||
if(size < 0 || mCheckLimits && (size > mMaxBytesLeft)) return false;
|
||||
std::vector<char> buf;
|
||||
if(size)
|
||||
{
|
||||
|
||||
@@ -1354,8 +1354,7 @@ void LLStringUtil::formatNumber(std::string& numStr, std::string decimals)
|
||||
|
||||
if (convertToS32(numStr, intStr))
|
||||
{
|
||||
strStream << intStr;
|
||||
numStr = strStream.str();
|
||||
numStr = fmt::to_string(intStr);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -1435,14 +1434,14 @@ bool LLStringUtil::formatDatetime(std::string& replacement, std::string token,
|
||||
{
|
||||
struct tm * gmt = gmtime (&loc_seconds);
|
||||
LLStringUtil::format_map_t args;
|
||||
args["[MDAY]"] = llformat ("%d", gmt->tm_mday);
|
||||
args["[MDAY]"] = fmt::to_string(gmt->tm_mday);
|
||||
replacement = LLStringOps::sDayFormat;
|
||||
LLStringUtil::format(replacement, args);
|
||||
}
|
||||
else if (code == "%-d")
|
||||
{
|
||||
struct tm * gmt = gmtime (&loc_seconds);
|
||||
replacement = llformat ("%d", gmt->tm_mday); // day of the month without leading zero
|
||||
replacement = fmt::to_string(gmt->tm_mday); // day of the month without leading zero
|
||||
}
|
||||
else if( !LLStringOps::sAM.empty() && !LLStringOps::sPM.empty() && code == "%p" )
|
||||
{
|
||||
|
||||
@@ -29,6 +29,16 @@
|
||||
|
||||
#include <boost/optional/optional.hpp>
|
||||
#include <string>
|
||||
|
||||
#if __cplusplus < 201606
|
||||
#include <absl/strings/string_view.h>
|
||||
namespace std {
|
||||
typedef absl::string_view string_view;
|
||||
}
|
||||
#else
|
||||
#include <string_view>
|
||||
#endif
|
||||
|
||||
#include <cstdio>
|
||||
//#include <locale>
|
||||
#include <iomanip>
|
||||
|
||||
@@ -126,9 +126,12 @@ public:
|
||||
// Returns true if this rotation is orthonormal with det ~= 1
|
||||
inline bool isOkRotation() const;
|
||||
} LL_ALIGN_POSTFIX(16);
|
||||
|
||||
#if !defined(LL_DEBUG)
|
||||
static_assert(std::is_trivial<LLMatrix3a>::value, "LLMatrix3a must be a trivial type");
|
||||
static_assert(std::is_standard_layout<LLMatrix3a>::value, "LLMatrix3a must be a standard layout type");
|
||||
|
||||
static_assert(std::is_trivial<LLRotation>::value, "LLRotation must be a trivial type");
|
||||
static_assert(std::is_standard_layout<LLRotation>::value, "LLRotation must be a standard layout type");
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -718,6 +718,8 @@ inline std::ostream& operator<<(std::ostream& s, const LLMatrix4a& m)
|
||||
|
||||
void matMulBoundBox(const LLMatrix4a &a, const LLVector4a *in_extents, LLVector4a *out_extents);
|
||||
|
||||
#if !defined(LL_DEBUG)
|
||||
static_assert(std::is_trivial<LLMatrix4a>::value, "LLMatrix4a must be a trivial type");
|
||||
static_assert(std::is_standard_layout<LLMatrix4a>::value, "LLMatrix4a must be a standard layout type");
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -104,7 +104,8 @@ private:
|
||||
LL_ALIGN_16(LLVector4a mV);
|
||||
} LL_ALIGN_POSTFIX(16);
|
||||
|
||||
#if !defined(LL_DEBUG)
|
||||
static_assert(std::is_trivial<LLPlane>::value, "LLPlane must be a trivial type");
|
||||
static_assert(std::is_standard_layout<LLPlane>::value, "LLPlane must be a standard layout type");
|
||||
|
||||
#endif
|
||||
#endif // LL_LLPLANE_H
|
||||
|
||||
@@ -105,7 +105,9 @@ protected:
|
||||
|
||||
} LL_ALIGN_POSTFIX(16);
|
||||
|
||||
#if !defined(LL_DEBUG)
|
||||
static_assert(std::is_trivial<LLQuaternion2>::value, "LLQuaternion2 must be a trivial type");
|
||||
static_assert(std::is_standard_layout<LLQuaternion2>::value, "LLQuaternion2 must be a standard layout type");
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
@@ -350,6 +350,8 @@ inline std::ostream& operator<<(std::ostream& s, const LLVector4a& v)
|
||||
return s;
|
||||
}
|
||||
|
||||
#if !defined(LL_DEBUG)
|
||||
static_assert(std::is_trivial<LLVector4a>::value, "LLVector4a must be a be a trivial type");
|
||||
static_assert(std::is_standard_layout<LLVector4a>::value, "LLVector4a must be a standard layout type");
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -64,7 +64,6 @@ set(llmessage_SOURCE_FILES
|
||||
llmessagetemplate.cpp
|
||||
llmessagetemplateparser.cpp
|
||||
llmessagethrottle.cpp
|
||||
llmime.cpp
|
||||
llnamevalue.cpp
|
||||
llnullcipher.cpp
|
||||
llpacketack.cpp
|
||||
@@ -163,7 +162,6 @@ set(llmessage_HEADER_FILES
|
||||
llmessagetemplate.h
|
||||
llmessagetemplateparser.h
|
||||
llmessagethrottle.h
|
||||
llmime.h
|
||||
llmsgvariabletype.h
|
||||
llnamevalue.h
|
||||
llnullcipher.h
|
||||
@@ -241,7 +239,6 @@ if (LL_TESTS)
|
||||
include(Tut)
|
||||
|
||||
SET(llmessage_TEST_SOURCE_FILES
|
||||
llmime.cpp
|
||||
llnamevalue.cpp
|
||||
lltrustedmessageservice.cpp
|
||||
lltemplatemessagedispatcher.cpp
|
||||
|
||||
@@ -960,4 +960,5 @@ P(webProfileResponders);
|
||||
P(wholeModelFeeResponder);
|
||||
P(wholeModelUploadResponder);
|
||||
P2(XMLRPCResponder, connect_40s);
|
||||
P(getUpdateInfoResponder);
|
||||
P(getUpdateInfoResponder);
|
||||
P2(AISAPIResponder, connect_60s);
|
||||
@@ -262,6 +262,8 @@ LLCacheName::~LLCacheName()
|
||||
delete &impl;
|
||||
}
|
||||
|
||||
const ReverseCache& LLCacheName::getReverseMap() const { return impl.mReverseCache; }
|
||||
|
||||
LLCacheName::Impl::Impl(LLMessageSystem* msg)
|
||||
: mMsg(msg), mUpstreamHost(LLHost::invalid)
|
||||
{
|
||||
|
||||
@@ -57,6 +57,8 @@ public:
|
||||
LLCacheName(LLMessageSystem* msg, const LLHost& upstream_host);
|
||||
~LLCacheName();
|
||||
|
||||
const std::map<std::string, LLUUID>& getReverseMap() const;
|
||||
|
||||
// registers the upstream host
|
||||
// for viewers, this is the currently connected simulator
|
||||
// for simulators, this is the data server
|
||||
|
||||
@@ -58,103 +58,6 @@ const std::string SYSTEM_FROM("Second Life");
|
||||
const std::string INTERACTIVE_SYSTEM_FROM("F387446C-37C4-45f2-A438-D99CBDBB563B");
|
||||
const S32 IM_TTL = 1;
|
||||
|
||||
|
||||
/**
|
||||
* LLIMInfo
|
||||
*/
|
||||
LLIMInfo::LLIMInfo() :
|
||||
mFromGroup(FALSE),
|
||||
mParentEstateID(0),
|
||||
mOffline(0),
|
||||
mViewerThinksToIsOnline(false),
|
||||
mIMType(IM_NOTHING_SPECIAL),
|
||||
mTimeStamp(0),
|
||||
mSource(IM_FROM_SIM),
|
||||
mTTL(IM_TTL)
|
||||
{
|
||||
}
|
||||
|
||||
LLIMInfo::LLIMInfo(
|
||||
const LLUUID& from_id,
|
||||
BOOL from_group,
|
||||
const LLUUID& to_id,
|
||||
EInstantMessage im_type,
|
||||
const std::string& name,
|
||||
const std::string& message,
|
||||
const LLUUID& id,
|
||||
U32 parent_estate_id,
|
||||
const LLUUID& region_id,
|
||||
const LLVector3& position,
|
||||
LLSD data,
|
||||
U8 offline,
|
||||
U32 timestamp,
|
||||
EIMSource source,
|
||||
S32 ttl) :
|
||||
mFromID(from_id),
|
||||
mFromGroup(from_group),
|
||||
mToID(to_id),
|
||||
mParentEstateID(0),
|
||||
mRegionID(region_id),
|
||||
mPosition(position),
|
||||
mOffline(offline),
|
||||
mViewerThinksToIsOnline(false),
|
||||
mIMType(im_type),
|
||||
mID(id),
|
||||
mTimeStamp(timestamp),
|
||||
mName(name),
|
||||
mMessage(message),
|
||||
mData(data),
|
||||
mSource(source),
|
||||
mTTL(ttl)
|
||||
{
|
||||
}
|
||||
|
||||
LLIMInfo::LLIMInfo(LLMessageSystem* msg, EIMSource source, S32 ttl) :
|
||||
mViewerThinksToIsOnline(false),
|
||||
mSource(source),
|
||||
mTTL(ttl)
|
||||
{
|
||||
unpackMessageBlock(msg);
|
||||
}
|
||||
|
||||
LLIMInfo::~LLIMInfo()
|
||||
{
|
||||
}
|
||||
|
||||
void LLIMInfo::packInstantMessage(LLMessageSystem* msg) const
|
||||
{
|
||||
LL_DEBUGS() << "LLIMInfo::packInstantMessage()" << LL_ENDL;
|
||||
msg->newMessageFast(_PREHASH_ImprovedInstantMessage);
|
||||
packMessageBlock(msg);
|
||||
}
|
||||
|
||||
void LLIMInfo::packMessageBlock(LLMessageSystem* msg) const
|
||||
{
|
||||
// Construct binary bucket
|
||||
std::vector<U8> bucket;
|
||||
if (mData.has("binary_bucket"))
|
||||
{
|
||||
bucket = mData["binary_bucket"].asBinary();
|
||||
}
|
||||
pack_instant_message_block(
|
||||
msg,
|
||||
mFromID,
|
||||
mFromGroup,
|
||||
LLUUID::null,
|
||||
mToID,
|
||||
mName,
|
||||
mMessage,
|
||||
mOffline,
|
||||
mIMType,
|
||||
mID,
|
||||
mParentEstateID,
|
||||
mRegionID,
|
||||
mPosition,
|
||||
mTimeStamp,
|
||||
&bucket[0],
|
||||
bucket.size());
|
||||
}
|
||||
|
||||
void pack_instant_message(
|
||||
LLMessageSystem* msg,
|
||||
const LLUUID& from_id,
|
||||
@@ -264,124 +167,3 @@ void pack_instant_message_block(
|
||||
}
|
||||
msg->addBinaryDataFast(_PREHASH_BinaryBucket, bb, binary_bucket_size);
|
||||
}
|
||||
|
||||
void LLIMInfo::unpackMessageBlock(LLMessageSystem* msg)
|
||||
{
|
||||
msg->getUUIDFast(_PREHASH_AgentData, _PREHASH_AgentID, mFromID);
|
||||
msg->getBOOLFast(_PREHASH_MessageBlock, _PREHASH_FromGroup, mFromGroup);
|
||||
msg->getUUIDFast(_PREHASH_MessageBlock, _PREHASH_ToAgentID, mToID);
|
||||
msg->getU32Fast(_PREHASH_MessageBlock, _PREHASH_ParentEstateID, mParentEstateID);
|
||||
msg->getUUIDFast(_PREHASH_MessageBlock, _PREHASH_RegionID, mRegionID);
|
||||
msg->getVector3Fast(_PREHASH_MessageBlock, _PREHASH_Position, mPosition);
|
||||
msg->getU8Fast(_PREHASH_MessageBlock, _PREHASH_Offline, mOffline);
|
||||
U8 dialog;
|
||||
msg->getU8Fast(_PREHASH_MessageBlock, _PREHASH_Dialog, dialog);
|
||||
mIMType = (EInstantMessage) dialog;
|
||||
msg->getUUIDFast(_PREHASH_MessageBlock, _PREHASH_ID, mID);
|
||||
msg->getU32Fast(_PREHASH_MessageBlock, _PREHASH_Timestamp, mTimeStamp);
|
||||
msg->getStringFast(_PREHASH_MessageBlock, _PREHASH_FromAgentName, mName);
|
||||
|
||||
msg->getStringFast(_PREHASH_MessageBlock, _PREHASH_Message, mMessage);
|
||||
|
||||
S32 binary_bucket_size = llmin(
|
||||
MTUBYTES,
|
||||
msg->getSizeFast(
|
||||
_PREHASH_MessageBlock,
|
||||
_PREHASH_BinaryBucket));
|
||||
if(binary_bucket_size > 0)
|
||||
{
|
||||
std::vector<U8> bucket;
|
||||
bucket.resize(binary_bucket_size);
|
||||
|
||||
msg->getBinaryDataFast(
|
||||
_PREHASH_MessageBlock,
|
||||
_PREHASH_BinaryBucket,
|
||||
&bucket[0],
|
||||
0,
|
||||
0,
|
||||
binary_bucket_size);
|
||||
mData["binary_bucket"] = bucket;
|
||||
}
|
||||
else
|
||||
{
|
||||
mData.clear();
|
||||
}
|
||||
}
|
||||
|
||||
LLSD im_info_to_llsd(LLPointer<LLIMInfo> im_info)
|
||||
{
|
||||
LLSD param_version;
|
||||
param_version["version"] = 1;
|
||||
LLSD param_message;
|
||||
param_message["from_id"] = im_info->mFromID;
|
||||
param_message["from_group"] = im_info->mFromGroup;
|
||||
param_message["to_id"] = im_info->mToID;
|
||||
param_message["from_name"] = im_info->mName;
|
||||
param_message["message"] = im_info->mMessage;
|
||||
param_message["type"] = (S32)im_info->mIMType;
|
||||
param_message["id"] = im_info->mID;
|
||||
param_message["timestamp"] = (S32)im_info->mTimeStamp;
|
||||
param_message["offline"] = (S32)im_info->mOffline;
|
||||
param_message["parent_estate_id"] = (S32)im_info->mParentEstateID;
|
||||
param_message["region_id"] = im_info->mRegionID;
|
||||
param_message["position"] = ll_sd_from_vector3(im_info->mPosition);
|
||||
param_message["data"] = im_info->mData;
|
||||
param_message["source"]= im_info->mSource;
|
||||
param_message["ttl"] = im_info->mTTL;
|
||||
|
||||
LLSD param_agent;
|
||||
param_agent["agent_id"] = im_info->mFromID;
|
||||
|
||||
LLSD params;
|
||||
params["version_params"] = param_version;
|
||||
params["message_params"] = param_message;
|
||||
params["agent_params"] = param_agent;
|
||||
|
||||
return params;
|
||||
}
|
||||
|
||||
LLPointer<LLIMInfo> llsd_to_im_info(const LLSD& im_info_sd)
|
||||
{
|
||||
LLSD param_message = im_info_sd["message_params"];
|
||||
LLSD param_agent = im_info_sd["agent_params"];
|
||||
|
||||
LLPointer<LLIMInfo> im_info = new LLIMInfo(
|
||||
param_message["from_id"].asUUID(),
|
||||
param_message["from_group"].asBoolean(),
|
||||
param_message["to_id"].asUUID(),
|
||||
(EInstantMessage) param_message["type"].asInteger(),
|
||||
param_message["from_name"].asString(),
|
||||
param_message["message"].asString(),
|
||||
param_message["id"].asUUID(),
|
||||
(U32) param_message["parent_estate_id"].asInteger(),
|
||||
param_message["region_id"].asUUID(),
|
||||
ll_vector3_from_sd(param_message["position"]),
|
||||
param_message["data"],
|
||||
(U8) param_message["offline"].asInteger(),
|
||||
(U32) param_message["timestamp"].asInteger(),
|
||||
(EIMSource)param_message["source"].asInteger(),
|
||||
param_message["ttl"].asInteger());
|
||||
|
||||
return im_info;
|
||||
}
|
||||
|
||||
LLPointer<LLIMInfo> LLIMInfo::clone()
|
||||
{
|
||||
return new LLIMInfo(
|
||||
mFromID,
|
||||
mFromGroup,
|
||||
mToID,
|
||||
mIMType,
|
||||
mName,
|
||||
mMessage,
|
||||
mID,
|
||||
mParentEstateID,
|
||||
mRegionID,
|
||||
mPosition,
|
||||
mData,
|
||||
mOffline,
|
||||
mTimeStamp,
|
||||
mSource,
|
||||
mTTL);
|
||||
}
|
||||
|
||||
|
||||
@@ -225,62 +225,6 @@ extern const std::string INTERACTIVE_SYSTEM_FROM;
|
||||
// Number of retry attempts on sending the im.
|
||||
extern const S32 IM_TTL;
|
||||
|
||||
|
||||
class LLIMInfo : public LLRefCount
|
||||
{
|
||||
protected:
|
||||
LLIMInfo();
|
||||
~LLIMInfo();
|
||||
|
||||
public:
|
||||
LLIMInfo(LLMessageSystem* msg,
|
||||
EIMSource source = IM_FROM_SIM,
|
||||
S32 ttl = IM_TTL);
|
||||
|
||||
LLIMInfo(
|
||||
const LLUUID& from_id,
|
||||
BOOL from_group,
|
||||
const LLUUID& to_id,
|
||||
EInstantMessage im_type,
|
||||
const std::string& name,
|
||||
const std::string& message,
|
||||
const LLUUID& id,
|
||||
U32 parent_estate_id,
|
||||
const LLUUID& region_id,
|
||||
const LLVector3& position,
|
||||
LLSD data,
|
||||
U8 offline,
|
||||
U32 timestamp,
|
||||
EIMSource source,
|
||||
S32 ttl = IM_TTL);
|
||||
|
||||
void packInstantMessage(LLMessageSystem* msg) const;
|
||||
void packMessageBlock(LLMessageSystem* msg) const;
|
||||
void unpackMessageBlock(LLMessageSystem* msg);
|
||||
LLPointer<LLIMInfo> clone();
|
||||
public:
|
||||
LLUUID mFromID;
|
||||
BOOL mFromGroup;
|
||||
LLUUID mToID;
|
||||
U32 mParentEstateID;
|
||||
LLUUID mRegionID;
|
||||
LLVector3 mPosition;
|
||||
U8 mOffline;
|
||||
bool mViewerThinksToIsOnline;
|
||||
EInstantMessage mIMType;
|
||||
LLUUID mID;
|
||||
U32 mTimeStamp;
|
||||
std::string mName;
|
||||
std::string mMessage;
|
||||
LLSD mData;
|
||||
|
||||
EIMSource mSource;
|
||||
S32 mTTL;
|
||||
};
|
||||
|
||||
LLPointer<LLIMInfo> llsd_to_im_info(const LLSD& im_info_sd);
|
||||
LLSD im_info_to_llsd(LLPointer<LLIMInfo> im_info);
|
||||
|
||||
void pack_instant_message(
|
||||
LLMessageSystem* msgsystem,
|
||||
const LLUUID& from_id,
|
||||
|
||||
@@ -1,629 +0,0 @@
|
||||
/**
|
||||
* @file llmime.cpp
|
||||
* @author Phoenix
|
||||
* @date 2006-12-20
|
||||
* @brief Implementation of mime tools.
|
||||
*
|
||||
* $LicenseInfo:firstyear=2006&license=viewerlgpl$
|
||||
* Second Life Viewer Source Code
|
||||
* Copyright (C) 2010, Linden Research, Inc.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation;
|
||||
* version 2.1 of the License only.
|
||||
*
|
||||
* 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 "linden_common.h"
|
||||
#include "llmime.h"
|
||||
|
||||
#include <vector>
|
||||
|
||||
#include "llmemorystream.h"
|
||||
|
||||
/**
|
||||
* Useful constants.
|
||||
*/
|
||||
// Headers specified in rfc-2045 will be canonicalized below.
|
||||
static const std::string CONTENT_LENGTH("Content-Length");
|
||||
static const std::string CONTENT_TYPE("Content-Type");
|
||||
static const S32 KNOWN_HEADER_COUNT = 6;
|
||||
static const std::string KNOWN_HEADER[KNOWN_HEADER_COUNT] =
|
||||
{
|
||||
CONTENT_LENGTH,
|
||||
CONTENT_TYPE,
|
||||
std::string("MIME-Version"),
|
||||
std::string("Content-Transfer-Encoding"),
|
||||
std::string("Content-ID"),
|
||||
std::string("Content-Description"),
|
||||
};
|
||||
|
||||
// parser helpers
|
||||
static const std::string MULTIPART("multipart");
|
||||
static const std::string BOUNDARY("boundary");
|
||||
static const std::string END_OF_CONTENT_PARAMETER("\r\n ;\t");
|
||||
static const std::string SEPARATOR_PREFIX("--");
|
||||
//static const std::string SEPARATOR_SUFFIX("\r\n");
|
||||
|
||||
/*
|
||||
Content-Type: multipart/mixed; boundary="segment"
|
||||
Content-Length: 24832
|
||||
|
||||
--segment
|
||||
Content-Type: image/j2c
|
||||
Content-Length: 23715
|
||||
|
||||
<data>
|
||||
|
||||
--segment
|
||||
Content-Type: text/xml; charset=UTF-8
|
||||
|
||||
<meta data>
|
||||
EOF
|
||||
|
||||
*/
|
||||
|
||||
/**
|
||||
* LLMimeIndex
|
||||
*/
|
||||
|
||||
/**
|
||||
* @class LLMimeIndex::Impl
|
||||
* @brief Implementation details of the mime index class.
|
||||
* @see LLMimeIndex
|
||||
*/
|
||||
class LLMimeIndex::Impl
|
||||
{
|
||||
public:
|
||||
Impl() : mOffset(-1), mUseCount(1)
|
||||
{}
|
||||
Impl(LLSD headers, S32 offset) :
|
||||
mHeaders(headers), mOffset(offset), mUseCount(1)
|
||||
{}
|
||||
public:
|
||||
LLSD mHeaders;
|
||||
S32 mOffset;
|
||||
S32 mUseCount;
|
||||
|
||||
typedef std::vector<LLMimeIndex> sub_part_t;
|
||||
sub_part_t mAttachments;
|
||||
};
|
||||
|
||||
LLSD LLMimeIndex::headers() const
|
||||
{
|
||||
return mImpl->mHeaders;
|
||||
}
|
||||
|
||||
S32 LLMimeIndex::offset() const
|
||||
{
|
||||
return mImpl->mOffset;
|
||||
}
|
||||
|
||||
S32 LLMimeIndex::contentLength() const
|
||||
{
|
||||
// Find the content length in the headers.
|
||||
S32 length = -1;
|
||||
LLSD content_length = mImpl->mHeaders[CONTENT_LENGTH];
|
||||
if(content_length.isDefined())
|
||||
{
|
||||
length = content_length.asInteger();
|
||||
}
|
||||
return length;
|
||||
}
|
||||
|
||||
std::string LLMimeIndex::contentType() const
|
||||
{
|
||||
std::string type;
|
||||
LLSD content_type = mImpl->mHeaders[CONTENT_TYPE];
|
||||
if(content_type.isDefined())
|
||||
{
|
||||
type = content_type.asString();
|
||||
}
|
||||
return type;
|
||||
}
|
||||
|
||||
bool LLMimeIndex::isMultipart() const
|
||||
{
|
||||
bool multipart = false;
|
||||
LLSD content_type = mImpl->mHeaders[CONTENT_TYPE];
|
||||
if(content_type.isDefined())
|
||||
{
|
||||
std::string type = content_type.asString();
|
||||
int comp = type.compare(0, MULTIPART.size(), MULTIPART);
|
||||
if(0 == comp)
|
||||
{
|
||||
multipart = true;
|
||||
}
|
||||
}
|
||||
return multipart;
|
||||
}
|
||||
|
||||
S32 LLMimeIndex::subPartCount() const
|
||||
{
|
||||
return mImpl->mAttachments.size();
|
||||
}
|
||||
|
||||
LLMimeIndex LLMimeIndex::subPart(S32 index) const
|
||||
{
|
||||
LLMimeIndex part;
|
||||
if((index >= 0) && (index < (S32)mImpl->mAttachments.size()))
|
||||
{
|
||||
part = mImpl->mAttachments[index];
|
||||
}
|
||||
return part;
|
||||
}
|
||||
|
||||
LLMimeIndex::LLMimeIndex() : mImpl(new LLMimeIndex::Impl)
|
||||
{
|
||||
}
|
||||
|
||||
LLMimeIndex::LLMimeIndex(LLSD headers, S32 content_offset) :
|
||||
mImpl(new LLMimeIndex::Impl(headers, content_offset))
|
||||
{
|
||||
}
|
||||
|
||||
LLMimeIndex::LLMimeIndex(const LLMimeIndex& mime) :
|
||||
mImpl(mime.mImpl)
|
||||
{
|
||||
++mImpl->mUseCount;
|
||||
}
|
||||
|
||||
LLMimeIndex::~LLMimeIndex()
|
||||
{
|
||||
if(0 == --mImpl->mUseCount)
|
||||
{
|
||||
delete mImpl;
|
||||
}
|
||||
}
|
||||
|
||||
LLMimeIndex& LLMimeIndex::operator=(const LLMimeIndex& mime)
|
||||
{
|
||||
// Increment use count first so that we handle self assignment
|
||||
// automatically.
|
||||
++mime.mImpl->mUseCount;
|
||||
if(0 == --mImpl->mUseCount)
|
||||
{
|
||||
delete mImpl;
|
||||
}
|
||||
mImpl = mime.mImpl;
|
||||
return *this;
|
||||
}
|
||||
|
||||
bool LLMimeIndex::attachSubPart(LLMimeIndex sub_part)
|
||||
{
|
||||
// *FIX: Should we check for multi-part?
|
||||
if(mImpl->mAttachments.size() < S32_MAX)
|
||||
{
|
||||
mImpl->mAttachments.push_back(sub_part);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* LLMimeParser
|
||||
*/
|
||||
/**
|
||||
* @class LLMimeParser::Impl
|
||||
* @brief Implementation details of the mime parser class.
|
||||
* @see LLMimeParser
|
||||
*/
|
||||
class LLMimeParser::Impl
|
||||
{
|
||||
public:
|
||||
// @brief Constructor.
|
||||
Impl();
|
||||
|
||||
// @brief Reset this for a new parse.
|
||||
void reset();
|
||||
|
||||
/**
|
||||
* @brief Parse a mime entity to find the index information.
|
||||
*
|
||||
* This method will scan the istr until a single complete mime
|
||||
* entity is read, an EOF, or limit bytes have been scanned. The
|
||||
* istr will be modified by this parsing, so pass in a temporary
|
||||
* stream or rewind/reset the stream after this call.
|
||||
* @param istr An istream which contains a mime entity.
|
||||
* @param limit The maximum number of bytes to scan.
|
||||
* @param separator The multipart separator if it is known.
|
||||
* @param is_subpart Set true if parsing a multipart sub part.
|
||||
* @param index[out] The parsed output.
|
||||
* @return Returns true if an index was parsed and no errors occurred.
|
||||
*/
|
||||
bool parseIndex(
|
||||
std::istream& istr,
|
||||
S32 limit,
|
||||
const std::string& separator,
|
||||
bool is_subpart,
|
||||
LLMimeIndex& index);
|
||||
|
||||
protected:
|
||||
/**
|
||||
* @brief parse the headers.
|
||||
*
|
||||
* At the end of a successful parse, mScanCount will be at the
|
||||
* start of the content.
|
||||
* @param istr The input stream.
|
||||
* @param limit maximum number of bytes to process
|
||||
* @param headers[out] A map of the headers found.
|
||||
* @return Returns true if the parse was successful.
|
||||
*/
|
||||
bool parseHeaders(std::istream& istr, S32 limit, LLSD& headers);
|
||||
|
||||
/**
|
||||
* @brief Figure out the separator string from a content type header.
|
||||
*
|
||||
* @param multipart_content_type The content type value from the headers.
|
||||
* @return Returns the separator string.
|
||||
*/
|
||||
std::string findSeparator(std::string multipart_content_type);
|
||||
|
||||
/**
|
||||
* @brief Scan through istr past the separator.
|
||||
*
|
||||
* @param istr The input stream.
|
||||
* @param limit Maximum number of bytes to scan.
|
||||
* @param separator The multipart separator.
|
||||
*/
|
||||
void scanPastSeparator(
|
||||
std::istream& istr,
|
||||
S32 limit,
|
||||
const std::string& separator);
|
||||
|
||||
/**
|
||||
* @brief Scan through istr past the content of the current mime part.
|
||||
*
|
||||
* @param istr The input stream.
|
||||
* @param limit Maximum number of bytes to scan.
|
||||
* @param headers The headers for this mime part.
|
||||
* @param separator The multipart separator if known.
|
||||
*/
|
||||
void scanPastContent(
|
||||
std::istream& istr,
|
||||
S32 limit,
|
||||
LLSD headers,
|
||||
const std::string separator);
|
||||
|
||||
/**
|
||||
* @brief Eat CRLF.
|
||||
*
|
||||
* This method has no concept of the limit, so ensure you have at
|
||||
* least 2 characters left to eat before hitting the limit. This
|
||||
* method will increment mScanCount as it goes.
|
||||
* @param istr The input stream.
|
||||
* @return Returns true if CRLF was found and consumed off of istr.
|
||||
*/
|
||||
bool eatCRLF(std::istream& istr);
|
||||
|
||||
// @brief Returns true if parsing should continue.
|
||||
bool continueParse() const { return (!mError && mContinue); }
|
||||
|
||||
// @brief anonymous enumeration for parse buffer size.
|
||||
enum
|
||||
{
|
||||
LINE_BUFFER_LENGTH = 1024
|
||||
};
|
||||
|
||||
protected:
|
||||
S32 mScanCount;
|
||||
bool mContinue;
|
||||
bool mError;
|
||||
char mBuffer[LINE_BUFFER_LENGTH];
|
||||
};
|
||||
|
||||
LLMimeParser::Impl::Impl()
|
||||
{
|
||||
reset();
|
||||
}
|
||||
|
||||
void LLMimeParser::Impl::reset()
|
||||
{
|
||||
mScanCount = 0;
|
||||
mContinue = true;
|
||||
mError = false;
|
||||
mBuffer[0] = '\0';
|
||||
}
|
||||
|
||||
bool LLMimeParser::Impl::parseIndex(
|
||||
std::istream& istr,
|
||||
S32 limit,
|
||||
const std::string& separator,
|
||||
bool is_subpart,
|
||||
LLMimeIndex& index)
|
||||
{
|
||||
LLSD headers;
|
||||
bool parsed_something = false;
|
||||
if(parseHeaders(istr, limit, headers))
|
||||
{
|
||||
parsed_something = true;
|
||||
LLMimeIndex mime(headers, mScanCount);
|
||||
index = mime;
|
||||
if(index.isMultipart())
|
||||
{
|
||||
// Figure out the separator, scan past it, and recurse.
|
||||
std::string ct = headers[CONTENT_TYPE].asString();
|
||||
std::string sep = findSeparator(ct);
|
||||
scanPastSeparator(istr, limit, sep);
|
||||
while(continueParse() && parseIndex(istr, limit, sep, true, mime))
|
||||
{
|
||||
index.attachSubPart(mime);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Scan to the end of content.
|
||||
scanPastContent(istr, limit, headers, separator);
|
||||
if(is_subpart)
|
||||
{
|
||||
scanPastSeparator(istr, limit, separator);
|
||||
}
|
||||
}
|
||||
}
|
||||
if(mError) return false;
|
||||
return parsed_something;
|
||||
}
|
||||
|
||||
bool LLMimeParser::Impl::parseHeaders(
|
||||
std::istream& istr,
|
||||
S32 limit,
|
||||
LLSD& headers)
|
||||
{
|
||||
while(continueParse())
|
||||
{
|
||||
// Get the next line.
|
||||
// We subtract 1 from the limit so that we make sure
|
||||
// not to read past limit when we get() the newline.
|
||||
S32 max_get = llmin((S32)LINE_BUFFER_LENGTH, limit - mScanCount - 1);
|
||||
istr.getline(mBuffer, max_get, '\r');
|
||||
mScanCount += (S32)istr.gcount();
|
||||
int c = istr.get();
|
||||
if(EOF == c)
|
||||
{
|
||||
mContinue = false;
|
||||
return false;
|
||||
}
|
||||
++mScanCount;
|
||||
if(c != '\n')
|
||||
{
|
||||
mError = true;
|
||||
return false;
|
||||
}
|
||||
if(mScanCount >= limit)
|
||||
{
|
||||
mContinue = false;
|
||||
}
|
||||
|
||||
// Check if that's the end of headers.
|
||||
if('\0' == mBuffer[0])
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
// Split out the name and value.
|
||||
// *NOTE: The use of strchr() here is safe since mBuffer is
|
||||
// guaranteed to be NULL terminated from the call to getline()
|
||||
// above.
|
||||
char* colon = strchr(mBuffer, ':');
|
||||
if(!colon)
|
||||
{
|
||||
mError = true;
|
||||
return false;
|
||||
}
|
||||
|
||||
// Cononicalize the name part, and store the name: value in
|
||||
// the headers structure. We do this by iterating through
|
||||
// 'known' headers and replacing the value found with the
|
||||
// correct one.
|
||||
// *NOTE: Not so efficient, but iterating through a small
|
||||
// subset should not be too much of an issue.
|
||||
std::string name(mBuffer, colon++ - mBuffer);
|
||||
while(isspace(*colon)) ++colon;
|
||||
std::string value(colon);
|
||||
for(S32 ii = 0; ii < KNOWN_HEADER_COUNT; ++ii)
|
||||
{
|
||||
if(0 == LLStringUtil::compareInsensitive(name, KNOWN_HEADER[ii]))
|
||||
{
|
||||
name = KNOWN_HEADER[ii];
|
||||
break;
|
||||
}
|
||||
}
|
||||
headers[name] = value;
|
||||
}
|
||||
if(headers.isUndefined()) return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
std::string LLMimeParser::Impl::findSeparator(std::string header)
|
||||
{
|
||||
// 01234567890
|
||||
//Content-Type: multipart/mixed; boundary="segment"
|
||||
std::string separator;
|
||||
std::string::size_type pos = header.find(BOUNDARY);
|
||||
if(std::string::npos == pos) return separator;
|
||||
pos += BOUNDARY.size() + 1;
|
||||
std::string::size_type end;
|
||||
if(header[pos] == '"')
|
||||
{
|
||||
// the boundary is quoted, find the end from pos, and take the
|
||||
// substring.
|
||||
end = header.find('"', ++pos);
|
||||
if(std::string::npos == end)
|
||||
{
|
||||
// poorly formed boundary.
|
||||
mError = true;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// otherwise, it's every character until a whitespace, end of
|
||||
// line, or another parameter begins.
|
||||
end = header.find_first_of(END_OF_CONTENT_PARAMETER, pos);
|
||||
if(std::string::npos == end)
|
||||
{
|
||||
// it goes to the end of the string.
|
||||
end = header.size();
|
||||
}
|
||||
}
|
||||
if(!mError) separator = header.substr(pos, end - pos);
|
||||
return separator;
|
||||
}
|
||||
|
||||
void LLMimeParser::Impl::scanPastSeparator(
|
||||
std::istream& istr,
|
||||
S32 limit,
|
||||
const std::string& sep)
|
||||
{
|
||||
std::ostringstream ostr;
|
||||
ostr << SEPARATOR_PREFIX << sep;
|
||||
std::string separator = ostr.str();
|
||||
bool found_separator = false;
|
||||
while(!found_separator && continueParse())
|
||||
{
|
||||
// Subtract 1 from the limit so that we make sure not to read
|
||||
// past limit when we get() the newline.
|
||||
S32 max_get = llmin((S32)LINE_BUFFER_LENGTH, limit - mScanCount - 1);
|
||||
istr.getline(mBuffer, max_get, '\r');
|
||||
mScanCount += (S32)istr.gcount();
|
||||
if(istr.gcount() >= LINE_BUFFER_LENGTH - 1)
|
||||
{
|
||||
// that's way too long to be a separator, so ignore it.
|
||||
continue;
|
||||
}
|
||||
int c = istr.get();
|
||||
if(EOF == c)
|
||||
{
|
||||
mContinue = false;
|
||||
return;
|
||||
}
|
||||
++mScanCount;
|
||||
if(c != '\n')
|
||||
{
|
||||
mError = true;
|
||||
return;
|
||||
}
|
||||
if(mScanCount >= limit)
|
||||
{
|
||||
mContinue = false;
|
||||
}
|
||||
if(0 == LLStringUtil::compareStrings(std::string(mBuffer), separator))
|
||||
{
|
||||
found_separator = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void LLMimeParser::Impl::scanPastContent(
|
||||
std::istream& istr,
|
||||
S32 limit,
|
||||
LLSD headers,
|
||||
const std::string separator)
|
||||
{
|
||||
if(headers.has(CONTENT_LENGTH))
|
||||
{
|
||||
S32 content_length = headers[CONTENT_LENGTH].asInteger();
|
||||
// Subtract 2 here for the \r\n after the content.
|
||||
S32 max_skip = llmin(content_length, limit - mScanCount - 2);
|
||||
istr.ignore(max_skip);
|
||||
mScanCount += max_skip;
|
||||
|
||||
// *NOTE: Check for hitting the limit and eof here before
|
||||
// checking for the trailing EOF, because our mime parser has
|
||||
// to gracefully handle incomplete mime entites.
|
||||
if((mScanCount >= limit) || istr.eof())
|
||||
{
|
||||
mContinue = false;
|
||||
}
|
||||
else if(!eatCRLF(istr))
|
||||
{
|
||||
mError = true;
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool LLMimeParser::Impl::eatCRLF(std::istream& istr)
|
||||
{
|
||||
int c = istr.get();
|
||||
++mScanCount;
|
||||
if(c != '\r')
|
||||
{
|
||||
return false;
|
||||
}
|
||||
c = istr.get();
|
||||
++mScanCount;
|
||||
if(c != '\n')
|
||||
{
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
LLMimeParser::LLMimeParser() : mImpl(* new LLMimeParser::Impl)
|
||||
{
|
||||
}
|
||||
|
||||
LLMimeParser::~LLMimeParser()
|
||||
{
|
||||
delete & mImpl;
|
||||
}
|
||||
|
||||
void LLMimeParser::reset()
|
||||
{
|
||||
mImpl.reset();
|
||||
}
|
||||
|
||||
bool LLMimeParser::parseIndex(std::istream& istr, LLMimeIndex& index)
|
||||
{
|
||||
std::string separator;
|
||||
return mImpl.parseIndex(istr, S32_MAX, separator, false, index);
|
||||
}
|
||||
|
||||
bool LLMimeParser::parseIndex(
|
||||
const std::vector<U8>& buffer,
|
||||
LLMimeIndex& index)
|
||||
{
|
||||
LLMemoryStream mstr(&buffer[0], buffer.size());
|
||||
return parseIndex(mstr, buffer.size() + 1, index);
|
||||
}
|
||||
|
||||
bool LLMimeParser::parseIndex(
|
||||
std::istream& istr,
|
||||
S32 limit,
|
||||
LLMimeIndex& index)
|
||||
{
|
||||
std::string separator;
|
||||
return mImpl.parseIndex(istr, limit, separator, false, index);
|
||||
}
|
||||
|
||||
bool LLMimeParser::parseIndex(const U8* buffer, S32 length, LLMimeIndex& index)
|
||||
{
|
||||
LLMemoryStream mstr(buffer, length);
|
||||
return parseIndex(mstr, length + 1, index);
|
||||
}
|
||||
|
||||
/*
|
||||
bool LLMimeParser::verify(std::istream& isr, LLMimeIndex& index) const
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
bool LLMimeParser::verify(U8* buffer, S32 length, LLMimeIndex& index) const
|
||||
{
|
||||
LLMemoryStream mstr(buffer, length);
|
||||
return verify(mstr, index);
|
||||
}
|
||||
*/
|
||||
@@ -1,292 +0,0 @@
|
||||
/**
|
||||
* @file llmime.h
|
||||
* @author Phoenix
|
||||
* @date 2006-12-20
|
||||
* @brief Declaration of mime tools.
|
||||
*
|
||||
* $LicenseInfo:firstyear=2006&license=viewerlgpl$
|
||||
* Second Life Viewer Source Code
|
||||
* Copyright (C) 2010, Linden Research, Inc.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation;
|
||||
* version 2.1 of the License only.
|
||||
*
|
||||
* 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_LLMIME_H
|
||||
#define LL_LLMIME_H
|
||||
|
||||
#include <string>
|
||||
#include "llsd.h"
|
||||
|
||||
/**
|
||||
* This file declares various tools for parsing and creating MIME
|
||||
* objects as described in RFCs 2045, 2046, 2047, 2048, and 2049.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @class LLMimeIndex
|
||||
* @brief Skeletal information useful for handling mime packages.
|
||||
* @see LLMimeParser
|
||||
*
|
||||
* An instance of this class is the parsed output from a LLMimeParser
|
||||
* which then allows for easy access into a data stream to find and
|
||||
* get what you want out of it.
|
||||
*
|
||||
* This class meant as a tool to quickly find what you seek in a
|
||||
* parsed mime entity. As such, it does not have useful support for
|
||||
* modification of a mime entity and specializes the interface toward
|
||||
* querying data from a fixed mime entity. Modifying an instance of
|
||||
* LLMimeIndx does not alter a mime entity and changes to a mime
|
||||
* entity itself are not propogated into an instance of a LLMimeIndex.
|
||||
*
|
||||
* Usage:<br>
|
||||
* LLMimeIndex mime_index;<br>
|
||||
* std::ifstream fstr("package.mime", ios::binary);<br>
|
||||
* LLMimeParser parser;<br>
|
||||
* if(parser.parseIndex(fstr, mime_index))<br>
|
||||
* {<br>
|
||||
* std::vector<U8> content;<br>
|
||||
* content.resize(mime_index.contentLength());<br>
|
||||
* fstr.seekg(mime_index.offset(), ios::beg);<br>
|
||||
* // ...do work on fstr and content<br>
|
||||
* }<br>
|
||||
*/
|
||||
class LLMimeIndex
|
||||
{
|
||||
public:
|
||||
/* @name Client interface.
|
||||
*/
|
||||
//@{
|
||||
/**
|
||||
* @brief Get the full parsed headers for this.
|
||||
*
|
||||
* If there are any headers, it will be a map of header name to
|
||||
* the value found on the line. The name is everything before the
|
||||
* colon, and the value is the string found after the colon to the
|
||||
* end of the line after trimming leading whitespace. So, for
|
||||
* example:
|
||||
* Content-Type: text/plain
|
||||
* would become an entry in the headers of:
|
||||
* headers["Content-Type"] == "text/plain"
|
||||
*
|
||||
* If this instance of an index was generated by the
|
||||
* LLMimeParser::parseIndex() call, all header names in rfc2045
|
||||
* will be capitalized as in rfc, eg Content-Length and
|
||||
* MIME-Version, not content-length and mime-version.
|
||||
* @return Returns an LLSD map of header name to value. Returns
|
||||
* undef if there are no headers.
|
||||
*/
|
||||
LLSD headers() const;
|
||||
|
||||
/**
|
||||
* @brief Get the content offset.
|
||||
*
|
||||
* @return Returns the number of bytes to the start of the data
|
||||
* segment from the start of serialized mime entity. Returns -1 if
|
||||
* offset is not known.
|
||||
*/
|
||||
S32 offset() const;
|
||||
|
||||
/**
|
||||
* @brief Get the length of the data segment for this mime part.
|
||||
*
|
||||
* @return Returns the content length in bytes. Returns -1 if
|
||||
* length is not known.
|
||||
*/
|
||||
S32 contentLength() const;
|
||||
|
||||
/**
|
||||
* @brief Get the mime type associated with this node.
|
||||
*
|
||||
* @return Returns the mimetype.
|
||||
*/
|
||||
std::string contentType() const;
|
||||
|
||||
/**
|
||||
* @brief Helper method which simplifies parsing the return from type()
|
||||
*
|
||||
* @return Returns true if this is a multipart mime, and therefore
|
||||
* getting subparts will succeed.
|
||||
*/
|
||||
bool isMultipart() const;
|
||||
|
||||
/**
|
||||
* @brief Get the number of atachments.
|
||||
*
|
||||
* @return Returns the number of sub-parts for this.
|
||||
*/
|
||||
S32 subPartCount() const;
|
||||
|
||||
/**
|
||||
* @brief Get the indicated attachment.
|
||||
*
|
||||
* @param index Value from 0 to (subPartCount() - 1).
|
||||
* @return Returns the indicated sub-part, or an invalid mime
|
||||
* index on failure.
|
||||
*/
|
||||
LLMimeIndex subPart(S32 index) const;
|
||||
//@}
|
||||
|
||||
/* @name Interface for building, testing, and helpers for typical use.
|
||||
*/
|
||||
//@{
|
||||
/**
|
||||
* @brief Default constructor - creates a useless LLMimeIndex.
|
||||
*/
|
||||
LLMimeIndex();
|
||||
|
||||
/**
|
||||
* @brief Full constructor.
|
||||
*
|
||||
* @param headers The complete headers.
|
||||
* @param content_offset The number of bytes to the start of the
|
||||
* data segment of this mime entity from the start of the stream
|
||||
* or buffer.
|
||||
*/
|
||||
LLMimeIndex(LLSD headers, S32 content_offset);
|
||||
|
||||
/**
|
||||
* @brief Copy constructor.
|
||||
*
|
||||
* @param mime The other mime object.
|
||||
*/
|
||||
LLMimeIndex(const LLMimeIndex& mime);
|
||||
|
||||
// @brief Destructor.
|
||||
~LLMimeIndex();
|
||||
|
||||
/*
|
||||
* @breif Assignment operator.
|
||||
*
|
||||
* @param mime The other mime object.
|
||||
* @return Returns this after assignment.
|
||||
*/
|
||||
LLMimeIndex& operator=(const LLMimeIndex& mime);
|
||||
|
||||
/**
|
||||
* @brief Add attachment information as a sub-part to a multipart mime.
|
||||
*
|
||||
* @param sub_part the part to attach.
|
||||
* @return Returns true on success, false on failure.
|
||||
*/
|
||||
bool attachSubPart(LLMimeIndex sub_part);
|
||||
//@}
|
||||
|
||||
protected:
|
||||
// Implementation.
|
||||
class Impl;
|
||||
Impl* mImpl;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @class LLMimeParser
|
||||
* @brief This class implements a MIME parser and verifier.
|
||||
*
|
||||
* THOROUGH_DESCRIPTION
|
||||
*/
|
||||
class LLMimeParser
|
||||
{
|
||||
public:
|
||||
// @brief Make a new mime parser.
|
||||
LLMimeParser();
|
||||
|
||||
// @brief Mime parser Destructor.
|
||||
~LLMimeParser();
|
||||
|
||||
// @brief Reset internal state of this parser.
|
||||
void reset();
|
||||
|
||||
|
||||
/* @name Index generation interface.
|
||||
*/
|
||||
//@{
|
||||
/**
|
||||
* @brief Parse a stream to find the mime index information.
|
||||
*
|
||||
* This method will scan the istr until a single complete mime
|
||||
* entity is read or EOF. The istr will be modified by this
|
||||
* parsing, so pass in a temporary stream or rewind/reset the
|
||||
* stream after this call.
|
||||
* @param istr An istream which contains a mime entity.
|
||||
* @param index[out] The parsed output.
|
||||
* @return Returns true if an index was parsed and no errors occurred.
|
||||
*/
|
||||
bool parseIndex(std::istream& istr, LLMimeIndex& index);
|
||||
|
||||
/**
|
||||
* @brief Parse a vector to find the mime index information.
|
||||
*
|
||||
* @param buffer A vector with data to parse.
|
||||
* @param index[out] The parsed output.
|
||||
* @return Returns true if an index was parsed and no errors occurred.
|
||||
*/
|
||||
bool parseIndex(const std::vector<U8>& buffer, LLMimeIndex& index);
|
||||
|
||||
/**
|
||||
* @brief Parse a stream to find the mime index information.
|
||||
*
|
||||
* This method will scan the istr until a single complete mime
|
||||
* entity is read, an EOF, or limit bytes have been scanned. The
|
||||
* istr will be modified by this parsing, so pass in a temporary
|
||||
* stream or rewind/reset the stream after this call.
|
||||
* @param istr An istream which contains a mime entity.
|
||||
* @param limit The maximum number of bytes to scan.
|
||||
* @param index[out] The parsed output.
|
||||
* @return Returns true if an index was parsed and no errors occurred.
|
||||
*/
|
||||
bool parseIndex(std::istream& istr, S32 limit, LLMimeIndex& index);
|
||||
|
||||
/**
|
||||
* @brief Parse a memory bufffer to find the mime index information.
|
||||
*
|
||||
* @param buffer The start of the buffer to parse.
|
||||
* @param buffer_length The length of the buffer.
|
||||
* @param index[out] The parsed output.
|
||||
* @return Returns true if an index was parsed and no errors occurred.
|
||||
*/
|
||||
bool parseIndex(const U8* buffer, S32 buffer_length, LLMimeIndex& index);
|
||||
//@}
|
||||
|
||||
/**
|
||||
* @brief
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
//bool verify(std::istream& istr, LLMimeIndex& index) const;
|
||||
|
||||
/**
|
||||
* @brief
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
//bool verify(U8* buffer, S32 buffer_length, LLMimeIndex& index) const;
|
||||
|
||||
protected:
|
||||
// Implementation.
|
||||
class Impl;
|
||||
Impl& mImpl;
|
||||
|
||||
private:
|
||||
// @brief Not implemneted to prevent copy consturction.
|
||||
LLMimeParser(const LLMimeParser& parser);
|
||||
|
||||
// @brief Not implemneted to prevent assignment.
|
||||
LLMimeParser& operator=(const LLMimeParser& mime);
|
||||
};
|
||||
|
||||
#endif // LL_LLMIME_H
|
||||
@@ -31,7 +31,6 @@
|
||||
|
||||
#include "llnamevalue.h"
|
||||
|
||||
#include "u64.h"
|
||||
#include "llstring.h"
|
||||
#include "llstringtable.h"
|
||||
|
||||
@@ -149,7 +148,7 @@ void LLNameValue::init(const char *name, const char *data, const char *type, con
|
||||
else if (!strcmp(mStringType, "U64"))
|
||||
{
|
||||
mType = NVT_U64;
|
||||
mNameValueReference.u64 = new U64(str_to_U64(ll_safe_string(data)));
|
||||
mNameValueReference.u64 = new U64(std::stoull(data));
|
||||
}
|
||||
else if (!strcmp(mStringType, "VEC3"))
|
||||
{
|
||||
@@ -919,9 +918,7 @@ std::string LLNameValue::printData() const
|
||||
break;
|
||||
case NVT_U64:
|
||||
{
|
||||
char u64_string[U64_BUFFER_LEN]; /* Flawfinder: ignore */
|
||||
U64_to_str(*mNameValueReference.u64, u64_string, sizeof(u64_string));
|
||||
buffer = u64_string;
|
||||
buffer = fmt::to_string(*mNameValueReference.u64);
|
||||
}
|
||||
break;
|
||||
case NVT_VEC3:
|
||||
@@ -952,11 +949,7 @@ std::ostream& operator<<(std::ostream& s, const LLNameValue &a)
|
||||
s << *(a.mNameValueReference.u32);
|
||||
break;
|
||||
case NVT_U64:
|
||||
{
|
||||
char u64_string[U64_BUFFER_LEN]; /* Flawfinder: ignore */
|
||||
U64_to_str(*a.mNameValueReference.u64, u64_string, sizeof(u64_string));
|
||||
s << u64_string;
|
||||
}
|
||||
s << (*a.mNameValueReference.u64);
|
||||
break;
|
||||
case NVT_VEC3:
|
||||
s << *(a.mNameValueReference.vec3);
|
||||
|
||||
@@ -30,7 +30,6 @@
|
||||
#include "lluuid.h"
|
||||
#include "llerror.h"
|
||||
#include "llmath.h"
|
||||
#include "u64.h"
|
||||
|
||||
//number of bytes sent in each message
|
||||
const U32 LL_XFER_CHUNK_SIZE = 1000;
|
||||
@@ -347,12 +346,12 @@ void LLXfer::abort (S32 result_code)
|
||||
|
||||
if (result_code != LL_ERR_CIRCUIT_GONE)
|
||||
{
|
||||
gMessageSystem->newMessageFast(_PREHASH_AbortXfer);
|
||||
gMessageSystem->nextBlockFast(_PREHASH_XferID);
|
||||
gMessageSystem->addU64Fast(_PREHASH_ID, mID);
|
||||
gMessageSystem->addS32Fast(_PREHASH_Result, result_code);
|
||||
|
||||
gMessageSystem->sendMessage(mRemoteHost);
|
||||
gMessageSystem->newMessageFast(_PREHASH_AbortXfer);
|
||||
gMessageSystem->nextBlockFast(_PREHASH_XferID);
|
||||
gMessageSystem->addU64Fast(_PREHASH_ID, mID);
|
||||
gMessageSystem->addS32Fast(_PREHASH_Result, result_code);
|
||||
|
||||
gMessageSystem->sendMessage(mRemoteHost);
|
||||
}
|
||||
|
||||
mStatus = e_LL_XFER_ABORTED;
|
||||
@@ -363,7 +362,7 @@ void LLXfer::abort (S32 result_code)
|
||||
|
||||
std::string LLXfer::getFileName()
|
||||
{
|
||||
return U64_to_str(mID);
|
||||
return fmt::to_string(mID);
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////
|
||||
|
||||
@@ -35,7 +35,6 @@
|
||||
|
||||
#include "llerror.h"
|
||||
#include "lluuid.h"
|
||||
#include "u64.h"
|
||||
|
||||
const F32 LL_XFER_REGISTRATION_TIMEOUT = 60.0f; // timeout if a registered transfer hasn't been requested in 60 seconds
|
||||
const F32 LL_PACKET_TIMEOUT = 3.0f; // packet timeout at 3 s
|
||||
@@ -543,11 +542,10 @@ void LLXferManager::processReceiveData (LLMessageSystem *mesgsys, void ** /*user
|
||||
if (fdata_size < 0 ||
|
||||
fdata_size > BUF_SIZE)
|
||||
{
|
||||
char U64_BUF[MAX_STRING]; /* Flawfinder : ignore */
|
||||
LL_WARNS("Xfer") << "Received invalid xfer data size of " << fdata_size
|
||||
<< " in packet number " << packetnum
|
||||
<< " from " << mesgsys->getSender()
|
||||
<< " for xfer id: " << U64_to_str(id, U64_BUF, sizeof(U64_BUF))
|
||||
<< " for xfer id: " << fmt::to_string(id)
|
||||
<< LL_ENDL;
|
||||
return;
|
||||
}
|
||||
@@ -556,10 +554,9 @@ void LLXferManager::processReceiveData (LLMessageSystem *mesgsys, void ** /*user
|
||||
xferp = findXferByID(id, mReceiveList);
|
||||
if (!xferp)
|
||||
{
|
||||
char U64_BUF[MAX_STRING]; /* Flawfinder : ignore */
|
||||
LL_WARNS("Xfer") << "received xfer data from " << mesgsys->getSender()
|
||||
<< " for non-existent xfer id: "
|
||||
<< U64_to_str(id, U64_BUF, sizeof(U64_BUF)) << LL_ENDL;
|
||||
<< fmt::to_string(id) << LL_ENDL;
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -765,8 +762,7 @@ void LLXferManager::processFileRequest (LLMessageSystem *mesgsys, void ** /*user
|
||||
mesgsys->getBOOL("XferID", "UseBigPackets", b_use_big_packets);
|
||||
|
||||
mesgsys->getU64Fast(_PREHASH_XferID, _PREHASH_ID, id);
|
||||
char U64_BUF[MAX_STRING]; /* Flawfinder : ignore */
|
||||
LL_INFOS("Xfer") << "xfer request id: " << U64_to_str(id, U64_BUF, sizeof(U64_BUF))
|
||||
LL_INFOS("Xfer") << "xfer request id: " << fmt::to_string(id)
|
||||
<< " to " << mesgsys->getSender() << LL_ENDL;
|
||||
|
||||
mesgsys->getStringFast(_PREHASH_XferID, _PREHASH_Filename, local_filename);
|
||||
@@ -890,9 +886,8 @@ void LLXferManager::processFileRequest (LLMessageSystem *mesgsys, void ** /*user
|
||||
}
|
||||
else
|
||||
{ // no uuid or filename - use the ID sent
|
||||
char U64_BUF[MAX_STRING]; /* Flawfinder : ignore */
|
||||
LL_INFOS("Xfer") << "starting memory transfer: "
|
||||
<< U64_to_str(id, U64_BUF, sizeof(U64_BUF)) << " to "
|
||||
<< fmt::to_string(id) << " to "
|
||||
<< mesgsys->getSender() << LL_ENDL;
|
||||
|
||||
xferp = findXferByID(id, mSendList);
|
||||
@@ -903,7 +898,7 @@ void LLXferManager::processFileRequest (LLMessageSystem *mesgsys, void ** /*user
|
||||
}
|
||||
else
|
||||
{
|
||||
LL_INFOS("Xfer") << "Warning: xfer ID " << U64_BUF << " not found." << LL_ENDL;
|
||||
LL_INFOS("Xfer") << "Warning: xfer ID " << fmt::to_string(id) << " not found." << LL_ENDL;
|
||||
result = LL_ERR_FILE_NOT_FOUND;
|
||||
}
|
||||
}
|
||||
@@ -937,12 +932,12 @@ void LLXferManager::processFileRequest (LLMessageSystem *mesgsys, void ** /*user
|
||||
{ // Not many transfers in progress already, so start immediately
|
||||
xferp->sendNextPacket();
|
||||
changeNumActiveXfers(xferp->mRemoteHost,1);
|
||||
LL_DEBUGS("Xfer") << "Starting xfer ID " << U64_to_str(id) << " immediately" << LL_ENDL;
|
||||
LL_DEBUGS("Xfer") << "Starting xfer ID " << fmt::to_string(id) << " immediately" << LL_ENDL;
|
||||
}
|
||||
else if (mHardLimitOutgoingXfersPerCircuit == 0 ||
|
||||
(host_statusp->mNumActive + host_statusp->mNumPending) < mHardLimitOutgoingXfersPerCircuit)
|
||||
{ // Must close the file handle and wait for earlier ones to complete
|
||||
LL_INFOS("Xfer") << " queueing xfer request id " << U64_to_str(id) << ", "
|
||||
LL_INFOS("Xfer") << " queueing xfer request id " << fmt::to_string(id) << ", "
|
||||
<< host_statusp->mNumActive << " active and "
|
||||
<< host_statusp->mNumPending << " pending ahead of this one"
|
||||
<< LL_ENDL;
|
||||
@@ -983,13 +978,13 @@ void LLXferManager::processFileRequest (LLMessageSystem *mesgsys, void ** /*user
|
||||
}
|
||||
else
|
||||
{
|
||||
LL_WARNS("Xfer") << "LLXferManager::processFileRequest() - no LLHostStatus found for id " << U64_to_str(id)
|
||||
LL_WARNS("Xfer") << "LLXferManager::processFileRequest() - no LLHostStatus found for id " << fmt::to_string(id)
|
||||
<< " host " << xferp->mRemoteHost << LL_ENDL;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
LL_WARNS("Xfer") << "LLXferManager::processFileRequest() - no xfer found for id " << U64_to_str(id) << LL_ENDL;
|
||||
LL_WARNS("Xfer") << "LLXferManager::processFileRequest() - no xfer found for id " << fmt::to_string(id) << LL_ENDL;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1113,7 +1108,7 @@ void LLXferManager::retransmitUnackedPackets()
|
||||
{
|
||||
if (xferp->reopenFileHandle())
|
||||
{
|
||||
LL_WARNS("Xfer") << "Error re-opening file handle for xfer ID " << U64_to_str(xferp->mID)
|
||||
LL_WARNS("Xfer") << "Error re-opening file handle for xfer ID " << fmt::to_string(xferp->mID)
|
||||
<< " to host " << xferp->mRemoteHost << LL_ENDL;
|
||||
xferp->abort(LL_ERR_CANNOT_OPEN_FILE);
|
||||
iter = mSendList.erase(iter);
|
||||
@@ -1122,7 +1117,7 @@ void LLXferManager::retransmitUnackedPackets()
|
||||
}
|
||||
else
|
||||
{ // No error re-opening the file, send the first packet
|
||||
LL_DEBUGS("Xfer") << "Moving pending xfer ID " << U64_to_str(xferp->mID) << " to active" << LL_ENDL;
|
||||
LL_DEBUGS("Xfer") << "Moving pending xfer ID " << fmt::to_string(xferp->mID) << " to active" << LL_ENDL;
|
||||
xferp->sendNextPacket();
|
||||
changeNumActiveXfers(xferp->mRemoteHost,1);
|
||||
}
|
||||
@@ -1136,7 +1131,7 @@ void LLXferManager::retransmitUnackedPackets()
|
||||
// so we don't blow through bandwidth.
|
||||
//
|
||||
|
||||
while (mXferAckQueue.size())
|
||||
while (!mXferAckQueue.empty())
|
||||
{
|
||||
if (mAckThrottle.checkOverflow(1000.0f*8.0f))
|
||||
{
|
||||
|
||||
@@ -73,7 +73,6 @@
|
||||
#include "llxfermanager.h"
|
||||
#include "timing.h"
|
||||
#include "llquaternion.h"
|
||||
#include "u64.h"
|
||||
#include "v3dmath.h"
|
||||
#include "v3math.h"
|
||||
#include "v4math.h"
|
||||
@@ -2600,54 +2599,54 @@ void LLMessageSystem::summarizeLogs(std::ostream& str)
|
||||
|
||||
// Incoming
|
||||
str << buffer << std::endl << "Incoming:" << std::endl;
|
||||
tmp_str = U64_to_str(mTotalBytesIn);
|
||||
tmp_str = fmt::to_string(mTotalBytesIn);
|
||||
buffer = llformat( "Total bytes received: %20s (%5.2f kbits per second)", tmp_str.c_str(), ((F32)mTotalBytesIn * 0.008f) / run_time);
|
||||
str << buffer << std::endl;
|
||||
tmp_str = U64_to_str(mPacketsIn);
|
||||
tmp_str = fmt::to_string(mPacketsIn);
|
||||
buffer = llformat( "Total packets received: %20s (%5.2f packets per second)", tmp_str.c_str(), ((F32) mPacketsIn / run_time));
|
||||
str << buffer << std::endl;
|
||||
buffer = llformat( "Average packet size: %20.0f bytes", (F32)mTotalBytesIn / (F32)mPacketsIn);
|
||||
str << buffer << std::endl;
|
||||
tmp_str = U64_to_str(mReliablePacketsIn);
|
||||
tmp_str = fmt::to_string(mReliablePacketsIn);
|
||||
buffer = llformat( "Total reliable packets: %20s (%5.2f%%)", tmp_str.c_str(), 100.f * ((F32) mReliablePacketsIn)/((F32) mPacketsIn + 1));
|
||||
str << buffer << std::endl;
|
||||
tmp_str = U64_to_str(mCompressedPacketsIn);
|
||||
tmp_str = fmt::to_string(mCompressedPacketsIn);
|
||||
buffer = llformat( "Total compressed packets: %20s (%5.2f%%)", tmp_str.c_str(), 100.f * ((F32) mCompressedPacketsIn)/((F32) mPacketsIn + 1));
|
||||
str << buffer << std::endl;
|
||||
S64 savings = mUncompressedBytesIn - mCompressedBytesIn;
|
||||
tmp_str = U64_to_str(savings);
|
||||
tmp_str = fmt::to_string(savings);
|
||||
buffer = llformat( "Total compression savings: %20s bytes", tmp_str.c_str());
|
||||
str << buffer << std::endl;
|
||||
tmp_str = U64_to_str(savings/(mCompressedPacketsIn +1));
|
||||
tmp_str = fmt::to_string(savings/(mCompressedPacketsIn +1));
|
||||
buffer = llformat( "Avg comp packet savings: %20s (%5.2f : 1)", tmp_str.c_str(), ((F32) mUncompressedBytesIn)/((F32) mCompressedBytesIn+1));
|
||||
str << buffer << std::endl;
|
||||
tmp_str = U64_to_str(savings/(mPacketsIn+1));
|
||||
tmp_str = fmt::to_string(savings/(mPacketsIn+1));
|
||||
buffer = llformat( "Avg overall comp savings: %20s (%5.2f : 1)", tmp_str.c_str(), ((F32) mTotalBytesIn + (F32) savings)/((F32) mTotalBytesIn + 1.f));
|
||||
|
||||
// Outgoing
|
||||
str << buffer << std::endl << std::endl << "Outgoing:" << std::endl;
|
||||
tmp_str = U64_to_str(mTotalBytesOut);
|
||||
tmp_str = fmt::to_string(mTotalBytesOut);
|
||||
buffer = llformat( "Total bytes sent: %20s (%5.2f kbits per second)", tmp_str.c_str(), ((F32)mTotalBytesOut * 0.008f) / run_time );
|
||||
str << buffer << std::endl;
|
||||
tmp_str = U64_to_str(mPacketsOut);
|
||||
tmp_str = fmt::to_string(mPacketsOut);
|
||||
buffer = llformat( "Total packets sent: %20s (%5.2f packets per second)", tmp_str.c_str(), ((F32)mPacketsOut / run_time));
|
||||
str << buffer << std::endl;
|
||||
buffer = llformat( "Average packet size: %20.0f bytes", (F32)mTotalBytesOut / (F32)mPacketsOut);
|
||||
str << buffer << std::endl;
|
||||
tmp_str = U64_to_str(mReliablePacketsOut);
|
||||
tmp_str = fmt::to_string(mReliablePacketsOut);
|
||||
buffer = llformat( "Total reliable packets: %20s (%5.2f%%)", tmp_str.c_str(), 100.f * ((F32) mReliablePacketsOut)/((F32) mPacketsOut + 1));
|
||||
str << buffer << std::endl;
|
||||
tmp_str = U64_to_str(mCompressedPacketsOut);
|
||||
tmp_str = fmt::to_string(mCompressedPacketsOut);
|
||||
buffer = llformat( "Total compressed packets: %20s (%5.2f%%)", tmp_str.c_str(), 100.f * ((F32) mCompressedPacketsOut)/((F32) mPacketsOut + 1));
|
||||
str << buffer << std::endl;
|
||||
savings = mUncompressedBytesOut - mCompressedBytesOut;
|
||||
tmp_str = U64_to_str(savings);
|
||||
tmp_str = fmt::to_string(savings);
|
||||
buffer = llformat( "Total compression savings: %20s bytes", tmp_str.c_str());
|
||||
str << buffer << std::endl;
|
||||
tmp_str = U64_to_str(savings/(mCompressedPacketsOut +1));
|
||||
tmp_str = fmt::to_string(savings/(mCompressedPacketsOut +1));
|
||||
buffer = llformat( "Avg comp packet savings: %20s (%5.2f : 1)", tmp_str.c_str(), ((F32) mUncompressedBytesOut)/((F32) mCompressedBytesOut+1));
|
||||
str << buffer << std::endl;
|
||||
tmp_str = U64_to_str(savings/(mPacketsOut+1));
|
||||
tmp_str = fmt::to_string(savings/(mPacketsOut+1));
|
||||
buffer = llformat( "Avg overall comp savings: %20s (%5.2f : 1)", tmp_str.c_str(), ((F32) mTotalBytesOut + (F32) savings)/((F32) mTotalBytesOut + 1.f));
|
||||
str << buffer << std::endl << std::endl;
|
||||
buffer = llformat( "SendPacket failures: %20d", mSendPacketFailureCount);
|
||||
|
||||
@@ -1,445 +0,0 @@
|
||||
/**
|
||||
* @file llmime_test.cpp
|
||||
* @author Phoenix
|
||||
* @date 2006-12-24
|
||||
* @brief BRIEF_DESC of llmime_test.cpp
|
||||
*
|
||||
* $LicenseInfo:firstyear=2006&license=viewerlgpl$
|
||||
* Second Life Viewer Source Code
|
||||
* Copyright (C) 2010, Linden Research, Inc.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation;
|
||||
* version 2.1 of the License only.
|
||||
*
|
||||
* 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 "linden_common.h"
|
||||
|
||||
#include "llsdserialize.h"
|
||||
|
||||
#include "../llmime.h"
|
||||
|
||||
#include "../test/lltut.h"
|
||||
|
||||
namespace tut
|
||||
{
|
||||
struct mime_index
|
||||
{
|
||||
};
|
||||
typedef test_group<mime_index> mime_index_t;
|
||||
typedef mime_index_t::object mime_index_object_t;
|
||||
tut::mime_index_t tut_mime_index("LLMime");
|
||||
|
||||
template<> template<>
|
||||
void mime_index_object_t::test<1>()
|
||||
{
|
||||
LLMimeIndex mime;
|
||||
ensure("no headers", mime.headers().isUndefined());
|
||||
ensure_equals("invalid offset", mime.offset(), -1);
|
||||
ensure_equals("invalid content length", mime.contentLength(), -1);
|
||||
ensure("no content type", mime.contentType().empty());
|
||||
ensure("not multipart", !mime.isMultipart());
|
||||
ensure_equals("no attachments", mime.subPartCount(), 0);
|
||||
}
|
||||
|
||||
template<> template<>
|
||||
void mime_index_object_t::test<2>()
|
||||
{
|
||||
const S32 CONTENT_LENGTH = 6000;
|
||||
const S32 CONTENT_OFFSET = 100;
|
||||
const std::string CONTENT_TYPE = std::string("image/j2c");
|
||||
LLSD headers;
|
||||
headers["Content-Length"] = CONTENT_LENGTH;
|
||||
headers["Content-Type"] = CONTENT_TYPE;
|
||||
LLMimeIndex mime(headers, CONTENT_OFFSET);
|
||||
ensure("headers are map", mime.headers().isMap());
|
||||
ensure_equals("offset", mime.offset(), CONTENT_OFFSET);
|
||||
ensure_equals("content length", mime.contentLength(), CONTENT_LENGTH);
|
||||
ensure_equals("type is image/j2c", mime.contentType(), CONTENT_TYPE);
|
||||
ensure("not multipart", !mime.isMultipart());
|
||||
ensure_equals("no attachments", mime.subPartCount(), 0);
|
||||
}
|
||||
|
||||
template<> template<>
|
||||
void mime_index_object_t::test<3>()
|
||||
{
|
||||
const S32 MULTI_CONTENT_LENGTH = 8000;
|
||||
const S32 MULTI_CONTENT_OFFSET = 100;
|
||||
const std::string MULTI_CONTENT_TYPE = std::string("multipart/mixed");
|
||||
LLSD headers;
|
||||
headers["Content-Length"] = MULTI_CONTENT_LENGTH;
|
||||
headers["Content-Type"] = MULTI_CONTENT_TYPE;
|
||||
LLMimeIndex mime(headers, MULTI_CONTENT_OFFSET);
|
||||
LL_INFOS() << "headers: " << LLSDOStreamer<LLSDNotationFormatter>(headers)
|
||||
<< LL_ENDL;
|
||||
|
||||
|
||||
const S32 META_CONTENT_LENGTH = 700;
|
||||
const S32 META_CONTENT_OFFSET = 69;
|
||||
const std::string META_CONTENT_TYPE = std::string(
|
||||
"text/llsd+xml");
|
||||
headers = LLSD::emptyMap();
|
||||
headers["Content-Length"] = META_CONTENT_LENGTH;
|
||||
headers["Content-Type"] = META_CONTENT_TYPE;
|
||||
LLMimeIndex meta(headers, META_CONTENT_OFFSET);
|
||||
mime.attachSubPart(meta);
|
||||
|
||||
const S32 IMAGE_CONTENT_LENGTH = 6000;
|
||||
const S32 IMAGE_CONTENT_OFFSET = 200;
|
||||
const std::string IMAGE_CONTENT_TYPE = std::string("image/j2c");
|
||||
headers = LLSD::emptyMap();
|
||||
headers["Content-Length"] = IMAGE_CONTENT_LENGTH;
|
||||
headers["Content-Type"] = IMAGE_CONTENT_TYPE;
|
||||
LLMimeIndex image(headers, IMAGE_CONTENT_OFFSET);
|
||||
mime.attachSubPart(image);
|
||||
|
||||
// make sure we have a valid multi-part
|
||||
ensure("is multipart", mime.isMultipart());
|
||||
ensure_equals("multi offset", mime.offset(), MULTI_CONTENT_OFFSET);
|
||||
ensure_equals(
|
||||
"multi content length",
|
||||
mime.contentLength(),
|
||||
MULTI_CONTENT_LENGTH);
|
||||
ensure_equals("two attachments", mime.subPartCount(), 2);
|
||||
|
||||
// make sure ranged gets do the right thing with out of bounds
|
||||
// sub-parts.
|
||||
LLMimeIndex invalid_child(mime.subPart(-1));
|
||||
ensure("no headers", invalid_child.headers().isUndefined());
|
||||
ensure_equals("invalid offset", invalid_child.offset(), -1);
|
||||
ensure_equals(
|
||||
"invalid content length", invalid_child.contentLength(), -1);
|
||||
ensure("no content type", invalid_child.contentType().empty());
|
||||
ensure("not multipart", !invalid_child.isMultipart());
|
||||
ensure_equals("no attachments", invalid_child.subPartCount(), 0);
|
||||
|
||||
invalid_child = mime.subPart(2);
|
||||
ensure("no headers", invalid_child.headers().isUndefined());
|
||||
ensure_equals("invalid offset", invalid_child.offset(), -1);
|
||||
ensure_equals(
|
||||
"invalid content length", invalid_child.contentLength(), -1);
|
||||
ensure("no content type", invalid_child.contentType().empty());
|
||||
ensure("not multipart", !invalid_child.isMultipart());
|
||||
ensure_equals("no attachments", invalid_child.subPartCount(), 0);
|
||||
}
|
||||
|
||||
template<> template<>
|
||||
void mime_index_object_t::test<4>()
|
||||
{
|
||||
const S32 MULTI_CONTENT_LENGTH = 8000;
|
||||
const S32 MULTI_CONTENT_OFFSET = 100;
|
||||
const std::string MULTI_CONTENT_TYPE = std::string("multipart/mixed");
|
||||
LLSD headers;
|
||||
headers["Content-Length"] = MULTI_CONTENT_LENGTH;
|
||||
headers["Content-Type"] = MULTI_CONTENT_TYPE;
|
||||
LLMimeIndex mime(headers, MULTI_CONTENT_OFFSET);
|
||||
|
||||
const S32 META_CONTENT_LENGTH = 700;
|
||||
const S32 META_CONTENT_OFFSET = 69;
|
||||
const std::string META_CONTENT_TYPE = std::string(
|
||||
"application/llsd+xml");
|
||||
headers = LLSD::emptyMap();
|
||||
headers["Content-Length"] = META_CONTENT_LENGTH;
|
||||
headers["Content-Type"] = META_CONTENT_TYPE;
|
||||
LLMimeIndex meta(headers, META_CONTENT_OFFSET);
|
||||
mime.attachSubPart(meta);
|
||||
|
||||
const S32 IMAGE_CONTENT_LENGTH = 6000;
|
||||
const S32 IMAGE_CONTENT_OFFSET = 200;
|
||||
const std::string IMAGE_CONTENT_TYPE = std::string("image/j2c");
|
||||
headers = LLSD::emptyMap();
|
||||
headers["Content-Length"] = IMAGE_CONTENT_LENGTH;
|
||||
headers["Content-Type"] = IMAGE_CONTENT_TYPE;
|
||||
LLMimeIndex image(headers, IMAGE_CONTENT_OFFSET);
|
||||
mime.attachSubPart(image);
|
||||
|
||||
// check what we have
|
||||
ensure("is multipart", mime.isMultipart());
|
||||
ensure_equals("multi offset", mime.offset(), MULTI_CONTENT_OFFSET);
|
||||
ensure_equals(
|
||||
"multi content length",
|
||||
mime.contentLength(),
|
||||
MULTI_CONTENT_LENGTH);
|
||||
ensure_equals("two attachments", mime.subPartCount(), 2);
|
||||
|
||||
LLMimeIndex actual_meta = mime.subPart(0);
|
||||
ensure_equals(
|
||||
"meta type", actual_meta.contentType(), META_CONTENT_TYPE);
|
||||
ensure_equals(
|
||||
"meta offset", actual_meta.offset(), META_CONTENT_OFFSET);
|
||||
ensure_equals(
|
||||
"meta content length",
|
||||
actual_meta.contentLength(),
|
||||
META_CONTENT_LENGTH);
|
||||
|
||||
LLMimeIndex actual_image = mime.subPart(1);
|
||||
ensure_equals(
|
||||
"image type", actual_image.contentType(), IMAGE_CONTENT_TYPE);
|
||||
ensure_equals(
|
||||
"image offset", actual_image.offset(), IMAGE_CONTENT_OFFSET);
|
||||
ensure_equals(
|
||||
"image content length",
|
||||
actual_image.contentLength(),
|
||||
IMAGE_CONTENT_LENGTH);
|
||||
}
|
||||
|
||||
/*
|
||||
template<> template<>
|
||||
void mime_index_object_t::test<5>()
|
||||
{
|
||||
}
|
||||
template<> template<>
|
||||
void mime_index_object_t::test<6>()
|
||||
{
|
||||
}
|
||||
template<> template<>
|
||||
void mime_index_object_t::test<7>()
|
||||
{
|
||||
}
|
||||
template<> template<>
|
||||
void mime_index_object_t::test<8>()
|
||||
{
|
||||
}
|
||||
template<> template<>
|
||||
void mime_index_object_t::test<>()
|
||||
{
|
||||
}
|
||||
*/
|
||||
}
|
||||
|
||||
|
||||
namespace tut
|
||||
{
|
||||
struct mime_parse
|
||||
{
|
||||
};
|
||||
typedef test_group<mime_parse> mime_parse_t;
|
||||
typedef mime_parse_t::object mime_parse_object_t;
|
||||
tut::mime_parse_t tut_mime_parse("LLMimeParse");
|
||||
|
||||
template<> template<>
|
||||
void mime_parse_object_t::test<1>()
|
||||
{
|
||||
// parse one mime object
|
||||
const std::string SERIALIZED_MIME("Content-Length: 200\r\nContent-Type: text/plain\r\n\r\naaaaaaaaaaaaaaaaaaaabbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbcccccccccc\r\n");
|
||||
std::stringstream istr;
|
||||
istr.str(SERIALIZED_MIME);
|
||||
LLMimeIndex mime;
|
||||
LLMimeParser parser;
|
||||
bool ok = parser.parseIndex(istr, mime);
|
||||
ensure("Parse successful.", ok);
|
||||
ensure_equals("content type", mime.contentType(), "text/plain");
|
||||
ensure_equals("content length", mime.contentLength(), 200);
|
||||
ensure_equals("offset", mime.offset(), 49);
|
||||
}
|
||||
|
||||
template<> template<>
|
||||
void mime_parse_object_t::test<2>()
|
||||
{
|
||||
// make sure we only parse one.
|
||||
const std::string SERIALIZED_MIME("Content-Length: 200\r\nContent-Type: text/plain\r\n\r\naaaaaaaaaaaaaaaaaaaabbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbcccccccccc\r\n\r\nContent-Length: 200\r\nContent-Type: text/plain\r\n\r\naaaaaaaaaaaaaaaaaaaabbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbcccccccccc\r\n\r\n");
|
||||
std::stringstream istr;
|
||||
istr.str(SERIALIZED_MIME);
|
||||
LLMimeIndex mime;
|
||||
LLMimeParser parser;
|
||||
bool ok = parser.parseIndex(istr, mime);
|
||||
ensure("Parse successful.", ok);
|
||||
ensure("not multipart.", !mime.isMultipart());
|
||||
ensure_equals("content type", mime.contentType(), "text/plain");
|
||||
ensure_equals("content length", mime.contentLength(), 200);
|
||||
ensure_equals("offset", mime.offset(), 49);
|
||||
}
|
||||
|
||||
template<> template<>
|
||||
void mime_parse_object_t::test<3>()
|
||||
{
|
||||
// test multi-part and lack of content length for some of it.
|
||||
/*
|
||||
Content-Type: multipart/mixed; boundary="segment"rnContent-Length: 148rnrn--segmentrnContent-Type: text/plainrnrnsome datarnrn--segmentrnContent-Type: text/xml; charset=UTF-8rnContent-Length: 22rnrn<llsd><undef /></llsd>rnrn
|
||||
*/
|
||||
const std::string SERIALIZED_MIME("Content-Type: multipart/mixed; boundary=\"segment\"\r\nContent-Length: 150\r\n\r\n--segment\r\nContent-Type: text/plain\r\n\r\nsome data\r\n\r\n--segment\r\nContent-Type: text/xml; charset=UTF-8\r\nContent-Length: 22\r\n\r\n<llsd><undef /></llsd>\r\n\r\n");
|
||||
std::stringstream istr;
|
||||
istr.str(SERIALIZED_MIME);
|
||||
LLMimeIndex mime;
|
||||
LLMimeParser parser;
|
||||
bool ok = parser.parseIndex(istr, mime);
|
||||
ensure("Parse successful.", ok);
|
||||
ensure("is multipart.", mime.isMultipart());
|
||||
ensure_equals("sub-part count", mime.subPartCount(), 2);
|
||||
ensure_equals("content length", mime.contentLength(), 150);
|
||||
ensure_equals("data offset for multipart", mime.offset(), 74);
|
||||
|
||||
LLMimeIndex mime_plain(mime.subPart(0));
|
||||
ensure_equals(
|
||||
"first part type",
|
||||
mime_plain.contentType(),
|
||||
"text/plain");
|
||||
ensure_equals(
|
||||
"first part content length not known.",
|
||||
mime_plain.contentLength(),
|
||||
-1);
|
||||
ensure_equals("first part offset", mime_plain.offset(), 113);
|
||||
|
||||
LLMimeIndex mime_xml(mime.subPart(1));
|
||||
ensure_equals(
|
||||
"second part type",
|
||||
mime_xml.contentType(),
|
||||
"text/xml; charset=UTF-8");
|
||||
ensure_equals(
|
||||
"second part content length",
|
||||
mime_xml.contentLength(),
|
||||
22);
|
||||
ensure_equals("second part offset", mime_xml.offset(), 198);
|
||||
}
|
||||
|
||||
template<> template<>
|
||||
void mime_parse_object_t::test<4>()
|
||||
{
|
||||
// test multi-part, unquoted separator, and premature eof conditions
|
||||
/*
|
||||
Content-Type: multipart/mixed; boundary=segmentrnContent-Length: 220rnrn--segmentrnContent-Type: text/plainrnContent-Length: 55rnrnhow are you today?rnI do not know. I guess I am:n'fine'rnrn--segmentrnContent-Type: text/xml; charset=UTF-8rnContent-Length: 22rnrn<llsd><undef /></llsd>rnrn */
|
||||
const std::string SERIALIZED_MIME("Content-Type: multipart/mixed; boundary=segment\r\nContent-Length: 220\r\n\r\n--segment\r\nContent-Type: text/plain\r\nContent-Length: 55\r\n\r\nhow are you today?\r\nI do not know. I guess I am:\n'fine'\r\n\r\n--segment\r\nContent-Type: text/xml; charset=UTF-8\r\nContent-Length: 22\r\n\r\n<llsd><undef /></llsd>\r\n\r\n");
|
||||
std::stringstream istr;
|
||||
istr.str(SERIALIZED_MIME);
|
||||
LLMimeIndex mime;
|
||||
LLMimeParser parser;
|
||||
bool ok = parser.parseIndex(istr, mime);
|
||||
ensure("Parse successful.", ok);
|
||||
ensure("is multipart.", mime.isMultipart());
|
||||
ensure_equals("sub-part count", mime.subPartCount(), 2);
|
||||
ensure_equals("content length", mime.contentLength(), 220);
|
||||
ensure_equals("data offset for multipart", mime.offset(), 72);
|
||||
|
||||
LLMimeIndex mime_plain(mime.subPart(0));
|
||||
ensure_equals(
|
||||
"first part type",
|
||||
mime_plain.contentType(),
|
||||
"text/plain");
|
||||
ensure_equals(
|
||||
"first part content length",
|
||||
mime_plain.contentLength(),
|
||||
55);
|
||||
ensure_equals("first part offset", mime_plain.offset(), 131);
|
||||
|
||||
LLMimeIndex mime_xml(mime.subPart(1));
|
||||
ensure_equals(
|
||||
"second part type",
|
||||
mime_xml.contentType(),
|
||||
"text/xml; charset=UTF-8");
|
||||
ensure_equals(
|
||||
"second part content length",
|
||||
mime_xml.contentLength(),
|
||||
22);
|
||||
ensure_equals("second part offset", mime_xml.offset(), 262);
|
||||
}
|
||||
|
||||
template<> template<>
|
||||
void mime_parse_object_t::test<5>()
|
||||
{
|
||||
// test multi-part with multiple params
|
||||
const std::string SERIALIZED_MIME("Content-Type: multipart/mixed; boundary=segment; comment=\"testing multiple params.\"\r\nContent-Length: 220\r\n\r\n--segment\r\nContent-Type: text/plain\r\nContent-Length: 55\r\n\r\nhow are you today?\r\nI do not know. I guess I am:\n'fine'\r\n\r\n--segment\r\nContent-Type: text/xml; charset=UTF-8\r\nContent-Length: 22\r\n\r\n<llsd><undef /></llsd>\r\n\r\n");
|
||||
std::stringstream istr;
|
||||
istr.str(SERIALIZED_MIME);
|
||||
LLMimeIndex mime;
|
||||
LLMimeParser parser;
|
||||
bool ok = parser.parseIndex(istr, mime);
|
||||
ensure("Parse successful.", ok);
|
||||
ensure("is multipart.", mime.isMultipart());
|
||||
ensure_equals("sub-part count", mime.subPartCount(), 2);
|
||||
ensure_equals("content length", mime.contentLength(), 220);
|
||||
|
||||
LLMimeIndex mime_plain(mime.subPart(0));
|
||||
ensure_equals(
|
||||
"first part type",
|
||||
mime_plain.contentType(),
|
||||
"text/plain");
|
||||
ensure_equals(
|
||||
"first part content length",
|
||||
mime_plain.contentLength(),
|
||||
55);
|
||||
|
||||
LLMimeIndex mime_xml(mime.subPart(1));
|
||||
ensure_equals(
|
||||
"second part type",
|
||||
mime_xml.contentType(),
|
||||
"text/xml; charset=UTF-8");
|
||||
ensure_equals(
|
||||
"second part content length",
|
||||
mime_xml.contentLength(),
|
||||
22);
|
||||
}
|
||||
|
||||
template<> template<>
|
||||
void mime_parse_object_t::test<6>()
|
||||
{
|
||||
// test multi-part with no specified boundary and eof
|
||||
/*
|
||||
Content-Type: multipart/relatedrnContent-Length: 220rnrn--rnContent-Type: text/plainrnContent-Length: 55rnrnhow are you today?rnI do not know. I guess I am:n'fine'rnrn--rnContent-Type: text/xml; charset=UTF-8rnContent-Length: 22rnrn<llsd><undef /></llsd>rnrn
|
||||
*/
|
||||
const std::string SERIALIZED_MIME("Content-Type: multipart/related\r\nContent-Length: 500\r\n\r\n--\r\nContent-Type: text/plain\r\nContent-Length: 55\r\n\r\nhow are you today?\r\nI do not know. I guess I am:\n'fine'\r\n\r\n--\r\nContent-Type: text/xml; charset=UTF-8\r\nContent-Length: 22\r\n\r\n<llsd><undef /></llsd>\r\n\r\n");
|
||||
std::stringstream istr;
|
||||
istr.str(SERIALIZED_MIME);
|
||||
LLMimeIndex mime;
|
||||
LLMimeParser parser;
|
||||
bool ok = parser.parseIndex(istr, mime);
|
||||
ensure("Parse successful.", ok);
|
||||
ensure("is multipart.", mime.isMultipart());
|
||||
ensure_equals("sub-part count", mime.subPartCount(), 2);
|
||||
ensure_equals("content length", mime.contentLength(), 500);
|
||||
ensure_equals("data offset for multipart", mime.offset(), 56);
|
||||
|
||||
LLMimeIndex mime_plain(mime.subPart(0));
|
||||
ensure_equals(
|
||||
"first part type",
|
||||
mime_plain.contentType(),
|
||||
"text/plain");
|
||||
ensure_equals(
|
||||
"first part content length",
|
||||
mime_plain.contentLength(),
|
||||
55);
|
||||
ensure_equals("first part offset", mime_plain.offset(), 108);
|
||||
|
||||
LLMimeIndex mime_xml(mime.subPart(1));
|
||||
ensure_equals(
|
||||
"second part type",
|
||||
mime_xml.contentType(),
|
||||
"text/xml; charset=UTF-8");
|
||||
ensure_equals(
|
||||
"second part content length",
|
||||
mime_xml.contentLength(),
|
||||
22);
|
||||
ensure_equals("second part offset", mime_xml.offset(), 232);
|
||||
}
|
||||
|
||||
/*
|
||||
template<> template<>
|
||||
void mime_parse_object_t::test<>()
|
||||
{
|
||||
}
|
||||
template<> template<>
|
||||
void mime_parse_object_t::test<>()
|
||||
{
|
||||
}
|
||||
template<> template<>
|
||||
void mime_parse_object_t::test<>()
|
||||
{
|
||||
}
|
||||
template<> template<>
|
||||
void mime_parse_object_t::test<>()
|
||||
{
|
||||
}
|
||||
*/
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -5,21 +5,21 @@
|
||||
* $LicenseInfo:firstyear=2013&license=viewerlgpl$
|
||||
* Second Life Viewer Source Code
|
||||
* Copyright (C) 2013, 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$
|
||||
*/
|
||||
@@ -42,13 +42,13 @@ class domMesh;
|
||||
class LLDAELoader : public LLModelLoader
|
||||
{
|
||||
public:
|
||||
typedef std::map<std::string, LLImportMaterial> material_map;
|
||||
typedef std::map<std::string, LLImportMaterial> material_map;
|
||||
typedef std::map<daeElement*, std::vector<LLPointer<LLModel> > > dae_model_map;
|
||||
dae_model_map mModelsMap;
|
||||
dae_model_map mModelsMap;
|
||||
|
||||
LLDAELoader(
|
||||
std::string filename,
|
||||
S32 lod,
|
||||
std::string filename,
|
||||
S32 lod,
|
||||
LLModelLoader::load_callback_t load_cb,
|
||||
LLModelLoader::joint_lookup_func_t joint_lookup_func,
|
||||
LLModelLoader::texture_load_func_t texture_load_func,
|
||||
@@ -56,41 +56,40 @@ public:
|
||||
void* opaque_userdata,
|
||||
JointTransformMap& jointTransformMap,
|
||||
JointNameSet& jointsFromNodes,
|
||||
std::map<std::string, std::string>& jointAliasMap,
|
||||
std::map<std::string, std::string>& jointAliasMap,
|
||||
U32 maxJointsPerMesh,
|
||||
U32 modelLimit,
|
||||
bool preprocess);
|
||||
virtual ~LLDAELoader() ;
|
||||
virtual ~LLDAELoader();
|
||||
|
||||
virtual bool OpenFile(const std::string& filename);
|
||||
|
||||
protected:
|
||||
|
||||
void processElement(daeElement* element, bool& badElement, DAE* dae);
|
||||
void processElement(daeElement* element, bool& badElement, DAE* dae, daeElement* domRoot);
|
||||
void processDomModel(LLModel* model, DAE* dae, daeElement* pRoot, domMesh* mesh, domSkin* skin);
|
||||
|
||||
material_map getMaterials(LLModel* model, domInstance_geometry* instance_geo, DAE* dae);
|
||||
LLImportMaterial profileToMaterial(domProfile_COMMON* material, DAE* dae);
|
||||
LLColor4 getDaeColor(daeElement* element);
|
||||
|
||||
daeElement* getChildFromElement( daeElement* pElement, std::string const & name );
|
||||
|
||||
bool isNodeAJoint( domNode* pNode );
|
||||
void processJointNode( domNode* pNode, std::map<std::string,LLMatrix4>& jointTransforms );
|
||||
void extractTranslation( domTranslate* pTranslate, LLMatrix4& transform );
|
||||
void extractTranslationViaElement( daeElement* pTranslateElement, LLMatrix4& transform );
|
||||
void extractTranslationViaSID( daeElement* pElement, LLMatrix4& transform );
|
||||
void buildJointToNodeMappingFromScene( daeElement* pRoot );
|
||||
void processJointToNodeMapping( domNode* pNode );
|
||||
void processChildJoints( domNode* pParentNode );
|
||||
material_map getMaterials(LLModel* model, domInstance_geometry* instance_geo, DAE* dae) const;
|
||||
LLImportMaterial profileToMaterial(domProfile_COMMON* material, DAE* dae) const;
|
||||
LLColor4 getDaeColor(daeElement* element) const;
|
||||
|
||||
bool verifyCount( int expected, int result );
|
||||
daeElement* getChildFromElement(daeElement* pElement, std::string const& name);
|
||||
|
||||
bool isNodeAJoint(const domNode* pNode) const;
|
||||
void processJointNode(domNode* pNode, JointTransformMap& jointTransforms);
|
||||
void extractTranslation(const domTranslate* pTranslate, LLMatrix4& transform) const;
|
||||
void extractTranslationViaSID(daeElement* pElement, LLMatrix4& transform) const;
|
||||
void buildJointToNodeMappingFromScene(daeElement* pRoot);
|
||||
void processJointToNodeMapping(domNode* pNode);
|
||||
void processChildJoints(domNode* pParentNode);
|
||||
|
||||
bool verifyCount(const size_t expected, const size_t result) const;
|
||||
|
||||
//Verify that a controller matches vertex counts
|
||||
bool verifyController( domController* pController );
|
||||
bool verifyController(const domController* pController) const;
|
||||
|
||||
static bool addVolumeFacesFromDomMesh(LLModel* model, domMesh* mesh);
|
||||
static bool createVolumeFacesFromDomMesh(LLModel* model, domMesh *mesh);
|
||||
static bool createVolumeFacesFromDomMesh(LLModel* model, domMesh* mesh);
|
||||
|
||||
static LLModel* loadModelFromDomMesh(domMesh* mesh);
|
||||
|
||||
@@ -99,11 +98,11 @@ protected:
|
||||
//
|
||||
bool loadModelsFromDomMesh(domMesh* mesh, std::vector<LLModel*>& models_out, U32 submodel_limit);
|
||||
|
||||
static std::string getElementLabel(daeElement *element);
|
||||
static size_t getSuffixPosition(std::string label);
|
||||
static std::string getLodlessLabel(daeElement *element);
|
||||
static std::string getElementLabel(daeElement* element);
|
||||
static size_t getSuffixPosition(const std::string label);
|
||||
static std::string getLodlessLabel(daeElement* element);
|
||||
|
||||
static std::string preprocessDAE(std::string filename);
|
||||
static std::string preprocessDAE(const std::string filename);
|
||||
|
||||
private:
|
||||
U32 mGeneratedModelLimit; // Attempt to limit amount of generated submodels
|
||||
|
||||
@@ -99,7 +99,7 @@ public:
|
||||
|
||||
S32 mLod;
|
||||
|
||||
LLMatrix4 mTransform;
|
||||
LLMatrix4 mTransform, mBindTransform;
|
||||
BOOL mFirstTransform;
|
||||
LLVector3 mExtents[2];
|
||||
|
||||
@@ -180,7 +180,7 @@ public:
|
||||
//-----------------------------------------------------------------------------
|
||||
// isNodeAJoint()
|
||||
//-----------------------------------------------------------------------------
|
||||
bool isNodeAJoint(const char* name)
|
||||
bool isNodeAJoint(const char* name) const
|
||||
{
|
||||
return name != NULL && mJointMap.find(name) != mJointMap.end();
|
||||
}
|
||||
|
||||
@@ -2146,7 +2146,7 @@ void LLRender::setLineWidth(F32 line_width)
|
||||
}
|
||||
if (mNewContext.lineWidth != line_width || mDirty)
|
||||
{
|
||||
if (mMode == LLRender::LINES || LLRender::LINE_STRIP)
|
||||
if (mMode == LLRender::LINES || mMode == LLRender::LINE_STRIP)
|
||||
{
|
||||
flush();
|
||||
}
|
||||
@@ -2483,16 +2483,17 @@ void LLRender::vertexBatchPreTransformed(LLVector4a* verts, S32 vert_count)
|
||||
mTexcoordsp[mCount] = mTexcoordsp[mCount - 1];
|
||||
}
|
||||
|
||||
mVerticesp.copyArray(mCount, verts, vert_count);
|
||||
|
||||
for (S32 i = 0; i < vert_count; i++)
|
||||
{
|
||||
mVerticesp[mCount] = verts[i];
|
||||
|
||||
mCount++;
|
||||
mTexcoordsp[mCount] = mTexcoordsp[mCount-1];
|
||||
mColorsp[mCount] = mColorsp[mCount-1];
|
||||
}
|
||||
|
||||
mVerticesp[mCount] = mVerticesp[mCount-1];
|
||||
if (mCount > 0) // ND: Guard against crashes if mCount is zero, yes it can happen
|
||||
mVerticesp[mCount] = mVerticesp[mCount-1];
|
||||
|
||||
mPrimitiveReset = false;
|
||||
}
|
||||
@@ -2520,17 +2521,20 @@ void LLRender::vertexBatchPreTransformed(LLVector4a* verts, LLVector2* uvs, S32
|
||||
mTexcoordsp[mCount] = mTexcoordsp[mCount - 1];
|
||||
}
|
||||
|
||||
mVerticesp.copyArray(mCount, verts, vert_count);
|
||||
mTexcoordsp.copyArray(mCount, uvs, vert_count);
|
||||
|
||||
for (S32 i = 0; i < vert_count; i++)
|
||||
{
|
||||
mVerticesp[mCount] = verts[i];
|
||||
mTexcoordsp[mCount] = uvs[i];
|
||||
|
||||
mCount++;
|
||||
mColorsp[mCount] = mColorsp[mCount-1];
|
||||
}
|
||||
|
||||
mVerticesp[mCount] = mVerticesp[mCount-1];
|
||||
mTexcoordsp[mCount] = mTexcoordsp[mCount-1];
|
||||
|
||||
if (mCount > 0)
|
||||
{
|
||||
mVerticesp[mCount] = mVerticesp[mCount - 1];
|
||||
mTexcoordsp[mCount] = mTexcoordsp[mCount - 1];
|
||||
}
|
||||
|
||||
mPrimitiveReset = false;
|
||||
}
|
||||
@@ -2564,9 +2568,12 @@ void LLRender::vertexBatchPreTransformed(LLVector4a* verts, LLVector2* uvs, LLCo
|
||||
mColorsp.copyArray(mCount, colors, vert_count);
|
||||
mCount += vert_count;
|
||||
|
||||
mVerticesp[mCount] = mVerticesp[mCount-1];
|
||||
mTexcoordsp[mCount] = mTexcoordsp[mCount-1];
|
||||
mColorsp[mCount] = mColorsp[mCount-1];
|
||||
if (mCount > 0)
|
||||
{
|
||||
mVerticesp[mCount] = mVerticesp[mCount - 1];
|
||||
mTexcoordsp[mCount] = mTexcoordsp[mCount - 1];
|
||||
mColorsp[mCount] = mColorsp[mCount - 1];
|
||||
}
|
||||
|
||||
mPrimitiveReset = false;
|
||||
}
|
||||
|
||||
@@ -1197,6 +1197,10 @@ void LLVertexBuffer::genBuffer(U32 size)
|
||||
{
|
||||
mMappedData = sDynamicVBOPool.allocate(mGLBuffer, mSize);
|
||||
}
|
||||
if ((sDisableVBOMapping || mUsage != GL_DYNAMIC_DRAW_ARB) && !mMappedData)
|
||||
{
|
||||
LL_ERRS() << "mMappedData allocation failedd" << LL_ENDL;
|
||||
}
|
||||
|
||||
sGLCount++;
|
||||
}
|
||||
@@ -1213,6 +1217,10 @@ void LLVertexBuffer::genIndices(U32 size)
|
||||
{
|
||||
mMappedIndexData = sDynamicIBOPool.allocate(mGLIndices, mIndicesSize);
|
||||
}
|
||||
if ((sDisableVBOMapping || mUsage != GL_DYNAMIC_DRAW_ARB) && !mMappedIndexData)
|
||||
{
|
||||
LL_ERRS() << "mMappedIndexData allocation failedd" << LL_ENDL;
|
||||
}
|
||||
|
||||
sGLCount++;
|
||||
}
|
||||
@@ -1848,6 +1856,7 @@ volatile U8* LLVertexBuffer::mapIndexBuffer(S32 index, S32 count, bool map_range
|
||||
LL_ERRS() << "Attempted to map a specific range of a buffer that was already mapped." << LL_ENDL;
|
||||
}
|
||||
|
||||
bool was_locked = mIndexLocked;
|
||||
if (!mIndexLocked)
|
||||
{
|
||||
mIndexLocked = true;
|
||||
@@ -1942,6 +1951,10 @@ volatile U8* LLVertexBuffer::mapIndexBuffer(S32 index, S32 count, bool map_range
|
||||
|
||||
LL_ERRS() << "glMapBuffer returned NULL (no index data)" << LL_ENDL;
|
||||
}
|
||||
else if (was_locked)
|
||||
{
|
||||
LL_ERRS() << "mIndexLocked was true but no Index data allocated" << LL_ENDL;
|
||||
}
|
||||
else
|
||||
{
|
||||
LL_ERRS() << "memory allocation for Index data failed. " << LL_ENDL;
|
||||
|
||||
@@ -2475,7 +2475,7 @@ BOOL LLLineEditor::evaluateFloat()
|
||||
else
|
||||
{
|
||||
// Replace the expression with the result
|
||||
std::string result_str = llformat("%f", result);
|
||||
std::string result_str = fmt::to_string(result);
|
||||
setText(result_str);
|
||||
selectAll();
|
||||
}
|
||||
|
||||
@@ -74,8 +74,9 @@ private:
|
||||
bool historyHandler(const LLSD& payload)
|
||||
{
|
||||
// we ignore "load" messages, but rewrite the persistence file on any other
|
||||
// onDelete handes "delete" message, so skip that too.
|
||||
std::string sigtype = payload["sigtype"];
|
||||
if (sigtype != "load")
|
||||
if (sigtype != "load" && sigtype != "delete")
|
||||
{
|
||||
savePersistentNotifications();
|
||||
}
|
||||
@@ -85,11 +86,15 @@ private:
|
||||
// The history channel gets all notifications except those that have been cancelled
|
||||
static bool historyFilter(LLNotificationPtr pNotification)
|
||||
{
|
||||
return !pNotification->isCancelled();
|
||||
return pNotification->isPersistent() && !pNotification->isCancelled() && !pNotification->isRespondedTo() && !pNotification->isExpired();
|
||||
}
|
||||
|
||||
void savePersistentNotifications()
|
||||
{
|
||||
if (mLoading)
|
||||
{
|
||||
return;
|
||||
}
|
||||
LL_INFOS() << "Saving open notifications to " << mFileName << LL_ENDL;
|
||||
|
||||
llofstream notify_file(mFileName.c_str());
|
||||
@@ -104,6 +109,9 @@ private:
|
||||
LLSD& data = output["data"];
|
||||
|
||||
AILOCK_mItems;
|
||||
|
||||
static LLCachedControl<S32> maxPersistentNotificaitons("MaxPersistentNotifications");
|
||||
|
||||
for (LLNotificationSet::iterator it = mItems.begin(); it != mItems.end(); ++it)
|
||||
{
|
||||
if (!LLNotificationTemplates::instance().templateExists((*it)->getName())) continue;
|
||||
@@ -111,7 +119,15 @@ private:
|
||||
// only store notifications flagged as persisting
|
||||
LLNotificationTemplatePtr templatep = LLNotificationTemplates::instance().getTemplate((*it)->getName());
|
||||
if (!templatep->mPersist) continue;
|
||||
if ((*it)->isCancelled() || (*it)->isExpired() || (*it)->isRespondedTo()) continue;
|
||||
|
||||
if (data.size() >= maxPersistentNotificaitons)
|
||||
{
|
||||
LL_WARNS() << "Too many persistent notifications."
|
||||
<< " Saved " << maxPersistentNotificaitons << " of " << mItems.size()
|
||||
<< " persistent notifications." << LL_ENDL;
|
||||
break;
|
||||
}
|
||||
data.append((*it)->asLLSD());
|
||||
}
|
||||
|
||||
@@ -121,53 +137,75 @@ private:
|
||||
|
||||
void loadPersistentNotifications()
|
||||
{
|
||||
if (mLoading)
|
||||
{
|
||||
return;
|
||||
}
|
||||
mLoading = true;
|
||||
LL_INFOS() << "Loading open notifications from " << mFileName << LL_ENDL;
|
||||
|
||||
llifstream notify_file(mFileName.c_str());
|
||||
if (!notify_file.is_open())
|
||||
while (true)
|
||||
{
|
||||
LL_WARNS() << "Failed to open " << mFileName << LL_ENDL;
|
||||
return;
|
||||
}
|
||||
llifstream notify_file(mFileName.c_str());
|
||||
if (!notify_file.is_open())
|
||||
{
|
||||
LL_WARNS() << "Failed to open " << mFileName << LL_ENDL;
|
||||
break;
|
||||
}
|
||||
|
||||
LLSD input;
|
||||
LLPointer<LLSDParser> parser = new LLSDXMLParser();
|
||||
if (parser->parse(notify_file, input, LLSDSerialize::SIZE_UNLIMITED) < 0)
|
||||
{
|
||||
LL_WARNS() << "Failed to parse open notifications" << LL_ENDL;
|
||||
return;
|
||||
}
|
||||
LLSD input;
|
||||
LLPointer<LLSDParser> parser = new LLSDXMLParser();
|
||||
if (parser->parse(notify_file, input, LLSDSerialize::SIZE_UNLIMITED) < 0)
|
||||
{
|
||||
LL_WARNS() << "Failed to parse open notifications" << LL_ENDL;
|
||||
break;
|
||||
}
|
||||
|
||||
if (input.isUndefined()) return;
|
||||
std::string version = input["version"];
|
||||
if (version != NOTIFICATION_PERSIST_VERSION)
|
||||
{
|
||||
LL_WARNS() << "Bad open notifications version: " << version << LL_ENDL;
|
||||
return;
|
||||
}
|
||||
LLSD& data = input["data"];
|
||||
if (data.isUndefined()) return;
|
||||
if (input.isUndefined()) return;
|
||||
std::string version = input["version"];
|
||||
if (version != NOTIFICATION_PERSIST_VERSION)
|
||||
{
|
||||
LL_WARNS() << "Bad open notifications version: " << version << LL_ENDL;
|
||||
break;
|
||||
}
|
||||
LLSD& data = input["data"];
|
||||
if (data.isUndefined()) break;
|
||||
|
||||
LLNotifications& instance = LLNotifications::instance();
|
||||
for (LLSD::array_const_iterator notification_it = data.beginArray();
|
||||
notification_it != data.endArray();
|
||||
++notification_it)
|
||||
{
|
||||
instance.add(LLNotificationPtr(new LLNotification(*notification_it)));
|
||||
S32 processed_notifications = 0;
|
||||
static LLCachedControl<S32> maxPersistentNotificaitons("MaxPersistentNotifications");
|
||||
|
||||
LLNotifications& instance = LLNotifications::instance();
|
||||
for (LLSD::array_const_iterator notification_it = data.beginArray();
|
||||
notification_it != data.endArray();
|
||||
++notification_it)
|
||||
{
|
||||
if (processed_notifications++ >= maxPersistentNotificaitons)
|
||||
{
|
||||
LL_WARNS() << "Too many persistent notifications."
|
||||
<< " Processed " << maxPersistentNotificaitons << " of " << data.size() << " persistent notifications." << LL_ENDL;
|
||||
break;
|
||||
}
|
||||
instance.add(LLNotificationPtr(new LLNotification(*notification_it)));
|
||||
|
||||
}
|
||||
break;
|
||||
}
|
||||
mLoading = false;
|
||||
savePersistentNotifications();
|
||||
}
|
||||
|
||||
//virtual
|
||||
void onDelete(LLNotificationPtr pNotification)
|
||||
{
|
||||
// we want to keep deleted notifications in our log
|
||||
AILOCK_mItems;
|
||||
mItems.insert(pNotification);
|
||||
|
||||
return;
|
||||
{
|
||||
AILOCK_mItems;
|
||||
mItems.erase(pNotification); // Delete immediately.
|
||||
}
|
||||
savePersistentNotifications();
|
||||
}
|
||||
|
||||
private:
|
||||
bool mLoading = false;
|
||||
std::string mFileName;
|
||||
};
|
||||
|
||||
@@ -277,6 +315,7 @@ LLNotificationForm::LLNotificationForm(const std::string& name, const LLXMLNodeP
|
||||
}
|
||||
|
||||
LLNotificationForm::LLNotificationForm(const LLSD& sd)
|
||||
: mIgnore(IGNORE_NO)
|
||||
{
|
||||
if (sd.isArray())
|
||||
{
|
||||
@@ -904,9 +943,9 @@ bool LLNotificationChannelBase::updateItem(const LLSD& payload, LLNotificationPt
|
||||
// if we have it in our list, pass on the delete, then delete it, else do nothing
|
||||
if (wasFound)
|
||||
{
|
||||
onDelete(pNotification);
|
||||
abortProcessing = mChanged(payload);
|
||||
mItems.erase(pNotification);
|
||||
onDelete(pNotification);
|
||||
}
|
||||
}
|
||||
return abortProcessing;
|
||||
@@ -1146,13 +1185,6 @@ void LLNotifications::createDefaultChannels()
|
||||
LLNotificationChannel::buildChannel("Visible", "Ignore",
|
||||
&LLNotificationFilters::includeEverything);
|
||||
|
||||
// create special history channel
|
||||
//std::string notifications_log_file = gDirUtilp->getExpandedFilename ( LL_PATH_PER_SL_ACCOUNT, "open_notifications.xml" );
|
||||
// use ^^^ when done debugging notifications serialization
|
||||
std::string notifications_log_file = gDirUtilp->getExpandedFilename ( LL_PATH_USER_SETTINGS, "open_notifications.xml" );
|
||||
// this isn't a leak, don't worry about the empty "new"
|
||||
new LLNotificationHistoryChannel(notifications_log_file);
|
||||
|
||||
// connect action methods to these channels
|
||||
LLNotifications::instance().getChannel("Expiration")->
|
||||
connectChanged(boost::bind(&LLNotifications::expirationHandler, this, _1));
|
||||
@@ -1164,6 +1196,14 @@ void LLNotifications::createDefaultChannels()
|
||||
connectFailedFilter(&handleIgnoredNotification);
|
||||
}
|
||||
|
||||
void LLNotifications::onLoginCompleted()
|
||||
{
|
||||
// create special history channel
|
||||
std::string notifications_log_file = gDirUtilp->getExpandedFilename ( LL_PATH_PER_SL_ACCOUNT, "singu_open_notifications_" + gHippoGridManager->getCurrentGrid()->getGridName() + ".xml");
|
||||
// this isn't a leak, don't worry about the empty "new"
|
||||
new LLNotificationHistoryChannel(notifications_log_file );
|
||||
}
|
||||
|
||||
static std::string sStringSkipNextTime("Skip this dialog next time");
|
||||
static std::string sStringAlwaysChoose("Always choose this option");
|
||||
|
||||
|
||||
@@ -796,6 +796,7 @@ public:
|
||||
// OK to call more than once because it will reload
|
||||
bool loadNotifications();
|
||||
void createDefaultChannels();
|
||||
void onLoginCompleted();
|
||||
|
||||
// we provide a collection of simple add notification functions so that it's reasonable to create notifications in one line
|
||||
LLNotificationPtr add(const std::string& name,
|
||||
|
||||
@@ -414,7 +414,7 @@ void LLResMgr::getIntegerString( std::string& output, S32 input ) const
|
||||
{
|
||||
if (fraction == remaining_count)
|
||||
{
|
||||
fraction_string = llformat("%d", fraction);
|
||||
fraction_string = fmt::to_string(fraction);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
@@ -3201,7 +3201,7 @@ LLScrollListItem* LLScrollListCtrl::addRow(LLScrollListItem *new_item, const LLS
|
||||
// empty columns strings index by ordinal
|
||||
if (column.empty())
|
||||
{
|
||||
column = llformat("%d", col_index);
|
||||
column = fmt::to_string(col_index);
|
||||
}
|
||||
|
||||
LLScrollListColumn* columnp = getColumn(column);
|
||||
|
||||
@@ -45,12 +45,13 @@
|
||||
|
||||
#if LL_GTK
|
||||
extern "C" {
|
||||
# include <gtk/gtk.h>
|
||||
#include <gtk/gtk.h>
|
||||
#include <gdk/gdk.h>
|
||||
#if GTK_CHECK_VERSION(2, 24, 0)
|
||||
#include <gdk/gdkx.h>
|
||||
#endif
|
||||
}
|
||||
#include <locale.h>
|
||||
#include <clocale>
|
||||
#endif // LL_GTK
|
||||
|
||||
extern "C" {
|
||||
@@ -1543,7 +1544,7 @@ BOOL LLWindowSDL::SDLReallyCaptureInput(BOOL capture)
|
||||
|
||||
XUngrabPointer(mSDL_Display, CurrentTime);
|
||||
// Make sure the ungrab happens RIGHT NOW.
|
||||
XSync(mSDL_Display, False);
|
||||
XSync(mSDL_Display, FALSE);
|
||||
} else
|
||||
{
|
||||
newmode = SDL_GRAB_QUERY; // neutral
|
||||
@@ -2269,8 +2270,12 @@ S32 OSMessageBoxSDL(const std::string& text, const std::string& caption, U32 typ
|
||||
gWindowImplementation->mSDL_XWindowID != None)
|
||||
{
|
||||
gtk_widget_realize(GTK_WIDGET(win)); // so we can get its gdkwin
|
||||
GdkWindow *gdkwin = gdk_window_foreign_new(gWindowImplementation->mSDL_XWindowID);
|
||||
gdk_window_set_transient_for(GTK_WIDGET(win)->window, gdkwin);
|
||||
#if GTK_CHECK_VERSION(2, 24, 0)
|
||||
GdkWindow* gdkwin = gdk_x11_window_foreign_new_for_display(gdk_display_get_default(), static_cast<Window>(gWindowImplementation->mSDL_XWindowID));
|
||||
#else
|
||||
GdkWindow* gdkwin = gdk_window_foreign_new(static_cast<GdkNativeWindow>(gWindowImplementation->mSDL_XWindowID));
|
||||
#endif
|
||||
gdk_window_set_transient_for(gtk_widget_get_window(GTK_WIDGET(win)), gdkwin);
|
||||
}
|
||||
# endif //LL_X11
|
||||
|
||||
@@ -2384,12 +2389,16 @@ BOOL LLWindowSDL::dialogColorPicker( F32 *r, F32 *g, F32 *b)
|
||||
if (mSDL_XWindowID != None)
|
||||
{
|
||||
gtk_widget_realize(GTK_WIDGET(win)); // so we can get its gdkwin
|
||||
GdkWindow *gdkwin = gdk_window_foreign_new(mSDL_XWindowID);
|
||||
gdk_window_set_transient_for(GTK_WIDGET(win)->window, gdkwin);
|
||||
#if GTK_CHECK_VERSION(2, 24, 0)
|
||||
GdkWindow* gdkwin = gdk_x11_window_foreign_new_for_display(gdk_display_get_default(), static_cast<Window>(mSDL_XWindowID));
|
||||
#else
|
||||
GdkWindow* gdkwin = gdk_window_foreign_new(static_cast<GdkNativeWindow>(mSDL_XWindowID));
|
||||
#endif
|
||||
gdk_window_set_transient_for(gtk_widget_get_window(GTK_WIDGET(win)), gdkwin);
|
||||
}
|
||||
# endif //LL_X11
|
||||
#endif //LL_X11
|
||||
|
||||
GtkColorSelection *colorsel = GTK_COLOR_SELECTION (GTK_COLOR_SELECTION_DIALOG(win)->colorsel);
|
||||
GtkColorSelection *colorsel = GTK_COLOR_SELECTION (gtk_color_selection_dialog_get_color_selection (GTK_COLOR_SELECTION_DIALOG(win)));
|
||||
|
||||
GdkColor color, orig_color;
|
||||
orig_color.pixel = 0;
|
||||
@@ -2415,8 +2424,6 @@ BOOL LLWindowSDL::dialogColorPicker( F32 *r, F32 *g, F32 *b)
|
||||
|
||||
gtk_window_set_modal(GTK_WINDOW(win), TRUE);
|
||||
gtk_widget_show_all(win);
|
||||
// hide the help button - we don't service it.
|
||||
gtk_widget_hide(GTK_COLOR_SELECTION_DIALOG(win)->help_button);
|
||||
gtk_main();
|
||||
|
||||
if (response == GTK_RESPONSE_OK &&
|
||||
@@ -2498,7 +2505,7 @@ void LLWindowSDL::spawnWebBrowser(const std::string& escaped_url, bool async)
|
||||
if (mSDL_Display)
|
||||
{
|
||||
// Just in case - before forking.
|
||||
XSync(mSDL_Display, False);
|
||||
XSync(mSDL_Display, FALSE);
|
||||
}
|
||||
# endif // LL_X11
|
||||
|
||||
@@ -2548,7 +2555,7 @@ void LLWindowSDL::bringToFront()
|
||||
if (mSDL_Display && !mFullscreen)
|
||||
{
|
||||
XRaiseWindow(mSDL_Display, mSDL_XWindowID);
|
||||
XSync(mSDL_Display, False);
|
||||
XSync(mSDL_Display, FALSE);
|
||||
}
|
||||
#endif // LL_X11
|
||||
}
|
||||
|
||||
@@ -1709,7 +1709,7 @@ target_link_libraries(${VIEWER_BINARY_NAME}
|
||||
absl::flat_hash_map
|
||||
absl::node_hash_map
|
||||
nlohmann_json::nlohmann_json
|
||||
${FMT_LIBRARY}
|
||||
fmt::fmt
|
||||
)
|
||||
|
||||
if (LINUX)
|
||||
|
||||
@@ -24,7 +24,6 @@
|
||||
#include "llviewerobjectlist.h"
|
||||
|
||||
#include <time.h>
|
||||
#include <boost/lexical_cast.hpp>
|
||||
|
||||
class NACLAntiSpamQueue
|
||||
{
|
||||
|
||||
@@ -1 +1 @@
|
||||
1.8.7
|
||||
1.8.9
|
||||
|
||||
@@ -10576,6 +10576,17 @@ This should be as low as possible, but too low may break functionality</string>
|
||||
<key>Value</key>
|
||||
<real>1.6</real>
|
||||
</map>
|
||||
<key>MaxPersistentNotifications</key>
|
||||
<map>
|
||||
<key>Comment</key>
|
||||
<string>Maximum amount of persistent notifications</string>
|
||||
<key>Persist</key>
|
||||
<integer>1</integer>
|
||||
<key>Type</key>
|
||||
<string>S32</string>
|
||||
<key>Value</key>
|
||||
<real>250</real>
|
||||
</map>
|
||||
<key>MaxSelectDistance</key>
|
||||
<map>
|
||||
<key>Comment</key>
|
||||
|
||||
@@ -207,6 +207,7 @@ void LLPrefsAscentSys::refreshValues()
|
||||
mDisplayScriptJumps = gSavedSettings.getBOOL("AscentDisplayTotalScriptJumps");
|
||||
mNumScriptDiff = gSavedSettings.getF32("Ascentnumscriptdiff");
|
||||
mReplaceLinks = gSavedSettings.getBOOL("SinguReplaceLinks");
|
||||
mEmergencySeconds = gSavedPerAccountSettings.getU32("EmergencyTeleportSeconds");
|
||||
mLandmark = gSavedPerAccountSettings.getString("EmergencyTeleportLandmark");
|
||||
mLandmarkBackup = gSavedPerAccountSettings.getString("EmergencyTeleportLandmarkBackup");
|
||||
|
||||
@@ -353,6 +354,7 @@ void LLPrefsAscentSys::cancel()
|
||||
gSavedSettings.setBOOL("AscentDisplayTotalScriptJumps", mDisplayScriptJumps);
|
||||
gSavedSettings.setF32("Ascentnumscriptdiff", mNumScriptDiff);
|
||||
gSavedSettings.setBOOL("SinguReplaceLinks", mReplaceLinks);
|
||||
gSavedPerAccountSettings.setU32("EmergencyTeleportSeconds", mEmergencySeconds);
|
||||
gSavedPerAccountSettings.setString("EmergencyTeleportLandmark", mLandmark);
|
||||
gSavedPerAccountSettings.setString("EmergencyTeleportLandmarkBackup", mLandmarkBackup);
|
||||
|
||||
|
||||
@@ -118,6 +118,7 @@ private:
|
||||
bool mDisplayScriptJumps;
|
||||
bool mReplaceLinks;
|
||||
F32 mNumScriptDiff;
|
||||
U32 mEmergencySeconds;
|
||||
std::string mLandmark;
|
||||
std::string mLandmarkBackup;
|
||||
|
||||
|
||||
@@ -163,10 +163,11 @@ Wavefront::Wavefront(LLFace* face, LLPolyMesh* mesh, const LLXform* transform, c
|
||||
if (transform_normals) Transform(normals, transform_normals);
|
||||
|
||||
const U32 pcount = mesh ? mesh->getNumFaces() : (vb->getNumIndices()/3); //indices
|
||||
const U16 offset = face->getIndicesStart(); //indices
|
||||
const U32 offset = face->getIndicesStart(); //indices
|
||||
for (U32 i = 0; i < pcount; ++i)
|
||||
{
|
||||
triangles.push_back(tri(getIndices[i * 3 + offset] + start, getIndices[i * 3 + 1 + offset] + start, getIndices[i * 3 + 2 + offset] + start));
|
||||
const auto off = i * 3 + offset;
|
||||
triangles.push_back(tri(getIndices[off] + start, getIndices[off + 1] + start, getIndices[off + 2] + start));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -174,9 +175,9 @@ void Wavefront::Transform(vert_t& v, const LLXform* x) //recursive
|
||||
{
|
||||
LLMatrix4 m;
|
||||
x->getLocalMat4(m);
|
||||
for (vert_t::iterator iterv = v.begin(); iterv != v.end(); ++iterv)
|
||||
for (auto& i : v)
|
||||
{
|
||||
iterv->first = iterv->first * m;
|
||||
i.first = i.first * m;
|
||||
}
|
||||
|
||||
if (const LLXform* xp = x->getParent()) Transform(v, xp);
|
||||
@@ -186,9 +187,9 @@ void Wavefront::Transform(vec3_t& v, const LLXform* x) //recursive
|
||||
{
|
||||
LLMatrix4 m;
|
||||
x->getLocalMat4(m);
|
||||
for (vec3_t::iterator iterv = v.begin(); iterv != v.end(); ++iterv)
|
||||
for (auto& i : v)
|
||||
{
|
||||
*iterv = *iterv * m;
|
||||
i = i * m;
|
||||
}
|
||||
|
||||
if (const LLXform* xp = x->getParent()) Transform(v, xp);
|
||||
@@ -252,9 +253,9 @@ namespace
|
||||
asset_id_matches);
|
||||
|
||||
// See if any of the inventory items matching this sculpt id are exportable
|
||||
for (U32 i = 0; i < items.size(); i++)
|
||||
for (const auto& item : items)
|
||||
{
|
||||
const LLPermissions item_permissions = items[i]->getPermissions();
|
||||
const LLPermissions item_permissions = item->getPermissions();
|
||||
if (item_permissions.allowExportBy(gAgentID, LFSimFeatureHandler::instance().exportPolicy()))
|
||||
{
|
||||
return true;
|
||||
@@ -269,9 +270,9 @@ namespace
|
||||
}
|
||||
}
|
||||
|
||||
class LFSaveSelectedObjects : public view_listener_t
|
||||
class LFSaveSelectedObjects final : public view_listener_t
|
||||
{
|
||||
bool handleEvent(LLPointer<LLOldEvents::LLEvent> event, const LLSD& userdata)
|
||||
bool handleEvent(LLPointer<LLOldEvents::LLEvent> event, const LLSD& userdata) override
|
||||
{
|
||||
if (LLObjectSelectionHandle selection = LLSelectMgr::getInstance()->getSelection())
|
||||
{
|
||||
@@ -288,10 +289,10 @@ namespace
|
||||
S32 included = 0;
|
||||
for (LLObjectSelection::iterator iter = selection->begin(); iter != selection->end(); ++iter)
|
||||
{
|
||||
total++;
|
||||
++total;
|
||||
LLSelectNode* node = *iter;
|
||||
if (!can_export_node(node)) continue;
|
||||
included++;
|
||||
++included;
|
||||
wfsaver->Add(node->getObject());
|
||||
}
|
||||
if (wfsaver->obj_v.empty())
|
||||
@@ -322,12 +323,12 @@ void WavefrontSaver::Add(const LLVOAvatar* av_vo) //adds attachments, too!
|
||||
{
|
||||
offset = -av_vo->getRenderPosition();
|
||||
avatar_joint_list_t vjv = av_vo->mMeshLOD;
|
||||
for (avatar_joint_list_t::const_iterator itervj = vjv.begin(); itervj != vjv.end(); ++itervj)
|
||||
for (const auto& itervj : vjv)
|
||||
{
|
||||
const LLViewerJoint* vj = dynamic_cast<LLViewerJoint*>(*itervj);
|
||||
const auto* vj = dynamic_cast<const LLViewerJoint*>(itervj);
|
||||
if (!vj || vj->mMeshParts.empty()) continue;
|
||||
|
||||
LLViewerJointMesh* vjm = dynamic_cast<LLViewerJointMesh*>(vj->mMeshParts[0]); //highest LOD
|
||||
auto* vjm = dynamic_cast<LLViewerJointMesh*>(vj->mMeshParts[0]); //highest LOD
|
||||
if (!vjm) continue;
|
||||
|
||||
vjm->updateJointGeometry();
|
||||
@@ -355,21 +356,19 @@ void WavefrontSaver::Add(const LLVOAvatar* av_vo) //adds attachments, too!
|
||||
Add(Wavefront(face, pm, NULL, &normfix));
|
||||
}
|
||||
|
||||
for (LLVOAvatar::attachment_map_t::const_iterator iter = av_vo->mAttachmentPoints.begin(); iter != av_vo->mAttachmentPoints.end(); ++iter)
|
||||
for (const auto& ap : av_vo->mAttachmentPoints)
|
||||
{
|
||||
LLViewerJointAttachment* ja = iter->second;
|
||||
LLViewerJointAttachment* ja = ap.second;
|
||||
if (!ja) continue;
|
||||
|
||||
for (LLViewerJointAttachment::attachedobjs_vec_t::iterator itero = ja->mAttachedObjects.begin(); itero != ja->mAttachedObjects.end(); ++itero)
|
||||
for (const auto& o : ja->mAttachedObjects)
|
||||
{
|
||||
LLViewerObject* o = *itero;
|
||||
if (!o) continue;
|
||||
|
||||
std::vector<LLViewerObject*> prims;
|
||||
o->addThisAndAllChildren(prims);
|
||||
for (std::vector<LLViewerObject* >::iterator iterc = prims.begin(); iterc != prims.end(); ++iterc)
|
||||
for (const auto& c : prims)
|
||||
{
|
||||
const LLViewerObject* c = *iterc;
|
||||
if (!c) continue;
|
||||
if (LLSelectNode* n = LLSelectMgr::getInstance()->getSelection()->findNode(const_cast<LLViewerObject*>(c)))
|
||||
{
|
||||
@@ -400,9 +399,9 @@ void WavefrontSaver::Add(const LLVOAvatar* av_vo) //adds attachments, too!
|
||||
}
|
||||
namespace
|
||||
{
|
||||
class LFSaveSelectedAvatar : public view_listener_t
|
||||
class LFSaveSelectedAvatar final : public view_listener_t
|
||||
{
|
||||
bool handleEvent(LLPointer<LLOldEvents::LLEvent> event, const LLSD& userdata)
|
||||
bool handleEvent(LLPointer<LLOldEvents::LLEvent> event, const LLSD& userdata) override
|
||||
{
|
||||
if (const LLVOAvatar* avatar = find_avatar_from_object(LLSelectMgr::getInstance()->getSelection()->getPrimaryObject()))
|
||||
{
|
||||
@@ -446,49 +445,48 @@ bool WavefrontSaver::saveFile(LLFILE* fp)
|
||||
|
||||
int num = 0;
|
||||
int index = 0;
|
||||
for (std::vector<Wavefront>::iterator w_iter = obj_v.begin(); w_iter != obj_v.end(); ++w_iter)
|
||||
for (const auto& obj : obj_v)
|
||||
{
|
||||
int count = 0;
|
||||
|
||||
std::string name = (*w_iter).name;
|
||||
std::string name = obj.name;
|
||||
if (name.empty()) name = llformat("%d", num++);
|
||||
|
||||
vert_t vertices = (*w_iter).vertices;
|
||||
vec3_t normals = (*w_iter).normals;
|
||||
tri_t triangles = (*w_iter).triangles;
|
||||
auto& vertices = obj.vertices;
|
||||
auto& normals = obj.normals;
|
||||
auto& triangles = obj.triangles;
|
||||
|
||||
//Write Object
|
||||
write_or_bust(fp, "o " + name + "\n");
|
||||
write_or_bust(fp, "o " + name + '\n');
|
||||
|
||||
//Write vertices; swap axes if necessary
|
||||
static const LLCachedControl<bool> swapYZ("OBJExportSwapYZ", false);
|
||||
const double xm = swapYZ ? -1.0 : 1.0;
|
||||
const int y = swapYZ ? 2 : 1;
|
||||
const int z = swapYZ ? 1 : 2;
|
||||
for (vert_t::iterator v_iter = vertices.begin(); v_iter != vertices.end(); ++v_iter)
|
||||
for (const auto& vert : vertices)
|
||||
{
|
||||
++count;
|
||||
const LLVector3 v = v_iter->first + offset;
|
||||
const LLVector3 v = vert.first + offset;
|
||||
write_or_bust(fp, llformat("v %f %f %f\n",v[0] * xm, v[y], v[z]));
|
||||
}
|
||||
|
||||
for (vec3_t::iterator n_iter = normals.begin(); n_iter != normals.end(); ++n_iter)
|
||||
for (const auto& n : normals)
|
||||
{
|
||||
const LLVector3 n = *n_iter;
|
||||
write_or_bust(fp, llformat("vn %f %f %f\n",n[0] * xm, n[y], n[z]));
|
||||
}
|
||||
|
||||
for (vert_t::iterator v_iter = vertices.begin(); v_iter != vertices.end(); ++v_iter)
|
||||
for (const auto& vert : vertices)
|
||||
{
|
||||
write_or_bust(fp, llformat("vt %f %f\n", v_iter->second[0], v_iter->second[1]));
|
||||
write_or_bust(fp, llformat("vt %f %f\n", vert.second[0], vert.second[1]));
|
||||
}
|
||||
|
||||
//Write triangles
|
||||
for (tri_t::iterator t_iter = triangles.begin(); t_iter != triangles.end(); ++t_iter)
|
||||
for (const auto& triangle : triangles)
|
||||
{
|
||||
const int f1 = t_iter->v0 + index + 1;
|
||||
const int f2 = t_iter->v1 + index + 1;
|
||||
const int f3 = t_iter->v2 + index + 1;
|
||||
const int f1 = triangle.v0 + index + 1;
|
||||
const int f2 = triangle.v1 + index + 1;
|
||||
const int f3 = triangle.v2 + index + 1;
|
||||
write_or_bust(fp, llformat("f %d/%d/%d %d/%d/%d %d/%d/%d\n",
|
||||
f1,f1,f1,f2,f2,f2,f3,f3,f3));
|
||||
}
|
||||
|
||||
@@ -32,16 +32,18 @@
|
||||
|
||||
// library includes
|
||||
#include "aifilepicker.h"
|
||||
#include "llavatarnamecache.h"
|
||||
#include "llnotificationsutil.h"
|
||||
|
||||
// newview includes
|
||||
#include "lfsimfeaturehandler.h"
|
||||
#include "llface.h"
|
||||
#include "llvovolume.h"
|
||||
#include "llviewerinventory.h"
|
||||
#include "llinventorymodel.h"
|
||||
#include "llinventoryfunctions.h"
|
||||
#include "llface.h"
|
||||
#include "llversioninfo.h"
|
||||
#include "llviewerinventory.h"
|
||||
#include "llviewertexturelist.h"
|
||||
#include "llvovolume.h"
|
||||
|
||||
// menu includes
|
||||
#include "llevent.h"
|
||||
@@ -74,11 +76,11 @@ typedef LLMemberListener<LLView> view_listener_t;
|
||||
|
||||
namespace DAEExportUtil
|
||||
{
|
||||
static LLUUID LL_TEXTURE_PLYWOOD = LLUUID("89556747-24cb-43ed-920b-47caed15465f");
|
||||
static LLUUID LL_TEXTURE_BLANK = LLUUID("5748decc-f629-461c-9a36-a35a221fe21f");
|
||||
static LLUUID LL_TEXTURE_INVISIBLE = LLUUID("38b86f85-2575-52a9-a531-23108d8da837");
|
||||
static LLUUID LL_TEXTURE_TRANSPARENT = LLUUID("8dcd4a48-2d37-4909-9f78-f7a9eb4ef903");
|
||||
static LLUUID LL_TEXTURE_MEDIA = LLUUID("8b5fec65-8d8d-9dc5-cda8-8fdf2716e361");
|
||||
const auto LL_TEXTURE_PLYWOOD = LLUUID("89556747-24cb-43ed-920b-47caed15465f");
|
||||
const auto LL_TEXTURE_BLANK = LLUUID("5748decc-f629-461c-9a36-a35a221fe21f");
|
||||
const auto LL_TEXTURE_INVISIBLE = LLUUID("38b86f85-2575-52a9-a531-23108d8da837");
|
||||
const auto LL_TEXTURE_TRANSPARENT = LLUUID("8dcd4a48-2d37-4909-9f78-f7a9eb4ef903");
|
||||
const auto LL_TEXTURE_MEDIA = LLUUID("8b5fec65-8d8d-9dc5-cda8-8fdf2716e361");
|
||||
|
||||
enum image_format_type
|
||||
{
|
||||
@@ -105,23 +107,17 @@ namespace DAEExportUtil
|
||||
|
||||
// See if any of the inventory items matching this texture id are exportable
|
||||
ExportPolicy policy = LFSimFeatureHandler::instance().exportPolicy();
|
||||
for (size_t i = 0; i < items.size(); i++)
|
||||
for (const auto& item : items)
|
||||
{
|
||||
const LLPermissions item_permissions = items[i]->getPermissions();
|
||||
const LLPermissions item_permissions = item->getPermissions();
|
||||
if (item_permissions.allowExportBy(gAgentID, policy))
|
||||
{
|
||||
if (name != NULL)
|
||||
{
|
||||
(*name) = items[i]->getName();
|
||||
}
|
||||
if (name) *name = item->getName();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
if (name != NULL)
|
||||
{
|
||||
(*name) = id.getString();
|
||||
}
|
||||
if (name) *name = id.getString();
|
||||
|
||||
return (policy & ep_full_perm) == ep_full_perm;
|
||||
}
|
||||
@@ -206,7 +202,7 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
BOOL postBuild()
|
||||
BOOL postBuild() override
|
||||
{
|
||||
mFileName = getChildView("file name editor");
|
||||
mExportBtn = getChildView("export button");
|
||||
@@ -306,14 +302,9 @@ public:
|
||||
S32 getNumExportableTextures()
|
||||
{
|
||||
S32 res = 0;
|
||||
|
||||
for (DAESaver::string_list_t::const_iterator t = mSaver.mTextureNames.begin(); t != mSaver.mTextureNames.end(); ++t)
|
||||
for (const auto& name : mSaver.mTextureNames)
|
||||
{
|
||||
std::string name = *t;
|
||||
if (!name.empty())
|
||||
{
|
||||
++res;
|
||||
}
|
||||
if (!name.empty()) ++res;
|
||||
}
|
||||
|
||||
return res;
|
||||
@@ -365,7 +356,7 @@ public:
|
||||
gIdleCallbacks.addFunction(saveTexturesWorker, this);
|
||||
}
|
||||
|
||||
class CacheReadResponder : public LLTextureCache::ReadResponder
|
||||
class CacheReadResponder final : public LLTextureCache::ReadResponder
|
||||
{
|
||||
private:
|
||||
LLPointer<LLImageFormatted> mFormattedImage;
|
||||
@@ -413,7 +404,7 @@ public:
|
||||
mImageLocal = imagelocal;
|
||||
}
|
||||
|
||||
virtual void completed(bool success)
|
||||
void completed(bool success) override
|
||||
{
|
||||
if (success && mFormattedImage.notNull() && mImageSize > 0)
|
||||
{
|
||||
@@ -546,10 +537,8 @@ void DAESaver::updateTextureInfo()
|
||||
{
|
||||
LLTextureEntry* te = obj->getTE(face_num);
|
||||
const LLUUID id = te->getID();
|
||||
if (std::find(mTextures.begin(), mTextures.end(), id) != mTextures.end())
|
||||
{
|
||||
continue;
|
||||
}
|
||||
if (std::find(mTextures.begin(), mTextures.end(), id) != mTextures.end()) continue;
|
||||
|
||||
mTextures.push_back(id);
|
||||
std::string name;
|
||||
if (id != DAEExportUtil::LL_TEXTURE_BLANK && DAEExportUtil::canExportTexture(id, &name))
|
||||
@@ -566,7 +555,6 @@ void DAESaver::updateTextureInfo()
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
class v4adapt
|
||||
{
|
||||
private:
|
||||
@@ -579,7 +567,7 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
void DAESaver::addSource(daeElement* mesh, const char* src_id, std::string params, const std::vector<F32> &vals)
|
||||
void DAESaver::addSource(daeElement* mesh, const char* src_id, const std::string& params, const std::vector<F32> &vals)
|
||||
{
|
||||
daeElement* source = mesh->add("source");
|
||||
source->setAttribute("id", src_id);
|
||||
@@ -588,9 +576,9 @@ void DAESaver::addSource(daeElement* mesh, const char* src_id, std::string param
|
||||
src_array->setAttribute("id", llformat("%s-%s", src_id, "array").c_str());
|
||||
src_array->setAttribute("count", llformat("%d", vals.size()).c_str());
|
||||
|
||||
for (U32 i = 0; i < vals.size(); i++)
|
||||
for (const auto& val : vals)
|
||||
{
|
||||
((domFloat_array*)src_array)->getValue().append(vals[i]);
|
||||
static_cast<domFloat_array*>(src_array)->getValue().append(val);
|
||||
}
|
||||
|
||||
domAccessor* acc = daeSafeCast<domAccessor>(source->add("technique_common accessor"));
|
||||
@@ -598,10 +586,10 @@ void DAESaver::addSource(daeElement* mesh, const char* src_id, std::string param
|
||||
acc->setCount(vals.size() / params.size());
|
||||
acc->setStride(params.size());
|
||||
|
||||
for (std::string::iterator p_iter = params.begin(); p_iter != params.end(); ++p_iter)
|
||||
for (const auto& param : params)
|
||||
{
|
||||
domElement* pX = acc->add("param");
|
||||
pX->setAttribute("name", llformat("%c", *p_iter).c_str());
|
||||
pX->setAttribute("name", (LLStringUtil::null + param).c_str());
|
||||
pX->setAttribute("type", "float");
|
||||
}
|
||||
}
|
||||
@@ -650,7 +638,7 @@ void DAESaver::addPolygons(daeElement* mesh, const char* geomID, const char* mat
|
||||
{
|
||||
for (S32 i = 0; i < face->mNumIndices; i++)
|
||||
{
|
||||
U16 index = index_offset + face->mIndices[i];
|
||||
U32 index = index_offset + face->mIndices[i];
|
||||
(p->getValue()).append(index);
|
||||
if (i % 3 == 0)
|
||||
{
|
||||
@@ -710,11 +698,21 @@ void DAESaver::transformTexCoord(S32 num_vert, LLVector2* coord, LLVector3* posi
|
||||
|
||||
bool DAESaver::saveDAE(std::string filename)
|
||||
{
|
||||
// Collada expects file and folder names to be escaped
|
||||
// Note: cdom::nativePathToUri()
|
||||
// Same as in LLDAELoader::OpenFile()
|
||||
const char* allowed =
|
||||
"ABCDEFGHIJKLMNOPQRSTUVWXYZ"
|
||||
"abcdefghijklmnopqrstuvwxyz"
|
||||
"0123456789"
|
||||
"%-._~:\"|\\/";
|
||||
std::string uri_filename = LLURI::escape(filename, allowed);
|
||||
|
||||
mAllMaterials.clear();
|
||||
mTotalNumMaterials = 0;
|
||||
DAE dae;
|
||||
// First set the filename to save
|
||||
daeElement* root = dae.add(filename);
|
||||
daeElement* root = dae.add(uri_filename);
|
||||
|
||||
// Obligatory elements in header
|
||||
daeElement* asset = root->add("asset");
|
||||
@@ -734,9 +732,13 @@ bool DAESaver::saveDAE(std::string filename)
|
||||
up_axis->setCharData("Z_UP");
|
||||
|
||||
// File creator
|
||||
std::string author;
|
||||
if (!LLAvatarNameCache::getNSName(gAgentID, author))
|
||||
author = "Unknown";
|
||||
|
||||
daeElement* contributor = asset->add("contributor");
|
||||
contributor->add("author")->setCharData(LLAppViewer::instance()->getSecondLifeTitle() + " User");
|
||||
contributor->add("authoring_tool")->setCharData(LLAppViewer::instance()->getSecondLifeTitle() + " Collada Export");
|
||||
contributor->add("author")->setCharData(author);
|
||||
contributor->add("authoring_tool")->setCharData(LLVersionInfo::getChannelAndVersion() + " Collada Export");
|
||||
|
||||
daeElement* images = root->add("library_images");
|
||||
daeElement* geomLib = root->add("library_geometries");
|
||||
@@ -825,7 +827,6 @@ bool DAESaver::saveDAE(std::string filename)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
addSource(mesh, llformat("%s-%s", geomID, "positions").c_str(), "XYZ", position_data);
|
||||
addSource(mesh, llformat("%s-%s", geomID, "normals").c_str(), "XYZ", normal_data);
|
||||
addSource(mesh, llformat("%s-%s", geomID, "map0").c_str(), "ST", uv_data);
|
||||
@@ -845,12 +846,11 @@ bool DAESaver::saveDAE(std::string filename)
|
||||
// Add triangles
|
||||
if (gSavedSettings.getBOOL("DAEExportConsolidateMaterials"))
|
||||
{
|
||||
for (U32 objMaterial = 0; objMaterial < objMaterials.size(); objMaterial++)
|
||||
for (const auto& objMaterial : objMaterials)
|
||||
{
|
||||
int_list_t faces;
|
||||
getFacesWithMaterial(obj, objMaterials[objMaterial], &faces);
|
||||
std::string matName = objMaterials[objMaterial].name;
|
||||
addPolygons(mesh, geomID, (matName + "-material").c_str(), obj, &faces);
|
||||
getFacesWithMaterial(obj, objMaterial, &faces);
|
||||
addPolygons(mesh, geomID, (objMaterial.name + "-material").c_str(), obj, &faces);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -888,12 +888,12 @@ bool DAESaver::saveDAE(std::string filename)
|
||||
|
||||
// Bind materials
|
||||
daeElement* tq = nodeGeometry->add("bind_material technique_common");
|
||||
for (U32 objMaterial = 0; objMaterial < objMaterials.size(); objMaterial++)
|
||||
for (const auto& objMaterial : objMaterials)
|
||||
{
|
||||
std::string matName = objMaterials[objMaterial].name;
|
||||
daeElement* instanceMaterial = tq->add("instance_material");
|
||||
instanceMaterial->setAttribute("symbol", (matName + "-material").c_str());
|
||||
instanceMaterial->setAttribute("target", ("#" + matName + "-material").c_str());
|
||||
std::string matName = objMaterial.name + "-material";
|
||||
instanceMaterial->setAttribute("symbol", matName.c_str());
|
||||
instanceMaterial->setAttribute("target", ('#' + matName).c_str());
|
||||
}
|
||||
|
||||
nodeGeometry->setAttribute("url", llformat("#%s-%s", geomID, "mesh").c_str());
|
||||
@@ -904,12 +904,12 @@ bool DAESaver::saveDAE(std::string filename)
|
||||
generateEffects(effects);
|
||||
|
||||
// Materials
|
||||
for (U32 objMaterial = 0; objMaterial < mAllMaterials.size(); objMaterial++)
|
||||
for (const auto& objMaterial : mAllMaterials)
|
||||
{
|
||||
daeElement* mat = materials->add("material");
|
||||
mat->setAttribute("id", (mAllMaterials[objMaterial].name + "-material").c_str());
|
||||
mat->setAttribute("id", (objMaterial.name + "-material").c_str());
|
||||
daeElement* matEffect = mat->add("instance_effect");
|
||||
matEffect->setAttribute("url", ("#" + mAllMaterials[objMaterial].name + "-fx").c_str());
|
||||
matEffect->setAttribute("url", ('#' + objMaterial.name + "-fx").c_str());
|
||||
}
|
||||
|
||||
root->add("scene instance_visual_scene")->setAttribute("url", "#Scene");
|
||||
@@ -930,11 +930,11 @@ DAESaver::MaterialInfo DAESaver::getMaterial(LLTextureEntry* te)
|
||||
{
|
||||
if (gSavedSettings.getBOOL("DAEExportConsolidateMaterials"))
|
||||
{
|
||||
for (U32 i=0; i < mAllMaterials.size(); i++)
|
||||
for (const auto& mat : mAllMaterials)
|
||||
{
|
||||
if (mAllMaterials[i].matches(te))
|
||||
if (mat.matches(te))
|
||||
{
|
||||
return mAllMaterials[i];
|
||||
return mat;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -944,7 +944,7 @@ DAESaver::MaterialInfo DAESaver::getMaterial(LLTextureEntry* te)
|
||||
ret.color = te->getColor();
|
||||
ret.name = llformat("Material%d", mAllMaterials.size());
|
||||
mAllMaterials.push_back(ret);
|
||||
return mAllMaterials[mAllMaterials.size() - 1];
|
||||
return ret;
|
||||
}
|
||||
|
||||
void DAESaver::getMaterials(LLViewerObject* obj, material_list_t* ret)
|
||||
@@ -954,10 +954,7 @@ void DAESaver::getMaterials(LLViewerObject* obj, material_list_t* ret)
|
||||
{
|
||||
LLTextureEntry* te = obj->getTE(face_num);
|
||||
|
||||
if (skipFace(te))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
if (skipFace(te)) continue;
|
||||
|
||||
MaterialInfo mat = getMaterial(te);
|
||||
|
||||
@@ -968,7 +965,7 @@ void DAESaver::getMaterials(LLViewerObject* obj, material_list_t* ret)
|
||||
}
|
||||
}
|
||||
|
||||
void DAESaver::getFacesWithMaterial(LLViewerObject* obj, MaterialInfo& mat, int_list_t* ret)
|
||||
void DAESaver::getFacesWithMaterial(LLViewerObject* obj, const MaterialInfo& mat, int_list_t* ret)
|
||||
{
|
||||
S32 num_faces = obj->getVolume()->getNumVolumeFaces();
|
||||
for (S32 face_num = 0; face_num < num_faces; ++face_num)
|
||||
@@ -985,11 +982,11 @@ void DAESaver::generateEffects(daeElement *effects)
|
||||
// Effects (face color, alpha)
|
||||
bool export_textures = gSavedSettings.getBOOL("DAEExportTextures");
|
||||
|
||||
for (U32 mat = 0; mat < mAllMaterials.size(); mat++)
|
||||
for (const auto& mat : mAllMaterials)
|
||||
{
|
||||
LLColor4 color = mAllMaterials[mat].color;
|
||||
LLColor4 color = mat.color;
|
||||
domEffect* effect = (domEffect*)effects->add("effect");
|
||||
effect->setId((mAllMaterials[mat].name + "-fx").c_str());
|
||||
effect->setId((mat.name + "-fx").c_str());
|
||||
daeElement* profile = effect->add("profile_COMMON");
|
||||
std::string colladaName;
|
||||
|
||||
@@ -999,7 +996,7 @@ void DAESaver::generateEffects(daeElement *effects)
|
||||
U32 i = 0;
|
||||
for (; i < mTextures.size(); i++)
|
||||
{
|
||||
if (mAllMaterials[mat].textureID == mTextures[i])
|
||||
if (mat.textureID == mTextures[i])
|
||||
{
|
||||
textID = mTextures[i];
|
||||
break;
|
||||
@@ -1043,19 +1040,18 @@ void DAESaver::generateEffects(daeElement *effects)
|
||||
|
||||
void DAESaver::generateImagesSection(daeElement* images)
|
||||
{
|
||||
for (U32 i=0; i < mTextureNames.size(); i++)
|
||||
for (const auto& name : mTextureNames)
|
||||
{
|
||||
std::string name = mTextureNames[i];
|
||||
if (name.empty()) continue;
|
||||
std::string colladaName = name + "_" + mImageFormat;
|
||||
std::string colladaName = name + '_' + mImageFormat;
|
||||
daeElement* image = images->add("image");
|
||||
image->setAttribute("id", colladaName.c_str());
|
||||
image->setAttribute("name", colladaName.c_str());
|
||||
image->add("init_from")->setCharData(LLURI::escape(name + "." + mImageFormat));
|
||||
image->add("init_from")->setCharData(LLURI::escape(name + '.' + mImageFormat));
|
||||
}
|
||||
}
|
||||
|
||||
class DAESaveSelectedObjects : public view_listener_t
|
||||
class DAESaveSelectedObjects final : public view_listener_t
|
||||
{
|
||||
bool handleEvent(LLPointer<LLOldEvents::LLEvent> event, const LLSD& userdata)
|
||||
{
|
||||
|
||||
@@ -33,50 +33,29 @@ class LLViewerObject;
|
||||
class DAESaver
|
||||
{
|
||||
public:
|
||||
class MaterialInfo
|
||||
struct MaterialInfo
|
||||
{
|
||||
public:
|
||||
LLUUID textureID;
|
||||
LLColor4 color;
|
||||
std::string name;
|
||||
|
||||
bool matches(LLTextureEntry* te)
|
||||
bool matches(LLTextureEntry* te) const
|
||||
{
|
||||
return (textureID == te->getID()) && (color == te->getColor());
|
||||
}
|
||||
|
||||
bool operator== (const MaterialInfo& rhs)
|
||||
bool operator== (const MaterialInfo& rhs) const
|
||||
{
|
||||
return (textureID == rhs.textureID) && (color == rhs.color) && (name == rhs.name);
|
||||
}
|
||||
|
||||
bool operator!= (const MaterialInfo& rhs)
|
||||
bool operator!= (const MaterialInfo& rhs) const
|
||||
{
|
||||
return !(*this == rhs);
|
||||
}
|
||||
|
||||
MaterialInfo()
|
||||
{
|
||||
}
|
||||
|
||||
MaterialInfo(const MaterialInfo& rhs)
|
||||
{
|
||||
textureID = rhs.textureID;
|
||||
color = rhs.color;
|
||||
name = rhs.name;
|
||||
}
|
||||
|
||||
MaterialInfo& operator= (const MaterialInfo& rhs)
|
||||
{
|
||||
textureID = rhs.textureID;
|
||||
color = rhs.color;
|
||||
name = rhs.name;
|
||||
return *this;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
typedef std::vector<std::pair<LLViewerObject*,std::string> > obj_info_t;
|
||||
typedef std::vector<std::pair<LLViewerObject*,std::string>> obj_info_t;
|
||||
typedef uuid_vec_t id_list_t;
|
||||
typedef std::vector<std::string> string_list_t;
|
||||
typedef std::vector<S32> int_list_t;
|
||||
@@ -97,12 +76,12 @@ public:
|
||||
|
||||
private:
|
||||
void transformTexCoord(S32 num_vert, LLVector2* coord, LLVector3* positions, LLVector3* normals, LLTextureEntry* te, LLVector3 scale);
|
||||
void addSource(daeElement* mesh, const char* src_id, std::string params, const std::vector<F32> &vals);
|
||||
void addSource(daeElement* mesh, const char* src_id, const std::string& params, const std::vector<F32> &vals);
|
||||
void addPolygons(daeElement* mesh, const char* geomID, const char* materialID, LLViewerObject* obj, int_list_t* faces_to_include);
|
||||
bool skipFace(LLTextureEntry *te);
|
||||
MaterialInfo getMaterial(LLTextureEntry* te);
|
||||
void getMaterials(LLViewerObject* obj, material_list_t* ret);
|
||||
void getFacesWithMaterial(LLViewerObject* obj, MaterialInfo& mat, int_list_t* ret);
|
||||
void getFacesWithMaterial(LLViewerObject* obj, const MaterialInfo& mat, int_list_t* ret);
|
||||
void generateEffects(daeElement *effects);
|
||||
void generateImagesSection(daeElement* images);
|
||||
};
|
||||
|
||||
@@ -95,6 +95,9 @@
|
||||
;File Handling
|
||||
SetOverwrite on
|
||||
|
||||
;Verify CRC
|
||||
CRCCheck on
|
||||
|
||||
;--------------------------------
|
||||
;Interface Settings
|
||||
|
||||
@@ -209,6 +212,7 @@
|
||||
!insertmacro MUI_RESERVEFILE_LANGDLL
|
||||
ReserveFile "${NSISDIR}\Plugins\x86-unicode\INetC.dll"
|
||||
ReserveFile "${NSISDIR}\Plugins\x86-unicode\nsDialogs.dll"
|
||||
ReserveFile "${NSISDIR}\Plugins\x86-unicode\nsis7z.dll"
|
||||
ReserveFile "${NSISDIR}\Plugins\x86-unicode\StartMenu.dll"
|
||||
ReserveFile "${NSISDIR}\Plugins\x86-unicode\StdUtils.dll"
|
||||
ReserveFile "${NSISDIR}\Plugins\x86-unicode\System.dll"
|
||||
@@ -406,7 +410,14 @@ Section "Viewer"
|
||||
SetOutPath "$INSTDIR"
|
||||
;Remove old shader files first so fallbacks will work.
|
||||
RMDir /r "$INSTDIR\app_settings\shaders\*"
|
||||
|
||||
;Remove old Microsoft DLLs, reboot if needed
|
||||
Delete /REBOOTOK "$INSTDIR\api-ms-win-*.dll"
|
||||
Delete /REBOOTOK "$INSTDIR\concrt*.dll"
|
||||
Delete /REBOOTOK "$INSTDIR\msvcp*.dll"
|
||||
Delete /REBOOTOK "$INSTDIR\ucrtbase.dll"
|
||||
Delete /REBOOTOK "$INSTDIR\vccorlib*.dll"
|
||||
Delete /REBOOTOK "$INSTDIR\vcruntime*.dll"
|
||||
|
||||
;This placeholder is replaced by the complete list of all the files in the installer, by viewer_manifest.py
|
||||
%%INSTALL_FILES%%
|
||||
|
||||
@@ -416,9 +427,9 @@ Section "Viewer"
|
||||
|
||||
;Download LibVLC
|
||||
!ifdef WIN64_BIN_BUILD
|
||||
inetc::get /RESUME "Failed to download VLC media package. Retry?" "https://videolan.mirrors.hivelocity.net/vlc/3.0.8/win64/vlc-3.0.8-win64.7z" "$TEMP\AlchemyInst\libvlc.7z" /END
|
||||
inetc::get /RESUME "Failed to download VLC media package. Retry?" "https://download.videolan.org/pub/videolan/vlc/3.0.8/win64/vlc-3.0.8-win64.7z" "$TEMP\AlchemyInst\libvlc.7z" /END
|
||||
!else
|
||||
inetc::get /RESUME "Failed to download VLC media package. Retry?" "https://videolan.mirrors.hivelocity.net/vlc/3.0.8/win32/vlc-3.0.8-win32.7z" "$TEMP\AlchemyInst\libvlc.7z" /END
|
||||
inetc::get /RESUME "Failed to download VLC media package. Retry?" "https://download.videolan.org/pub/videolan/vlc/3.0.8/win32/vlc-3.0.8-win32.7z" "$TEMP\AlchemyInst\libvlc.7z" /END
|
||||
!endif
|
||||
Nsis7z::ExtractWithDetails "$TEMP\AlchemyInst\libvlc.7z" "Unpacking media plugins %s..."
|
||||
Rename "$TEMP\AlchemyInst\vlc-3.0.8\libvlc.dll" "$INSTDIR\llplugin\libvlc.dll"
|
||||
@@ -457,9 +468,9 @@ Section "Viewer"
|
||||
CreateShortCut "$SMPROGRAMS\$STARTMENUFOLDER\$INSTSHORTCUT.lnk" "$\"$INSTDIR\$INSTEXE$\"" "$SHORTCUT_LANG_PARAM"
|
||||
CreateShortCut "$SMPROGRAMS\$STARTMENUFOLDER\Uninstall $INSTSHORTCUT.lnk" "$\"$INSTDIR\uninst.exe$\"" ""
|
||||
!endif
|
||||
WriteINIStr "$SMPROGRAMS\$STARTMENUFOLDER\SL Create Account.url" "InternetShortcut" "URL" "http://join.secondlife.com/"
|
||||
WriteINIStr "$SMPROGRAMS\$STARTMENUFOLDER\SL Your Account.url" "InternetShortcut" "URL" "http://www.secondlife.com/account/"
|
||||
WriteINIStr "$SMPROGRAMS\$STARTMENUFOLDER\SL Scripting Language Help.url" "InternetShortcut" "URL" "http://wiki.secondlife.com/wiki/LSL_Portal"
|
||||
WriteINIStr "$SMPROGRAMS\$STARTMENUFOLDER\SL Create Account.url" "InternetShortcut" "URL" "https://join.secondlife.com/"
|
||||
WriteINIStr "$SMPROGRAMS\$STARTMENUFOLDER\SL Your Account.url" "InternetShortcut" "URL" "https://www.secondlife.com/account/"
|
||||
WriteINIStr "$SMPROGRAMS\$STARTMENUFOLDER\SL Scripting Language Help.url" "InternetShortcut" "URL" "https://wiki.secondlife.com/wiki/LSL_Portal"
|
||||
|
||||
!insertmacro MUI_STARTMENU_WRITE_END
|
||||
|
||||
|
||||
@@ -55,9 +55,8 @@
|
||||
|
||||
## - For advanced debugging cases, you can run the viewer under the
|
||||
## control of another program, such as strace, gdb, or valgrind. If
|
||||
## you're building your own viewer, bear in mind that the executable
|
||||
## in the bin directory will be stripped: you should replace it with
|
||||
## an unstripped binary before you run.
|
||||
## you're building your own viewer, run the configure step with
|
||||
## -DPACKAGE:BOOL=OFF to produce an unstripped binary for debugging.
|
||||
if [ -n "$ASCENDED_DEVELOPER" ]; then
|
||||
if [ "$ASCENDED_DEVELOPER" = "1" ]; then
|
||||
export LL_WRAPPER='gdb --args'
|
||||
|
||||
@@ -40,11 +40,21 @@
|
||||
/// Classes for AISv3 support.
|
||||
///----------------------------------------------------------------------------
|
||||
|
||||
extern AIHTTPTimeoutPolicy AISAPIResponder_timeout;
|
||||
|
||||
class AISCommand final : public LLHTTPClient::ResponderWithCompleted
|
||||
{
|
||||
public:
|
||||
typedef boost::function<void()> command_func_type;
|
||||
// AISCommand - base class for retry-able HTTP requests using the AISv3 cap.
|
||||
|
||||
// Limit max in flight requests to 2. Server was aggressively throttling otherwise.
|
||||
constexpr static U8 sMaxActiveAISCommands = 4;
|
||||
static U8 sActiveAISCommands;
|
||||
static std::queue< boost::intrusive_ptr< AISCommand > > sPendingAISCommands;
|
||||
|
||||
virtual AIHTTPTimeoutPolicy const& getHTTPTimeoutPolicy(void) const { return AISAPIResponder_timeout; }
|
||||
|
||||
AISCommand(AISAPI::COMMAND_TYPE type, const char* name, const LLUUID& targetId, AISAPI::completion_t callback) :
|
||||
mCommandFunc(NULL),
|
||||
mRetryPolicy(new LLAdaptiveRetryPolicy(1.0, 32.0, 2.0, 10)),
|
||||
@@ -53,10 +63,30 @@ public:
|
||||
mName(name),
|
||||
mType(type)
|
||||
{}
|
||||
|
||||
virtual ~AISCommand()
|
||||
{
|
||||
if (mActive)
|
||||
{
|
||||
--sActiveAISCommands;
|
||||
while (sActiveAISCommands < sMaxActiveAISCommands && !sPendingAISCommands.empty())
|
||||
{
|
||||
sPendingAISCommands.front()->dispatch();
|
||||
sPendingAISCommands.pop();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void run( command_func_type func )
|
||||
{
|
||||
(mCommandFunc = func)();
|
||||
mCommandFunc = func;
|
||||
if (sActiveAISCommands >= sMaxActiveAISCommands)
|
||||
{
|
||||
sPendingAISCommands.push(this);
|
||||
}
|
||||
else
|
||||
{
|
||||
dispatch();
|
||||
}
|
||||
}
|
||||
|
||||
char const* getName(void) const override
|
||||
@@ -64,6 +94,17 @@ public:
|
||||
return mName;
|
||||
}
|
||||
|
||||
private:
|
||||
void dispatch()
|
||||
{
|
||||
if (LLApp::isQuitting())
|
||||
{
|
||||
return;
|
||||
}
|
||||
++sActiveAISCommands;
|
||||
mActive = true;
|
||||
(mCommandFunc)();
|
||||
}
|
||||
void markComplete()
|
||||
{
|
||||
// Command func holds a reference to self, need to release it
|
||||
@@ -72,42 +113,56 @@ public:
|
||||
mRetryPolicy->onSuccess();
|
||||
}
|
||||
|
||||
void malformedResponse() { mStatus = HTTP_INTERNAL_ERROR_OTHER; mReason = llformat("Malformed response contents (original code: %d)", mStatus); }
|
||||
|
||||
bool onFailure()
|
||||
{
|
||||
bool retry = mStatus != HTTP_INTERNAL_ERROR_OTHER && mStatus != 410; // We handle these and stop
|
||||
LL_WARNS("Inventory") << "Inventory error: " << dumpResponse() << LL_ENDL;
|
||||
if (retry) mRetryPolicy->onFailure(mStatus, getResponseHeaders());
|
||||
mRetryPolicy->onFailure(mStatus, getResponseHeaders());
|
||||
F32 seconds_to_wait;
|
||||
if (retry && mRetryPolicy->shouldRetry(seconds_to_wait))
|
||||
if (mRetryPolicy->shouldRetry(seconds_to_wait))
|
||||
{
|
||||
if (mStatus == 503)
|
||||
{
|
||||
// Pad delay a bit more since we're getting throttled.
|
||||
seconds_to_wait += 10.f + ll_frand(4.f);
|
||||
}
|
||||
LL_WARNS("Inventory") << "Retrying in " << seconds_to_wait << "seconds due to inventory error for " << getName() <<": " << dumpResponse() << LL_ENDL;
|
||||
doAfterInterval(mCommandFunc,seconds_to_wait);
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
// Command func holds a reference to self, need to release it
|
||||
// after a success or final failure.
|
||||
// *TODO: Notify user? This seems bad.
|
||||
LL_WARNS("Inventory") << "Abort due to inventory error for " << getName() <<": " << dumpResponse() << LL_ENDL;
|
||||
mCommandFunc = no_op;
|
||||
return false;
|
||||
}
|
||||
return retry;
|
||||
}
|
||||
|
||||
protected:
|
||||
void httpCompleted() override
|
||||
{
|
||||
AISAPI::InvokeAISCommandCoro(this, getURL(), mTargetId, getContent(), mCompletionFunc, (AISAPI::COMMAND_TYPE)mType);
|
||||
// Continue through if successful or longer retrying,
|
||||
if (isGoodStatus(mStatus) || !onFailure())
|
||||
{
|
||||
markComplete();
|
||||
AISAPI::InvokeAISCommandCoro(this, getURL(), mTargetId, getContent(), mCompletionFunc, (AISAPI::COMMAND_TYPE)mType);
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
command_func_type mCommandFunc;
|
||||
LLPointer<LLHTTPRetryPolicy> mRetryPolicy;
|
||||
AISAPI::completion_t mCompletionFunc;
|
||||
const LLUUID mTargetId;
|
||||
const char* mName;
|
||||
bool mActive = false;
|
||||
AISAPI::COMMAND_TYPE mType;
|
||||
};
|
||||
|
||||
U8 AISCommand::sActiveAISCommands = 0;
|
||||
std::queue< boost::intrusive_ptr< AISCommand > > AISCommand::sPendingAISCommands;
|
||||
|
||||
//=========================================================================
|
||||
const std::string AISAPI::INVENTORY_CAP_NAME("InventoryAPIv3");
|
||||
const std::string AISAPI::LIBRARY_CAP_NAME("LibraryAPIv3");
|
||||
@@ -312,21 +367,18 @@ void AISAPI::UpdateItem(const LLUUID &itemId, const LLSD &updates, completion_t
|
||||
boost::intrusive_ptr< AISCommand > responder = new AISCommand(UPDATEITEM, "UpdateItem",itemId, callback);
|
||||
responder->run(boost::bind(&LLHTTPClient::patch, url, updates, responder/*,*/ DEBUG_CURLIO_PARAM(debug_off), keep_alive, (AIStateMachine*)NULL, 0));
|
||||
}
|
||||
void AISAPI::InvokeAISCommandCoro(AISCommand* responder,
|
||||
void AISAPI::InvokeAISCommandCoro(LLHTTPClient::ResponderWithCompleted* responder,
|
||||
std::string url,
|
||||
LLUUID targetId, LLSD result, completion_t callback, COMMAND_TYPE type)
|
||||
{
|
||||
LL_DEBUGS("Inventory") << "url: " << url << LL_ENDL;
|
||||
|
||||
auto status = responder->getStatus();
|
||||
auto status = responder->getStatus();
|
||||
|
||||
if (!responder->isGoodStatus(status) || !result.isMap())
|
||||
{
|
||||
if (!result.isMap())
|
||||
{
|
||||
responder->malformedResponse();
|
||||
}
|
||||
else if (status == 410) //GONE
|
||||
{
|
||||
LL_WARNS("Inventory") << "Inventory error: " << status << ": " << responder->getReason() << LL_ENDL;
|
||||
if (status == 410) //GONE
|
||||
{
|
||||
// Item does not exist or was already deleted from server.
|
||||
// parent folder is out of sync
|
||||
@@ -360,11 +412,12 @@ void AISAPI::InvokeAISCommandCoro(AISCommand* responder,
|
||||
}
|
||||
}
|
||||
}
|
||||
// Keep these statuses accounted for in the responder too
|
||||
if (responder->onFailure()) // If we're retrying, exit early.
|
||||
return;
|
||||
if (!result.isMap())
|
||||
{
|
||||
LL_WARNS("Inventory") << "Inventory error: Malformed response contents" << LL_ENDL;
|
||||
}
|
||||
LL_WARNS("Inventory") << ll_pretty_print_sd(result) << LL_ENDL;
|
||||
}
|
||||
else responder->markComplete();
|
||||
|
||||
gInventory.onAISUpdateReceived("AISCommand", result);
|
||||
|
||||
|
||||
@@ -72,7 +72,7 @@ private:
|
||||
static std::string getInvCap();
|
||||
static std::string getLibCap();
|
||||
|
||||
static void InvokeAISCommandCoro(class AISCommand* responder,
|
||||
static void InvokeAISCommandCoro(LLHTTPClient::ResponderWithCompleted* responder,
|
||||
std::string url, LLUUID targetId, LLSD body,
|
||||
completion_t callback, COMMAND_TYPE type);
|
||||
};
|
||||
|
||||
@@ -26,7 +26,6 @@
|
||||
|
||||
#include "llviewerprecompiledheaders.h"
|
||||
|
||||
#include <boost/lexical_cast.hpp>
|
||||
#include "llagent.h"
|
||||
#include "llagentcamera.h"
|
||||
#include "llagentwearables.h"
|
||||
@@ -3994,7 +3993,7 @@ LLSD LLAppearanceMgr::dumpCOF() const
|
||||
LLUUID linked_asset_id(linked_item->getAssetUUID());
|
||||
md5.update((unsigned char*)linked_asset_id.mData, 16);
|
||||
U32 flags = linked_item->getFlags();
|
||||
md5.update(boost::lexical_cast<std::string>(flags));
|
||||
md5.update(fmt::to_string(flags));
|
||||
}
|
||||
else if (LLAssetType::AT_LINK_FOLDER != inv_item->getActualType())
|
||||
{
|
||||
|
||||
@@ -235,7 +235,7 @@ struct crashpad_annotation : public crashpad::Annotation {
|
||||
crashpad_annotation(const char* name) : crashpad::Annotation(T, name, buffer.data())
|
||||
{}
|
||||
void set(const std::string& src) {
|
||||
LL_INFOS() << name() << ": " << src.c_str() << LL_ENDL;
|
||||
//LL_INFOS() << name() << ": " << src.c_str() << LL_ENDL;
|
||||
const size_t min_size = llmin(SIZE, src.size());
|
||||
memcpy(buffer.data(), src.data(), min_size);
|
||||
buffer.data()[SIZE - 1] = '\0';
|
||||
@@ -243,18 +243,27 @@ struct crashpad_annotation : public crashpad::Annotation {
|
||||
}
|
||||
};
|
||||
#define DEFINE_CRASHPAD_ANNOTATION(name, len) \
|
||||
static crashpad_annotation<len> g_crashpad_annotation_##name##_buffer(#name);
|
||||
static crashpad_annotation<len> g_crashpad_annotation_##name##_buffer("sentry[tags]["#name"]");
|
||||
#define DEFINE_CRASHPAD_ANNOTATION_EXTRA(name, len) \
|
||||
static crashpad_annotation<len> g_crashpad_annotation_##name##_buffer("sentry[extra]["#name"]");
|
||||
#define SET_CRASHPAD_ANNOTATION_VALUE(name, value) \
|
||||
g_crashpad_annotation_##name##_buffer.set(value);
|
||||
#else
|
||||
#define SET_CRASHPAD_ANNOTATION_VALUE(name, value)
|
||||
#define DEFINE_CRASHPAD_ANNOTATION_EXTRA(name, len)
|
||||
#define DEFINE_CRASHPAD_ANNOTATION(name, len)
|
||||
#endif
|
||||
|
||||
DEFINE_CRASHPAD_ANNOTATION(fatal_message, 512);
|
||||
DEFINE_CRASHPAD_ANNOTATION_EXTRA(fatal_message, 512);
|
||||
DEFINE_CRASHPAD_ANNOTATION(grid_name, 64);
|
||||
DEFINE_CRASHPAD_ANNOTATION(cpu_string, 128);
|
||||
DEFINE_CRASHPAD_ANNOTATION(startup_state, 32);
|
||||
DEFINE_CRASHPAD_ANNOTATION(region_name, 64);
|
||||
DEFINE_CRASHPAD_ANNOTATION_EXTRA(cpu_string, 128);
|
||||
DEFINE_CRASHPAD_ANNOTATION_EXTRA(gpu_string, 128);
|
||||
DEFINE_CRASHPAD_ANNOTATION_EXTRA(gl_version, 128);
|
||||
DEFINE_CRASHPAD_ANNOTATION_EXTRA(session_duration, 32);
|
||||
DEFINE_CRASHPAD_ANNOTATION_EXTRA(startup_state, 32);
|
||||
DEFINE_CRASHPAD_ANNOTATION_EXTRA(memory_sys, 32);
|
||||
DEFINE_CRASHPAD_ANNOTATION_EXTRA(memory_alloc, 32);
|
||||
|
||||
////// Windows-specific includes to the bottom - nasty defines in these pollute the preprocessor
|
||||
//
|
||||
@@ -1076,6 +1085,8 @@ bool LLAppViewer::init()
|
||||
gGLManager.getGLInfo(gDebugInfo);
|
||||
gGLManager.printGLInfoString();
|
||||
|
||||
writeDebugInfo();
|
||||
|
||||
// Load Default bindings
|
||||
load_default_bindings(gSavedSettings.getBOOL("LiruUseZQSDKeys"));
|
||||
|
||||
@@ -1163,6 +1174,8 @@ bool LLAppViewer::init()
|
||||
// save the graphics card
|
||||
gDebugInfo["GraphicsCard"] = LLFeatureManager::getInstance()->getGPUString();
|
||||
|
||||
writeDebugInfo();
|
||||
|
||||
// Save the current version to the prefs file
|
||||
gSavedSettings.setString("LastRunVersion",
|
||||
LLVersionInfo::getChannelAndVersion());
|
||||
@@ -1180,6 +1193,8 @@ bool LLAppViewer::init()
|
||||
gGLActive = FALSE;
|
||||
LLViewerMedia::initClass();
|
||||
LL_INFOS("InitInfo") << "Viewer media initialized." << LL_ENDL ;
|
||||
|
||||
writeDebugInfo();
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -1331,6 +1346,12 @@ bool LLAppViewer::mainLoop()
|
||||
//clear call stack records
|
||||
LL_CLEAR_CALLSTACKS();
|
||||
|
||||
#ifdef USE_CRASHPAD
|
||||
// Not event based. Update per frame
|
||||
SET_CRASHPAD_ANNOTATION_VALUE(session_duration, fmt::to_string(LLFrameTimer::getElapsedSeconds()));
|
||||
SET_CRASHPAD_ANNOTATION_VALUE(memory_alloc, fmt::to_string((LLMemory::getCurrentRSS() >> 10)/1000.f));
|
||||
#endif
|
||||
|
||||
//check memory availability information
|
||||
checkMemory() ;
|
||||
|
||||
@@ -2784,7 +2805,13 @@ void LLAppViewer::writeDebugInfo(bool isStatic)
|
||||
#else
|
||||
SET_CRASHPAD_ANNOTATION_VALUE(fatal_message, gDebugInfo["FatalMessage"].asString());
|
||||
SET_CRASHPAD_ANNOTATION_VALUE(grid_name, gDebugInfo["GridName"].asString());
|
||||
SET_CRASHPAD_ANNOTATION_VALUE(region_name, gDebugInfo["CurrentRegion"].asString());
|
||||
SET_CRASHPAD_ANNOTATION_VALUE(cpu_string, gDebugInfo["CPUInfo"]["CPUString"].asString());
|
||||
SET_CRASHPAD_ANNOTATION_VALUE(gpu_string, gDebugInfo["GraphicsCard"].asString());
|
||||
SET_CRASHPAD_ANNOTATION_VALUE(gl_version, gDebugInfo["GLInfo"]["GLVersion"].asString());
|
||||
SET_CRASHPAD_ANNOTATION_VALUE(session_duration, fmt::to_string(LLFrameTimer::getElapsedSeconds()));
|
||||
SET_CRASHPAD_ANNOTATION_VALUE(memory_alloc, fmt::to_string((LLMemory::getCurrentRSS() >> 10) / 1000.f));
|
||||
SET_CRASHPAD_ANNOTATION_VALUE(memory_sys, fmt::to_string(gDebugInfo["RAMInfo"]["Physical"].asInteger() * 0.001f));
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -2969,8 +2996,8 @@ void LLAppViewer::handleViewerCrash()
|
||||
gDebugInfo["ViewerExePath"] = gDirUtilp->getExecutablePathAndName();
|
||||
gDebugInfo["CurrentPath"] = gDirUtilp->getCurPath();
|
||||
gDebugInfo["Dynamic"]["SessionLength"] = F32(LLFrameTimer::getElapsedSeconds());
|
||||
gDebugInfo["StartupState"] = LLStartUp::getStartupStateString();
|
||||
gDebugInfo["Dynamic"]["RAMInfo"]["Allocated"] = (LLSD::Integer) LLMemory::getCurrentRSS() >> 10;
|
||||
gDebugInfo["StartupState"] = LLStartUp::getStartupStateString();
|
||||
gDebugInfo["FirstLogin"] = (LLSD::Boolean) gAgent.isFirstLogin();
|
||||
gDebugInfo["FirstRunThisInstall"] = gSavedSettings.getBOOL("FirstRunThisInstall");
|
||||
|
||||
@@ -4832,11 +4859,14 @@ void LLAppViewer::disconnectViewer()
|
||||
// floater_sound_preview.xml
|
||||
// floater_animation_preview.xml
|
||||
// files.
|
||||
|
||||
// A more generic mechanism would be nice..
|
||||
LLFloater* fl = static_cast<LLFloater*>(*it);
|
||||
if (fl
|
||||
&& (fl->getName() == "Image Preview"
|
||||
|| fl->getName() == "Sound Preview"
|
||||
|| fl->getName() == "Animation Preview"
|
||||
|| fl->getName() == "perm prefs"
|
||||
))
|
||||
{
|
||||
floaters_to_close.push_back(fl);
|
||||
@@ -5054,6 +5084,10 @@ void LLAppViewer::handleLoginComplete()
|
||||
}
|
||||
|
||||
mOnLoginCompleted();
|
||||
|
||||
// Singu Note: This would usually be registered via mOnLoginCompleted, but that would require code in newview regardless so.. just call directly here.
|
||||
LLNotifications::instance().onLoginCompleted();
|
||||
|
||||
// Singu Note: Due to MAINT-4001, we must do this here, it lives in LLSidepanelInventory::updateInbox upstream.
|
||||
// Consolidate Received items
|
||||
// We shouldn't have to do that but with a client/server system relying on a "well known folder" convention,
|
||||
|
||||
@@ -349,7 +349,10 @@ bool LLAttachmentsMgr::getPendingAttachments(uuid_set_t& ids) const
|
||||
ids.clear();
|
||||
|
||||
// Returns the union of the LL maintained list of attachments that are waiting for link creation and our maintained list of attachments that are pending link creation
|
||||
set_union(mRecentlyArrivedAttachments.begin(), mRecentlyArrivedAttachments.end(), mPendingAttachLinks.begin(), mPendingAttachLinks.end(), std::inserter(ids, ids.begin()));
|
||||
ids.insert(mRecentlyArrivedAttachments.begin(), mRecentlyArrivedAttachments.end());
|
||||
ids.insert(mPendingAttachLinks.begin(), mPendingAttachLinks.end());
|
||||
// Singu Note: "Expression: Sequence not ordered" using std::set_union
|
||||
//set_union(mRecentlyArrivedAttachments.begin(), mRecentlyArrivedAttachments.end(), mPendingAttachLinks.begin(), mPendingAttachLinks.end(), std::inserter(ids, ids.begin()));
|
||||
|
||||
return !ids.empty();
|
||||
}
|
||||
|
||||
@@ -531,17 +531,24 @@ void LLChatBar::sendChat( EChatType type )
|
||||
// static
|
||||
void LLChatBar::startChat(const char* line)
|
||||
{
|
||||
if (!gChatBar || !gChatBar->getParent())
|
||||
{
|
||||
return;
|
||||
}
|
||||
gChatBar->getParent()->setVisible(TRUE);
|
||||
gChatBar->setKeyboardFocus(TRUE);
|
||||
gSavedSettings.setBOOL("ChatVisible", TRUE);
|
||||
|
||||
if (line && gChatBar->mInputEditor)
|
||||
if (gChatBar->mInputEditor)
|
||||
{
|
||||
std::string line_string(line);
|
||||
gChatBar->mInputEditor->setText(line_string);
|
||||
if (line)
|
||||
{
|
||||
std::string line_string(line);
|
||||
gChatBar->mInputEditor->setText(line_string);
|
||||
}
|
||||
// always move cursor to end so users don't obliterate chat when accidentally hitting WASD
|
||||
gChatBar->mInputEditor->setCursorToEnd();
|
||||
}
|
||||
// always move cursor to end so users don't obliterate chat when accidentally hitting WASD
|
||||
gChatBar->mInputEditor->setCursorToEnd();
|
||||
}
|
||||
|
||||
|
||||
@@ -550,7 +557,8 @@ void LLChatBar::startChat(const char* line)
|
||||
void LLChatBar::stopChat()
|
||||
{
|
||||
// In simple UI mode, we never release focus from the chat bar
|
||||
gChatBar->setKeyboardFocus(FALSE);
|
||||
if (gChatBar)
|
||||
gChatBar->setKeyboardFocus(FALSE);
|
||||
|
||||
// If we typed a movement key and pressed return during the
|
||||
// same frame, the keyboard handlers will see the key as having
|
||||
@@ -562,7 +570,8 @@ void LLChatBar::stopChat()
|
||||
gAgent.stopTyping();
|
||||
|
||||
// hide chat bar so it doesn't grab focus back
|
||||
gChatBar->getParent()->setVisible(FALSE);
|
||||
if (gChatBar && gChatBar->getParent())
|
||||
gChatBar->getParent()->setVisible(FALSE);
|
||||
gSavedSettings.setBOOL("ChatVisible", FALSE);
|
||||
}
|
||||
|
||||
|
||||
@@ -515,6 +515,10 @@ void LLCloudLayer::connectNeighbor(LLCloudLayer *cloudp, U32 direction)
|
||||
return;
|
||||
}
|
||||
|
||||
if (mNeighbors[direction])
|
||||
{
|
||||
mNeighbors[direction]->mNeighbors[gDirOpposite[direction]] = NULL;
|
||||
}
|
||||
mNeighbors[direction] = cloudp;
|
||||
if (cloudp)
|
||||
mNeighbors[direction]->mNeighbors[gDirOpposite[direction]] = this;
|
||||
|
||||
@@ -1596,11 +1596,7 @@ void LLSpatialBridge::cleanupReferences()
|
||||
LLDrawable::cleanupReferences();
|
||||
if (mDrawable)
|
||||
{
|
||||
/*
|
||||
|
||||
DON'T DO THIS -- this should happen through octree destruction
|
||||
|
||||
mDrawable->setSpatialGroup(NULL);
|
||||
mDrawable->setGroup(NULL);
|
||||
if (mDrawable->getVObj())
|
||||
{
|
||||
LLViewerObject::const_child_list_t& child_list = mDrawable->getVObj()->getChildren();
|
||||
@@ -1608,17 +1604,18 @@ void LLSpatialBridge::cleanupReferences()
|
||||
iter != child_list.end(); iter++)
|
||||
{
|
||||
LLViewerObject* child = *iter;
|
||||
LLDrawable* drawable = child->mDrawable;
|
||||
LLDrawable* drawable = child->mDrawable;
|
||||
if (drawable)
|
||||
{
|
||||
drawable->setSpatialGroup(NULL);
|
||||
drawable->setGroup(NULL);
|
||||
}
|
||||
}
|
||||
}*/
|
||||
}
|
||||
|
||||
LLPointer<LLDrawable> drawablep = mDrawable;
|
||||
LLPointer<LLSpatialBridge> bridgep = mDrawable->getSpatialBridge();
|
||||
mDrawable->setSpatialBridge(nullptr);
|
||||
mDrawable = nullptr;
|
||||
drawablep->setSpatialBridge(nullptr);
|
||||
bridgep = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -52,7 +52,6 @@
|
||||
#include "llworld.h"
|
||||
|
||||
#include <boost/date_time.hpp>
|
||||
#include <boost/lexical_cast.hpp>
|
||||
|
||||
// [RLVa:KB]
|
||||
#include "rlvhandler.h"
|
||||
@@ -1006,7 +1005,7 @@ void LLFloaterAvatarList::refreshAvatarList()
|
||||
color = sRadarTextYoung;
|
||||
}
|
||||
}
|
||||
agep.value = age_set ? boost::lexical_cast<std::string>(entry->mAge) : "?";
|
||||
agep.value = age_set ? fmt::to_string(entry->mAge) : "?";
|
||||
agep.color = color;
|
||||
element.columns.add(agep);
|
||||
}
|
||||
@@ -1069,7 +1068,7 @@ void LLFloaterAvatarList::refreshAvatarList()
|
||||
else
|
||||
{
|
||||
LLStringUtil::format_map_t args;
|
||||
args["[COUNT]"] = boost::lexical_cast<std::string>(mAvatars.size());
|
||||
args["[COUNT]"] = fmt::to_string(mAvatars.size());
|
||||
setTitle(getString("TitleWithCount", args));
|
||||
}
|
||||
|
||||
|
||||
@@ -277,19 +277,19 @@ void LLFloaterBuyCurrencyUI::updateUI()
|
||||
S32 balance = gStatusBar->getBalance();
|
||||
childShow("balance_label");
|
||||
childShow("balance_amount");
|
||||
childSetTextArg("balance_amount", "[AMT]", llformat("%d", balance));
|
||||
childSetTextArg("balance_amount", "[AMT]", fmt::to_string(balance));
|
||||
childSetTextArg("balance_amount", "[CURRENCY]", gHippoGridManager->getConnectedGrid()->getCurrencySymbol());
|
||||
|
||||
S32 buying = mManager.getAmount();
|
||||
childShow("buying_label");
|
||||
childShow("buying_amount");
|
||||
childSetTextArg("buying_amount", "[AMT]", llformat("%d", buying));
|
||||
childSetTextArg("buying_amount", "[AMT]", fmt::to_string(buying));
|
||||
childSetTextArg("buying_amount", "[CURRENCY]", gHippoGridManager->getConnectedGrid()->getCurrencySymbol());
|
||||
|
||||
S32 total = balance + buying;
|
||||
childShow("total_label");
|
||||
childShow("total_amount");
|
||||
childSetTextArg("total_amount", "[AMT]", llformat("%d", total));
|
||||
childSetTextArg("total_amount", "[AMT]", fmt::to_string(total));
|
||||
childSetTextArg("total_amount", "[CURRENCY]", gHippoGridManager->getConnectedGrid()->getCurrencySymbol());
|
||||
|
||||
childSetVisible("purchase_warning_repurchase", false);
|
||||
|
||||
@@ -79,7 +79,7 @@
|
||||
//
|
||||
LLColor4 agent_chat_color(const LLUUID& id, const std::string&, bool local_chat = true);
|
||||
LLColor4 get_text_color(const LLChat& chat, bool from_im = false);
|
||||
void show_log_browser(const std::string&, const std::string&);
|
||||
void show_log_browser(const std::string&, const LLUUID&);
|
||||
|
||||
//
|
||||
// Member Functions
|
||||
@@ -96,7 +96,7 @@ LLFloaterChat::LLFloaterChat(const LLSD& seed)
|
||||
|
||||
LLTextEditor* history_editor_with_mute = getChild<LLTextEditor>("Chat History Editor with mute");
|
||||
getChild<LLUICtrl>("show mutes")->setCommitCallback(boost::bind(&LLFloaterChat::onClickToggleShowMute, this, _2, getChild<LLTextEditor>("Chat History Editor"), history_editor_with_mute));
|
||||
getChild<LLUICtrl>("chat_history_open")->setCommitCallback(boost::bind(show_log_browser, "chat", "chat"));
|
||||
getChild<LLUICtrl>("chat_history_open")->setCommitCallback(boost::bind(show_log_browser, "chat", LLUUID::null));
|
||||
}
|
||||
|
||||
LLFloaterChat::~LLFloaterChat()
|
||||
@@ -243,7 +243,7 @@ void log_chat_text(const LLChat& chat)
|
||||
else
|
||||
histstr = chat.mText;
|
||||
|
||||
LLLogChat::saveHistory(std::string("chat"), histstr);
|
||||
LLLogChat::saveHistory("chat", LLUUID::null, histstr);
|
||||
}
|
||||
// static
|
||||
void LLFloaterChat::addChatHistory(LLChat& chat, bool log_to_file)
|
||||
@@ -535,28 +535,19 @@ LLColor4 get_text_color(const LLChat& chat, bool from_im)
|
||||
//static
|
||||
void LLFloaterChat::loadHistory()
|
||||
{
|
||||
LLLogChat::loadHistory("chat", &chatFromLogFile, (void*)LLFloaterChat::getInstance());
|
||||
LLLogChat::loadHistory("chat", LLUUID::null, boost::bind(&LLFloaterChat::chatFromLogFile, getInstance(), _1, _2));
|
||||
}
|
||||
|
||||
//static
|
||||
void LLFloaterChat::chatFromLogFile(LLLogChat::ELogLineType type, std::string line, void* userdata)
|
||||
|
||||
void LLFloaterChat::chatFromLogFile(LLLogChat::ELogLineType type, const std::string& line)
|
||||
{
|
||||
switch (type)
|
||||
bool log_line = type == LLLogChat::LOG_LINE;
|
||||
if (log_line || gSavedPerAccountSettings.getBOOL("LogChat"))
|
||||
{
|
||||
case LLLogChat::LOG_EMPTY:
|
||||
if (gSavedPerAccountSettings.getBOOL("LogChat"))
|
||||
addChatHistory(static_cast<LLFloaterChat*>(userdata)->getString("IM_logging_string"), false);
|
||||
break;
|
||||
case LLLogChat::LOG_END:
|
||||
if (gSavedPerAccountSettings.getBOOL("LogChat"))
|
||||
addChatHistory(static_cast<LLFloaterChat*>(userdata)->getString("IM_end_log_string"), false);
|
||||
break;
|
||||
case LLLogChat::LOG_LINE:
|
||||
addChatHistory(line, FALSE);
|
||||
break;
|
||||
default:
|
||||
// nothing
|
||||
break;
|
||||
LLStyleSP style(new LLStyle(true, gSavedSettings.getColor4("LogChatColor"), LLStringUtil::null));
|
||||
const auto text = log_line ? line : getString(type == LLLogChat::LOG_END ? "IM_end_log_string" : "IM_logging_string");
|
||||
for (const auto& ed_name : { "Chat History Editor", "Chat History Editor with mute" })
|
||||
getChild<LLTextEditor>(ed_name)->appendText(text, false, true, style, false);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -73,7 +73,7 @@ public:
|
||||
static void triggerAlerts(const std::string& text);
|
||||
|
||||
void onClickToggleShowMute(bool show_mute, class LLTextEditor* history_editor, LLTextEditor* history_editor_with_mute);
|
||||
static void chatFromLogFile(LLLogChat::ELogLineType type, std::string line, void* userdata);
|
||||
void chatFromLogFile(LLLogChat::ELogLineType type, const std::string& line);
|
||||
static void loadHistory();
|
||||
static void* createSpeakersPanel(void* data);
|
||||
static void* createChatPanel(void* data);
|
||||
|
||||
@@ -1454,7 +1454,7 @@ void LLPanelLandObjects::onClickReturnOwnerList()
|
||||
|
||||
LLSD args;
|
||||
args["NAME"] = mSelectedName;
|
||||
args["N"] = std::to_string(mSelectedCount);
|
||||
args["N"] = fmt::to_string(mSelectedCount);
|
||||
if (mSelectedIsGroup)
|
||||
{
|
||||
LLNotificationsUtil::add("ReturnObjectsDeededToGroup", args, LLSD(), boost::bind(&LLPanelLandObjects::callbackReturnOwnerList, this, _1, _2));
|
||||
@@ -1665,7 +1665,7 @@ void LLPanelLandObjects::onClickReturnOwnerObjects()
|
||||
LLUUID owner_id = parcel->getOwnerID();
|
||||
|
||||
LLSD args;
|
||||
args["N"] = std::to_string(owned);
|
||||
args["N"] = fmt::to_string(owned);
|
||||
|
||||
if (owner_id == gAgent.getID())
|
||||
{
|
||||
|
||||
@@ -45,8 +45,6 @@
|
||||
#include "llmutelist.h"
|
||||
#include "llnamelistctrl.h"
|
||||
|
||||
#include <boost/lexical_cast.hpp>
|
||||
|
||||
//
|
||||
// Constants
|
||||
//
|
||||
|
||||
@@ -114,7 +114,7 @@ void LLFloaterObjectIMInfo::onClickMute()
|
||||
// [/RLVa:KB]
|
||||
|
||||
LLMuteList::instance().add(LLMute(mOwnerID, mName, mGroupOwned ? LLMute::GROUP : LLMute::AGENT));
|
||||
LLFloaterMute::showInstance();
|
||||
LLFloaterMute::showInstance()->selectMute(mOwnerID);
|
||||
close();
|
||||
}
|
||||
|
||||
|
||||
@@ -42,6 +42,7 @@
|
||||
#include "llviewerwindow.h"
|
||||
#include "lluictrlfactory.h"
|
||||
#include "llpermissions.h"
|
||||
#include "llsdserialize.h"
|
||||
#include "hippogridmanager.h"
|
||||
|
||||
extern class AIHTTPTimeoutPolicy floaterPermsResponder_timeout;
|
||||
@@ -63,6 +64,25 @@ U32 LLFloaterPerms::getEveryonePerms(std::string prefix)
|
||||
return flags;
|
||||
}
|
||||
|
||||
//static
|
||||
U32 LLFloaterPerms::getNextOwnerPerms(std::string prefix)
|
||||
{
|
||||
U32 flags = PERM_MOVE;
|
||||
if ( gSavedSettings.getBOOL(prefix+"NextOwnerCopy") )
|
||||
{
|
||||
flags |= PERM_COPY;
|
||||
}
|
||||
if ( gSavedSettings.getBOOL(prefix+"NextOwnerModify") )
|
||||
{
|
||||
flags |= PERM_MODIFY;
|
||||
}
|
||||
if ( gSavedSettings.getBOOL(prefix+"NextOwnerTransfer") )
|
||||
{
|
||||
flags |= PERM_TRANSFER;
|
||||
}
|
||||
return flags;
|
||||
}
|
||||
|
||||
//static
|
||||
U32 LLFloaterPerms::getNextOwnerPermsInverted(std::string prefix)
|
||||
{
|
||||
@@ -83,25 +103,6 @@ U32 LLFloaterPerms::getNextOwnerPermsInverted(std::string prefix)
|
||||
return flags;
|
||||
}
|
||||
|
||||
//static
|
||||
U32 LLFloaterPerms::getNextOwnerPerms(std::string prefix)
|
||||
{
|
||||
U32 flags = PERM_MOVE;
|
||||
if ( gSavedSettings.getBOOL(prefix+"NextOwnerCopy") )
|
||||
{
|
||||
flags |= PERM_COPY;
|
||||
}
|
||||
if ( gSavedSettings.getBOOL(prefix+"NextOwnerModify") )
|
||||
{
|
||||
flags |= PERM_MODIFY;
|
||||
}
|
||||
if ( gSavedSettings.getBOOL(prefix+"NextOwnerTransfer") )
|
||||
{
|
||||
flags |= PERM_TRANSFER;
|
||||
}
|
||||
return flags;
|
||||
}
|
||||
|
||||
namespace
|
||||
{
|
||||
void handle_checkboxes(LLView* view, const std::string& ctrl_name, const LLSD& value, const std::string& type)
|
||||
@@ -138,6 +139,7 @@ LLFloaterPermsDefault::LLFloaterPermsDefault(const LLSD& seed)
|
||||
LLUICtrlFactory::getInstance()->buildFloater(this, "floater_perm_prefs.xml");
|
||||
}
|
||||
|
||||
|
||||
// String equivalents of enum Categories - initialization order must match enum order!
|
||||
const std::string LLFloaterPermsDefault::sCategoryNames[CAT_LAST] =
|
||||
{
|
||||
@@ -224,41 +226,66 @@ void LLFloaterPermsDefault::onClickCancel()
|
||||
close();
|
||||
}
|
||||
|
||||
class LLFloaterPermsResponder : public LLHTTPClient::ResponderWithResult
|
||||
struct LLFloaterPermsRequester final : LLSingleton<LLFloaterPermsRequester>
|
||||
{
|
||||
friend class LLSingleton<LLFloaterPermsRequester>;
|
||||
std::string mUrl;
|
||||
LLSD mReport;
|
||||
U8 mRetriesCount = 0;
|
||||
static void init(const std::string url, const LLSD report)
|
||||
{
|
||||
auto& inst = instance();
|
||||
inst.mUrl = url;
|
||||
inst.mReport = report;
|
||||
inst.retry();
|
||||
}
|
||||
bool retry();
|
||||
};
|
||||
|
||||
class LLFloaterPermsResponder final : public LLHTTPClient::ResponderWithResult
|
||||
{
|
||||
public:
|
||||
LLFloaterPermsResponder() : LLHTTPClient::ResponderWithResult() {}
|
||||
private:
|
||||
static std::string sPreviousReason;
|
||||
|
||||
void httpFailure(void)
|
||||
void httpFailure() override
|
||||
{
|
||||
// <singu> Prevent 404s from annoying the user all the tme
|
||||
if (mStatus == HTTP_NOT_FOUND)
|
||||
LL_INFOS("FloaterPermsResponder") << "Failed to send default permissions to simulator. 404, reason: " << mReason << LL_ENDL;
|
||||
else
|
||||
// </singu>
|
||||
auto* requester = LLFloaterPermsRequester::getIfExists();
|
||||
if (!requester || requester->retry()) return;
|
||||
|
||||
LLFloaterPermsRequester::deleteSingleton();
|
||||
const std::string& reason = getReason();
|
||||
// Do not display the same error more than once in a row
|
||||
if (mReason != sPreviousReason)
|
||||
if (reason != sPreviousReason)
|
||||
{
|
||||
sPreviousReason = mReason;
|
||||
sPreviousReason = reason;
|
||||
LLSD args;
|
||||
args["REASON"] = mReason;
|
||||
args["REASON"] = reason;
|
||||
LLNotificationsUtil::add("DefaultObjectPermissions", args);
|
||||
}
|
||||
}
|
||||
void httpSuccess(void)
|
||||
void httpSuccess() override
|
||||
{
|
||||
//const LLSD& content = getContent();
|
||||
//dump_sequential_xml("perms_responder_result.xml", content);
|
||||
|
||||
// Since we have had a successful POST call be sure to display the next error message
|
||||
// even if it is the same as a previous one.
|
||||
sPreviousReason = "";
|
||||
mCapSent = true;
|
||||
LL_INFOS("FloaterPermsResponder") << "Sent default permissions to simulator" << LL_ENDL;
|
||||
LL_INFOS("ObjectPermissionsFloater") << "Default permissions successfully sent to simulator" << LL_ENDL;
|
||||
}
|
||||
/*virtual*/ AIHTTPTimeoutPolicy const& getHTTPTimeoutPolicy() const { return floaterPermsResponder_timeout; }
|
||||
/*virtual*/ char const* getName() const { return "LLFloaterPermsResponder"; }
|
||||
AIHTTPTimeoutPolicy const& getHTTPTimeoutPolicy() const override { return floaterPermsResponder_timeout; }
|
||||
char const* getName() const override { return "LLFloaterPermsResponder"; }
|
||||
};
|
||||
|
||||
bool LLFloaterPermsRequester::retry()
|
||||
{
|
||||
if (++mRetriesCount < 5)
|
||||
{
|
||||
LLHTTPClient::post(mUrl, mReport, new LLFloaterPermsResponder);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
std::string LLFloaterPermsResponder::sPreviousReason;
|
||||
|
||||
void LLFloaterPermsDefault::sendInitialPerms()
|
||||
@@ -266,12 +293,13 @@ void LLFloaterPermsDefault::sendInitialPerms()
|
||||
if (!mCapSent)
|
||||
{
|
||||
updateCap();
|
||||
mCapSent = true;
|
||||
}
|
||||
}
|
||||
|
||||
void LLFloaterPermsDefault::updateCap()
|
||||
{
|
||||
std::string object_url = gAgent.getRegion()->getCapability("AgentPreferences");
|
||||
std::string object_url = gAgent.getRegionCapability("AgentPreferences");
|
||||
|
||||
if (!object_url.empty())
|
||||
{
|
||||
@@ -283,13 +311,24 @@ void LLFloaterPermsDefault::updateCap()
|
||||
report["default_object_perm_masks"]["NextOwner"] =
|
||||
(LLSD::Integer)LLFloaterPerms::getNextOwnerPerms(sCategoryNames[CAT_OBJECTS]);
|
||||
|
||||
LLHTTPClient::post(object_url, report, new LLFloaterPermsResponder());
|
||||
{
|
||||
std::ostringstream sent_perms_log;
|
||||
LLSDSerialize::toPrettyXML(report, sent_perms_log);
|
||||
LL_DEBUGS("ObjectPermissionsFloater") << "Sending default permissions to '"
|
||||
<< object_url << "'\n"
|
||||
<< sent_perms_log.str() << LL_ENDL;
|
||||
}
|
||||
LLFloaterPermsRequester::init(object_url, report);
|
||||
}
|
||||
else
|
||||
{
|
||||
LL_DEBUGS("ObjectPermissionsFloater") << "AgentPreferences cap not available." << LL_ENDL;
|
||||
}
|
||||
}
|
||||
|
||||
void LLFloaterPermsDefault::ok()
|
||||
{
|
||||
// Changes were already applied to saved settings.
|
||||
// Changes were already applied automatically to saved settings.
|
||||
// Refreshing internal values makes it official.
|
||||
refresh();
|
||||
|
||||
@@ -302,11 +341,11 @@ void LLFloaterPermsDefault::cancel()
|
||||
{
|
||||
for (U32 iter = CAT_OBJECTS; iter < CAT_LAST; iter++)
|
||||
{
|
||||
gSavedSettings.setBOOL(sCategoryNames[iter]+"ShareWithGroup", mShareWithGroup[iter]);
|
||||
gSavedSettings.setBOOL(sCategoryNames[iter]+"EveryoneCopy", mEveryoneCopy[iter]);
|
||||
gSavedSettings.setBOOL(sCategoryNames[iter]+"NextOwnerCopy", mNextOwnerCopy[iter]);
|
||||
gSavedSettings.setBOOL(sCategoryNames[iter]+"NextOwnerModify", mNextOwnerModify[iter]);
|
||||
gSavedSettings.setBOOL(sCategoryNames[iter]+"NextOwnerTransfer", mNextOwnerTransfer[iter]);
|
||||
gSavedSettings.setBOOL(sCategoryNames[iter]+"ShareWithGroup", mShareWithGroup[iter]);
|
||||
gSavedSettings.setBOOL(sCategoryNames[iter]+"EveryoneCopy", mEveryoneCopy[iter]);
|
||||
gSavedPerAccountSettings.setBOOL(sCategoryNames[iter]+"EveryoneExport", mEveryoneExport[iter]);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -103,11 +103,7 @@ void LLFloaterPostcard::init()
|
||||
if(!gAgent.getID().isNull())
|
||||
{
|
||||
// we're logged in, so we can get this info.
|
||||
gMessageSystem->newMessageFast(_PREHASH_UserInfoRequest);
|
||||
gMessageSystem->nextBlockFast(_PREHASH_AgentData);
|
||||
gMessageSystem->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
|
||||
gMessageSystem->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
|
||||
gAgent.sendReliableMessage();
|
||||
gAgent.sendAgentUserInfoRequest();
|
||||
}
|
||||
|
||||
sInstances.insert(this);
|
||||
@@ -233,7 +229,7 @@ void LLFloaterPostcard::onClose(bool app_quitting)
|
||||
destroy();
|
||||
}
|
||||
|
||||
class LLSendPostcardResponder : public LLAssetUploadResponder
|
||||
class LLSendPostcardResponder final : public LLAssetUploadResponder
|
||||
{
|
||||
private:
|
||||
int mSnapshotIndex;
|
||||
@@ -248,22 +244,22 @@ public:
|
||||
{
|
||||
}
|
||||
// *TODO define custom uploadFailed here so it's not such a generic message
|
||||
/*virtual*/ void uploadComplete(const LLSD& content)
|
||||
void uploadComplete(const LLSD& content) override final
|
||||
{
|
||||
// we don't care about what the server returns from this post, just clean up the UI
|
||||
LLFloaterSnapshot::savePostcardDone(true, mSnapshotIndex);
|
||||
}
|
||||
/*virtual*/ void uploadFailure(const LLSD& content)
|
||||
void uploadFailure(const LLSD& content) override final
|
||||
{
|
||||
LLAssetUploadResponder::uploadFailure(content);
|
||||
LLFloaterSnapshot::savePostcardDone(false, mSnapshotIndex);
|
||||
}
|
||||
/*virtual*/ void httpFailure(void)
|
||||
void httpFailure(void) override final
|
||||
{
|
||||
LLAssetUploadResponder::httpFailure();
|
||||
LLFloaterSnapshot::savePostcardDone(false, mSnapshotIndex);
|
||||
}
|
||||
/*virtual*/ char const* getName(void) const { return "LLSendPostcardResponder"; }
|
||||
char const* getName(void) const override final { return "LLSendPostcardResponder"; }
|
||||
};
|
||||
|
||||
// static
|
||||
@@ -273,7 +269,6 @@ void LLFloaterPostcard::onClickSend(void* data)
|
||||
{
|
||||
LLFloaterPostcard *self = (LLFloaterPostcard *)data;
|
||||
|
||||
std::string from(self->childGetValue("from_form").asString());
|
||||
std::string to(self->childGetValue("to_form").asString());
|
||||
|
||||
boost::regex emailFormat("[A-Za-z0-9.%+-_]+@[A-Za-z0-9.-]+\\.[A-Za-z]{2,}(,[ \t]*[A-Za-z0-9.%+-_]+@[A-Za-z0-9.-]+\\.[A-Za-z]{2,})*");
|
||||
@@ -284,12 +279,6 @@ void LLFloaterPostcard::onClickSend(void* data)
|
||||
return;
|
||||
}
|
||||
|
||||
if (from.empty() || !boost::regex_match(from, emailFormat))
|
||||
{
|
||||
LLNotificationsUtil::add("PromptSelfEmail");
|
||||
return;
|
||||
}
|
||||
|
||||
std::string subject(self->childGetValue("subject_form").asString());
|
||||
if(subject.empty() || !self->mHasFirstMsgFocus)
|
||||
{
|
||||
@@ -349,10 +338,8 @@ void LLFloaterPostcard::uploadCallback(const LLUUID& asset_id, void *user_data,
|
||||
// static
|
||||
void LLFloaterPostcard::updateUserInfo(const std::string& email)
|
||||
{
|
||||
for (instance_list_t::iterator iter = sInstances.begin();
|
||||
iter != sInstances.end(); ++iter)
|
||||
for (auto& instance : sInstances)
|
||||
{
|
||||
LLFloaterPostcard *instance = *iter;
|
||||
const std::string& text = instance->childGetValue("from_form").asString();
|
||||
if (text.empty())
|
||||
{
|
||||
@@ -416,7 +403,6 @@ void LLFloaterPostcard::sendPostcard()
|
||||
// the capability already encodes: agent ID, region ID
|
||||
body["pos-global"] = mPosTakenGlobal.getValue();
|
||||
body["to"] = childGetValue("to_form").asString();
|
||||
body["from"] = childGetValue("from_form").asString();
|
||||
body["name"] = childGetValue("name_form").asString();
|
||||
body["subject"] = childGetValue("subject_form").asString();
|
||||
body["msg"] = childGetValue("msg_form").asString();
|
||||
|
||||
@@ -46,17 +46,17 @@ class LLLineEditor;
|
||||
class LLButton;
|
||||
class LLImageJPEG;
|
||||
|
||||
class LLFloaterPostcard
|
||||
class LLFloaterPostcard final
|
||||
: public LLFloater
|
||||
{
|
||||
public:
|
||||
LLFloaterPostcard(LLImageJPEG* jpeg, LLViewerTexture *img, const LLVector2& img_scale, const LLVector3d& pos_taken_global, int index);
|
||||
/*virtual*/ ~LLFloaterPostcard();
|
||||
/*virtual*/ ~LLFloaterPostcard() override;
|
||||
|
||||
/*virtual*/ void init();
|
||||
/*virtual*/ BOOL postBuild();
|
||||
/*virtual*/ void draw();
|
||||
/*virtual*/ void onClose(bool app_quitting);
|
||||
void init();
|
||||
/*virtual*/ BOOL postBuild() override;
|
||||
/*virtual*/ void draw() override;
|
||||
/*virtual*/ void onClose(bool app_quitting) override;
|
||||
|
||||
static LLFloaterPostcard* showFromSnapshot(LLImageJPEG *jpeg, LLViewerTexture *img, const LLVector2& img_scale, const LLVector3d& pos_taken_global, int index);
|
||||
|
||||
|
||||
@@ -43,11 +43,6 @@
|
||||
#include "llcombobox.h"
|
||||
#include "lllineeditor.h"
|
||||
#include "llviewerwindow.h"
|
||||
#if LL_MSVC
|
||||
// disable boost::lexical_cast warning
|
||||
#pragma warning (disable:4702)
|
||||
#endif
|
||||
#include <boost/lexical_cast.hpp>
|
||||
|
||||
LLFloaterPostProcess* LLFloaterPostProcess::sPostProcess = NULL;
|
||||
|
||||
@@ -190,7 +185,7 @@ void LLFloaterPostProcess::syncMenu()
|
||||
//llsd["uniform"][1]=>"uniform[1]"
|
||||
for(S32 i=0;i<it->second.size();++i)
|
||||
{
|
||||
childSetValue(it->first+'['+boost::lexical_cast<std::string>(i)+']',it->second[i]);
|
||||
childSetValue(it->first+'['+fmt::to_string(i)+']',it->second[i]);
|
||||
}
|
||||
}
|
||||
else
|
||||
|
||||
@@ -302,10 +302,10 @@ void LLFloaterWindLight::syncMenu()
|
||||
// blue horizon
|
||||
param_mgr->mBlueHorizon = cur_params.getVector(param_mgr->mBlueHorizon.mName, err);
|
||||
//setColorSwatch("WLBlueHorizon", param_mgr->mBlueHorizon, WL_BLUE_HORIZON_DENSITY_SCALE);
|
||||
childSetValue("WLBlueHorizonR", param_mgr->mBlueHorizon.r);
|
||||
childSetValue("WLBlueHorizonG", param_mgr->mBlueHorizon.g);
|
||||
childSetValue("WLBlueHorizonB", param_mgr->mBlueHorizon.b);
|
||||
childSetValue("WLBlueHorizonI", param_mgr->mBlueHorizon.i);
|
||||
childSetValue("WLBlueHorizonR", param_mgr->mBlueHorizon.r / WL_BLUE_HORIZON_DENSITY_SCALE);
|
||||
childSetValue("WLBlueHorizonG", param_mgr->mBlueHorizon.g / WL_BLUE_HORIZON_DENSITY_SCALE);
|
||||
childSetValue("WLBlueHorizonB", param_mgr->mBlueHorizon.b / WL_BLUE_HORIZON_DENSITY_SCALE);
|
||||
childSetValue("WLBlueHorizonI", param_mgr->mBlueHorizon.i / WL_BLUE_HORIZON_DENSITY_SCALE);
|
||||
|
||||
// haze density, horizon, mult, and altitude
|
||||
param_mgr->mHazeDensity = cur_params.getFloat(param_mgr->mHazeDensity.mName, err);
|
||||
@@ -320,20 +320,20 @@ void LLFloaterWindLight::syncMenu()
|
||||
// blue density
|
||||
param_mgr->mBlueDensity = cur_params.getVector(param_mgr->mBlueDensity.mName, err);
|
||||
//setColorSwatch("WLBlueDensity", param_mgr->mBlueDensity, WL_BLUE_HORIZON_DENSITY_SCALE);
|
||||
childSetValue("WLBlueDensityR", param_mgr->mBlueDensity.r);
|
||||
childSetValue("WLBlueDensityG", param_mgr->mBlueDensity.g);
|
||||
childSetValue("WLBlueDensityB", param_mgr->mBlueDensity.b);
|
||||
childSetValue("WLBlueDensityI", param_mgr->mBlueDensity.i);
|
||||
childSetValue("WLBlueDensityR", param_mgr->mBlueDensity.r / WL_BLUE_HORIZON_DENSITY_SCALE);
|
||||
childSetValue("WLBlueDensityG", param_mgr->mBlueDensity.g / WL_BLUE_HORIZON_DENSITY_SCALE);
|
||||
childSetValue("WLBlueDensityB", param_mgr->mBlueDensity.b / WL_BLUE_HORIZON_DENSITY_SCALE);
|
||||
childSetValue("WLBlueDensityI", param_mgr->mBlueDensity.i / WL_BLUE_HORIZON_DENSITY_SCALE);
|
||||
|
||||
// Lighting
|
||||
|
||||
// sunlight
|
||||
param_mgr->mSunlight = cur_params.getVector(param_mgr->mSunlight.mName, err);
|
||||
//setColorSwatch("WLSunlight", param_mgr->mSunlight, WL_SUN_AMBIENT_SLIDER_SCALE);
|
||||
childSetValue("WLSunlightR", param_mgr->mSunlight.r);
|
||||
childSetValue("WLSunlightG", param_mgr->mSunlight.g);
|
||||
childSetValue("WLSunlightB", param_mgr->mSunlight.b);
|
||||
childSetValue("WLSunlightI", param_mgr->mSunlight.i);
|
||||
childSetValue("WLSunlightR", param_mgr->mSunlight.r / WL_SUN_AMBIENT_SLIDER_SCALE);
|
||||
childSetValue("WLSunlightG", param_mgr->mSunlight.g / WL_SUN_AMBIENT_SLIDER_SCALE);
|
||||
childSetValue("WLSunlightB", param_mgr->mSunlight.b / WL_SUN_AMBIENT_SLIDER_SCALE);
|
||||
childSetValue("WLSunlightI", param_mgr->mSunlight.i / WL_SUN_AMBIENT_SLIDER_SCALE);
|
||||
|
||||
// glow
|
||||
param_mgr->mGlow = cur_params.getVector(param_mgr->mGlow.mName, err);
|
||||
@@ -343,10 +343,10 @@ void LLFloaterWindLight::syncMenu()
|
||||
// ambient
|
||||
param_mgr->mAmbient = cur_params.getVector(param_mgr->mAmbient.mName, err);
|
||||
//setColorSwatch("WLAmbient", param_mgr->mAmbient, WL_SUN_AMBIENT_SLIDER_SCALE);
|
||||
childSetValue("WLAmbientR", param_mgr->mAmbient.r);
|
||||
childSetValue("WLAmbientG", param_mgr->mAmbient.g);
|
||||
childSetValue("WLAmbientB", param_mgr->mAmbient.b);
|
||||
childSetValue("WLAmbientI", param_mgr->mAmbient.i);
|
||||
childSetValue("WLAmbientR", param_mgr->mAmbient.r / WL_SUN_AMBIENT_SLIDER_SCALE);
|
||||
childSetValue("WLAmbientG", param_mgr->mAmbient.g / WL_SUN_AMBIENT_SLIDER_SCALE);
|
||||
childSetValue("WLAmbientB", param_mgr->mAmbient.b / WL_SUN_AMBIENT_SLIDER_SCALE);
|
||||
childSetValue("WLAmbientI", param_mgr->mAmbient.i / WL_SUN_AMBIENT_SLIDER_SCALE);
|
||||
|
||||
childSetValue("WLSunAngle", param_mgr->mCurParams.getFloat("sun_angle",err) / F_TWO_PI);
|
||||
childSetValue("WLEastAngle", param_mgr->mCurParams.getFloat("east_angle",err) / F_TWO_PI);
|
||||
@@ -356,10 +356,10 @@ void LLFloaterWindLight::syncMenu()
|
||||
// Cloud Color
|
||||
param_mgr->mCloudColor = cur_params.getVector(param_mgr->mCloudColor.mName, err);
|
||||
//setColorSwatch("WLCloudColor", param_mgr->mCloudColor, WL_CLOUD_SLIDER_SCALE);
|
||||
childSetValue("WLCloudColorR", param_mgr->mCloudColor.r);
|
||||
childSetValue("WLCloudColorG", param_mgr->mCloudColor.g);
|
||||
childSetValue("WLCloudColorB", param_mgr->mCloudColor.b);
|
||||
childSetValue("WLCloudColorI", param_mgr->mCloudColor.i);
|
||||
childSetValue("WLCloudColorR", param_mgr->mCloudColor.r / WL_CLOUD_SLIDER_SCALE);
|
||||
childSetValue("WLCloudColorG", param_mgr->mCloudColor.g / WL_CLOUD_SLIDER_SCALE);
|
||||
childSetValue("WLCloudColorB", param_mgr->mCloudColor.b / WL_CLOUD_SLIDER_SCALE);
|
||||
childSetValue("WLCloudColorI", param_mgr->mCloudColor.i / WL_CLOUD_SLIDER_SCALE);
|
||||
|
||||
// Cloud
|
||||
param_mgr->mCloudMain = cur_params.getVector(param_mgr->mCloudMain.mName, err);
|
||||
@@ -513,18 +513,7 @@ void LLFloaterWindLight::onColorControlRMoved(LLUICtrl* ctrl, void* userdata)
|
||||
std::string name = color_ctrl->mSliderName;
|
||||
name.append("I");
|
||||
|
||||
if (color_ctrl->isSunOrAmbientColor)
|
||||
{
|
||||
childSetValue(name, color_ctrl->r / WL_SUN_AMBIENT_SLIDER_SCALE);
|
||||
}
|
||||
else if (color_ctrl->isBlueHorizonOrDensity)
|
||||
{
|
||||
childSetValue(name, color_ctrl->r / WL_BLUE_HORIZON_DENSITY_SCALE);
|
||||
}
|
||||
else
|
||||
{
|
||||
childSetValue(name, color_ctrl->r);
|
||||
}
|
||||
childSetValue(name, sldr_ctrl->getValueF32());
|
||||
}
|
||||
|
||||
color_ctrl->update(LLWLParamManager::getInstance()->mCurParams);
|
||||
|
||||
@@ -2010,7 +2010,7 @@ void LLFolderView::scrollToShowSelection()
|
||||
// However we allow scrolling for folder views with mAutoSelectOverride
|
||||
// (used in Places SP) as an exception because the selection in them
|
||||
// is not reset during items filtering. See STORM-133.
|
||||
if ( (!LLInventoryModelBackgroundFetch::instance().folderFetchActive() || mAutoSelectOverride)
|
||||
if ( (LLInventoryModelBackgroundFetch::instance().isEverythingFetched() || mAutoSelectOverride)
|
||||
&& mSelectedItems.size() )
|
||||
{
|
||||
mNeedsScroll = TRUE;
|
||||
|
||||
@@ -54,7 +54,6 @@
|
||||
|
||||
#include "hippogridmanager.h"
|
||||
|
||||
#include <boost/lexical_cast.hpp>
|
||||
///----------------------------------------------------------------------------
|
||||
/// Local function declarations, constants, enums, and typedefs
|
||||
///----------------------------------------------------------------------------
|
||||
@@ -97,7 +96,7 @@ LLFloaterPay::LLFloaterPay(const std::string& name,
|
||||
|
||||
for(U32 i = 0; i < MAX_PAY_BUTTONS; ++i)
|
||||
{
|
||||
mQuickPayButton[i] = getChild<LLButton>("fastpay " + boost::lexical_cast<std::string>(mQuickPayInfo[i]));
|
||||
mQuickPayButton[i] = getChild<LLButton>("fastpay " + fmt::to_string(mQuickPayInfo[i]));
|
||||
mQuickPayButton[i]->setClickedCallback(boost::bind(&LLFloaterPay::onGive,this,boost::ref(mQuickPayInfo[i])));
|
||||
mQuickPayButton[i]->setVisible(FALSE);
|
||||
mQuickPayButton[i]->setLabelArg("[CURRENCY]", gHippoGridManager->getConnectedGrid()->getCurrencySymbol());
|
||||
|
||||
@@ -94,7 +94,7 @@ void LLHUDIcon::renderIcon(BOOL for_select)
|
||||
if (mHidden)
|
||||
return;
|
||||
|
||||
if (mSourceObject.isNull() || mImagep.isNull())
|
||||
if (mSourceObject.isNull() || mImagep.isNull() || mSourceObject->mDrawable.isNull())
|
||||
{
|
||||
markDead();
|
||||
return;
|
||||
|
||||
@@ -375,9 +375,7 @@ LLFloaterIMPanel::LLFloaterIMPanel(
|
||||
|
||||
if ( gSavedPerAccountSettings.getBOOL("LogShowHistory") )
|
||||
{
|
||||
LLLogChat::loadHistory(mLogLabel,
|
||||
&chatFromLogFile,
|
||||
(void *)this);
|
||||
LLLogChat::loadHistory(mLogLabel, mSessionType == P2P_SESSION ? mOtherParticipantUUID : mSessionUUID, boost::bind(&LLFloaterIMPanel::chatFromLogFile, this, _1, _2));
|
||||
}
|
||||
|
||||
if ( !mSessionInitialized )
|
||||
@@ -801,7 +799,7 @@ void LLFloaterIMPanel::addHistoryLine(const std::string &utf8msg, LLColor4 incol
|
||||
// Now we're adding the actual line of text, so erase the
|
||||
// "Foo is typing..." text segment, and the optional timestamp
|
||||
// if it was present. JC
|
||||
removeTypingIndicator(NULL);
|
||||
removeTypingIndicator(source);
|
||||
|
||||
// Actually add the line
|
||||
bool prepend_newline = true;
|
||||
@@ -861,7 +859,7 @@ void LLFloaterIMPanel::addHistoryLine(const std::string &utf8msg, LLColor4 incol
|
||||
// Floater title contains display name -> bad idea to use that as filename
|
||||
// mLogLabel, however, is the old legacy name
|
||||
//LLLogChat::saveHistory(getTitle(),histstr);
|
||||
LLLogChat::saveHistory(mLogLabel, histstr);
|
||||
LLLogChat::saveHistory(mLogLabel, mSessionType == P2P_SESSION ? mOtherParticipantUUID : mSessionUUID, histstr);
|
||||
// [/Ansariel: Display name support]
|
||||
}
|
||||
|
||||
@@ -1179,9 +1177,9 @@ void LLFloaterIMPanel::onFlyoutCommit(LLComboBox* flyout, const LLSD& value)
|
||||
}
|
||||
}
|
||||
|
||||
void show_log_browser(const std::string& name, const std::string& id)
|
||||
void show_log_browser(const std::string& name, const LLUUID& id)
|
||||
{
|
||||
const std::string file(LLLogChat::makeLogFileName(name));
|
||||
const std::string file(LLLogChat::makeLogFileName(name, id));
|
||||
if (!LLFile::isfile(file))
|
||||
{
|
||||
make_ui_sound("UISndBadKeystroke");
|
||||
@@ -1195,7 +1193,7 @@ void show_log_browser(const std::string& name, const std::string& id)
|
||||
}
|
||||
LLFloaterWebContent::Params p;
|
||||
p.url("file:///" + file);
|
||||
p.id(id);
|
||||
p.id(id.asString());
|
||||
p.show_chrome(false);
|
||||
p.trusted_content(true);
|
||||
LLFloaterWebContent::showInstance("log", p); // If we passed id instead of "log", there would be no control over how many log browsers opened at once.
|
||||
@@ -1206,8 +1204,8 @@ void LLFloaterIMPanel::onClickHistory()
|
||||
if (mOtherParticipantUUID.notNull())
|
||||
{
|
||||
// [Ansariel: Display name support]
|
||||
//show_log_browser(getTitle(), mOtherParticipantUUID.asString());
|
||||
show_log_browser(mLogLabel, mOtherParticipantUUID.asString());
|
||||
//show_log_browser(getTitle(), mSessionType == P2P_SESSION ? mOtherParticipantUUID : mSessionUUID);
|
||||
show_log_browser(mLogLabel, mSessionType == P2P_SESSION ? mOtherParticipantUUID : mSessionUUID);
|
||||
// [/Ansariel: Display name support]
|
||||
}
|
||||
}
|
||||
@@ -1458,7 +1456,7 @@ void LLFloaterIMPanel::onSendMsg()
|
||||
|
||||
bool other_was_typing = mOtherTyping;
|
||||
addHistoryLine(utf8_text, gSavedSettings.getColor("UserChatColor"), true, gAgentID, name);
|
||||
if (other_was_typing) addTypingIndicator(mOtherTypingName);
|
||||
if (other_was_typing) addTypingIndicator(mOtherParticipantUUID);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -1588,90 +1586,99 @@ void LLFloaterIMPanel::sendTypingState(bool typing)
|
||||
}
|
||||
|
||||
|
||||
void LLFloaterIMPanel::processIMTyping(const LLIMInfo* im_info, bool typing)
|
||||
void LLFloaterIMPanel::processIMTyping(const LLUUID& from_id, BOOL typing)
|
||||
{
|
||||
if (typing)
|
||||
{
|
||||
// other user started typing
|
||||
std::string name;
|
||||
if (!LLAvatarNameCache::getNSName(im_info->mFromID, name)) name = im_info->mName;
|
||||
addTypingIndicator(name);
|
||||
addTypingIndicator(from_id);
|
||||
}
|
||||
else
|
||||
{
|
||||
// other user stopped typing
|
||||
removeTypingIndicator(im_info);
|
||||
removeTypingIndicator(from_id);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void LLFloaterIMPanel::addTypingIndicator(const std::string &name)
|
||||
void LLFloaterIMPanel::addTypingIndicator(const LLUUID& from_id)
|
||||
{
|
||||
// we may have lost a "stop-typing" packet, don't add it twice
|
||||
if (!mOtherTyping)
|
||||
// Singu TODO: Actually implement this?
|
||||
/* Operation of "<name> is typing" state machine:
|
||||
Not Typing state:
|
||||
|
||||
User types in P2P IM chat ... Send Start Typing, save Started time,
|
||||
start Idle Timer (N seconds) go to Typing state
|
||||
|
||||
Typing State:
|
||||
|
||||
User enters a non-return character: if Now - Started > ME_TYPING_TIMEOUT, send
|
||||
Start Typing, restart Idle Timer
|
||||
User enters a return character: stop Idle Timer, send IM and Stop
|
||||
Typing, go to Not Typing state
|
||||
Idle Timer expires: send Stop Typing, go to Not Typing state
|
||||
|
||||
The recipient has a complementary state machine in which a Start Typing
|
||||
that is not followed by either an IM or another Start Typing within OTHER_TYPING_TIMEOUT
|
||||
seconds switches the sender out of typing state.
|
||||
|
||||
This has the nice quality of being self-healing for lost start/stop
|
||||
messages while adding messages only for the (relatively rare) case of a
|
||||
user who types a very long message (one that takes more than ME_TYPING_TIMEOUT seconds
|
||||
to type).
|
||||
|
||||
Note: OTHER_TYPING_TIMEOUT must be > ME_TYPING_TIMEOUT for proper operation of the state machine
|
||||
|
||||
*/
|
||||
|
||||
// We may have lost a "stop-typing" packet, don't add it twice
|
||||
if (from_id.notNull() && !mOtherTyping)
|
||||
{
|
||||
mOtherTyping = true;
|
||||
// Save im_info so that removeTypingIndicator can be properly called because a timeout has occurred
|
||||
LLAvatarNameCache::getNSName(from_id, mOtherTypingName);
|
||||
|
||||
mTypingLineStartIndex = mHistoryEditor->getWText().length();
|
||||
LLUIString typing_start = sTypingStartString;
|
||||
typing_start.setArg("[NAME]", name);
|
||||
typing_start.setArg("[NAME]", mOtherTypingName);
|
||||
addHistoryLine(typing_start, gSavedSettings.getColor4("SystemChatColor"), false);
|
||||
mOtherTypingName = name;
|
||||
mOtherTyping = true;
|
||||
|
||||
// Update speaker
|
||||
LLIMSpeakerMgr* speaker_mgr = mSpeakers;
|
||||
if ( speaker_mgr )
|
||||
{
|
||||
speaker_mgr->setSpeakerTyping(from_id, TRUE);
|
||||
}
|
||||
mOtherTyping = true; // addHistoryLine clears this flag. Set it again.
|
||||
}
|
||||
// MBW -- XXX -- merge from release broke this (argument to this function changed from an LLIMInfo to a name)
|
||||
// Richard will fix.
|
||||
// mSpeakers->setSpeakerTyping(im_info->mFromID, TRUE);
|
||||
}
|
||||
|
||||
|
||||
void LLFloaterIMPanel::removeTypingIndicator(const LLIMInfo* im_info)
|
||||
void LLFloaterIMPanel::removeTypingIndicator(const LLUUID& from_id)
|
||||
{
|
||||
if (mOtherTyping)
|
||||
{
|
||||
// Must do this first, otherwise addHistoryLine calls us again.
|
||||
mOtherTyping = false;
|
||||
|
||||
S32 chars_to_remove = mHistoryEditor->getWText().length() - mTypingLineStartIndex;
|
||||
mHistoryEditor->removeTextFromEnd(chars_to_remove);
|
||||
if (im_info)
|
||||
|
||||
if (from_id.notNull())
|
||||
{
|
||||
mSpeakers->setSpeakerTyping(im_info->mFromID, FALSE);
|
||||
mSpeakers->setSpeakerTyping(from_id, FALSE);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//static
|
||||
void LLFloaterIMPanel::chatFromLogFile(LLLogChat::ELogLineType type, std::string line, void* userdata)
|
||||
void LLFloaterIMPanel::chatFromLogFile(LLLogChat::ELogLineType type, const std::string& line)
|
||||
{
|
||||
LLFloaterIMPanel* self = (LLFloaterIMPanel*)userdata;
|
||||
std::string message = line;
|
||||
|
||||
switch (type)
|
||||
bool log_line = type == LLLogChat::LOG_LINE;
|
||||
if (log_line || gSavedPerAccountSettings.getBOOL("LogInstantMessages"))
|
||||
{
|
||||
case LLLogChat::LOG_EMPTY:
|
||||
// add warning log enabled message
|
||||
if (gSavedPerAccountSettings.getBOOL("LogInstantMessages"))
|
||||
{
|
||||
message = LLFloaterChat::getInstance()->getString("IM_logging_string");
|
||||
}
|
||||
break;
|
||||
case LLLogChat::LOG_END:
|
||||
// add log end message
|
||||
if (gSavedPerAccountSettings.getBOOL("LogInstantMessages"))
|
||||
{
|
||||
message = LLFloaterChat::getInstance()->getString("IM_end_log_string");
|
||||
}
|
||||
break;
|
||||
case LLLogChat::LOG_LINE:
|
||||
// just add normal lines from file
|
||||
break;
|
||||
default:
|
||||
// nothing
|
||||
break;
|
||||
LLStyleSP style(new LLStyle(true, gSavedSettings.getColor4("LogChatColor"), LLStringUtil::null));
|
||||
mHistoryEditor->appendText(log_line ? line :
|
||||
getString(type == LLLogChat::LOG_END ? "IM_end_log_string" : "IM_logging_string"),
|
||||
false, true, style, false);
|
||||
}
|
||||
|
||||
//self->addHistoryLine(line, LLColor4::grey, FALSE);
|
||||
LLStyleSP style(new LLStyle(true, gSavedSettings.getColor4("LogChatColor"), LLStringUtil::null));
|
||||
self->mHistoryEditor->appendText(message, false, true, style, false);
|
||||
}
|
||||
|
||||
void LLFloaterIMPanel::showSessionStartError(
|
||||
|
||||
@@ -39,7 +39,6 @@
|
||||
|
||||
class LLAvatarName;
|
||||
class LLIMSpeakerMgr;
|
||||
class LLIMInfo;
|
||||
class LLInventoryCategory;
|
||||
class LLInventoryItem;
|
||||
class LLLineEditor;
|
||||
@@ -126,8 +125,8 @@ public:
|
||||
void sessionInitReplyReceived(const LLUUID& im_session_id);
|
||||
|
||||
// Handle other participant in the session typing.
|
||||
void processIMTyping(const LLIMInfo* im_info, bool typing);
|
||||
static void chatFromLogFile(LLLogChat::ELogLineType type, std::string line, void* userdata);
|
||||
void processIMTyping(const LLUUID& from_id, BOOL typing);
|
||||
void chatFromLogFile(LLLogChat::ELogLineType type, const std::string& line);
|
||||
|
||||
//show error statuses to the user
|
||||
void showSessionStartError(const std::string& error_string);
|
||||
@@ -177,10 +176,10 @@ private:
|
||||
void setTyping(bool typing);
|
||||
|
||||
// Add the "User is typing..." indicator.
|
||||
void addTypingIndicator(const std::string &name);
|
||||
void addTypingIndicator(const LLUUID& from_id);
|
||||
|
||||
// Remove the "User is typing..." indicator.
|
||||
void removeTypingIndicator(const LLIMInfo* im_info);
|
||||
void removeTypingIndicator(const LLUUID& from_id = LLUUID::null);
|
||||
|
||||
void sendTypingState(bool typing);
|
||||
|
||||
|
||||
@@ -560,7 +560,7 @@ void LLIMProcessing::processNewMessage(const LLUUID& from_id,
|
||||
chat.mFromID = from_id;
|
||||
chat.mFromName = name;
|
||||
chat.mSourceType = (from_id.isNull() || (name == SYSTEM_FROM)) ? CHAT_SOURCE_SYSTEM :
|
||||
(dialog == IM_FROM_TASK && dialog == IM_FROM_TASK_AS_ALERT) ? CHAT_SOURCE_OBJECT : CHAT_SOURCE_AGENT;
|
||||
(dialog == IM_FROM_TASK || dialog == IM_FROM_TASK_AS_ALERT) ? CHAT_SOURCE_OBJECT : CHAT_SOURCE_AGENT;
|
||||
|
||||
bool is_muted = LLMuteList::getInstance()->isMuted(from_id, name, LLMute::flagTextChat)
|
||||
// object IMs contain sender object id in session_id (STORM-1209)
|
||||
@@ -641,8 +641,7 @@ void LLIMProcessing::processNewMessage(const LLUUID& from_id,
|
||||
{
|
||||
RlvUtil::sendBusyMessage(from_id, RlvStrings::getVersion(), session_id);
|
||||
// We won't receive a typing stop message, so do that manually (see comment at the end of LLFloaterIMPanel::sendMsg)
|
||||
LLPointer<LLIMInfo> im_info = new LLIMInfo(gMessageSystem);
|
||||
gIMMgr->processIMTypingStop(im_info);
|
||||
gIMMgr->processIMTypingStop(from_id, dialog);
|
||||
}
|
||||
// [/RLVa:KB]
|
||||
else if (offline == IM_ONLINE
|
||||
@@ -918,16 +917,15 @@ void LLIMProcessing::processNewMessage(const LLUUID& from_id,
|
||||
autoresponder_finish(show_autoresponded, session_id, from_id, name, itemid, is_muted);
|
||||
}
|
||||
}
|
||||
LLPointer<LLIMInfo> im_info = new LLIMInfo(gMessageSystem);
|
||||
gIMMgr->processIMTypingStart(im_info);
|
||||
|
||||
gIMMgr->processIMTypingStart(from_id, dialog);
|
||||
script_msg_api(from_id.asString() + ", 4");
|
||||
}
|
||||
break;
|
||||
|
||||
case IM_TYPING_STOP:
|
||||
{
|
||||
LLPointer<LLIMInfo> im_info = new LLIMInfo(gMessageSystem);
|
||||
gIMMgr->processIMTypingStop(im_info);
|
||||
gIMMgr->processIMTypingStop(from_id, dialog);
|
||||
script_msg_api(from_id.asString() + ", 5");
|
||||
}
|
||||
break;
|
||||
@@ -1198,41 +1196,41 @@ void LLIMProcessing::processNewMessage(const LLUUID& from_id,
|
||||
}
|
||||
else // IM_TASK_INVENTORY_OFFERED
|
||||
{
|
||||
if (offline == IM_OFFLINE && session_id.isNull() && aux_id.notNull() && binary_bucket_size > sizeof(S8)* 5)
|
||||
if (sizeof(S8) == binary_bucket_size)
|
||||
{
|
||||
// cap received offline message
|
||||
std::string str_bucket = ll_safe_string((char*)binary_bucket, binary_bucket_size);
|
||||
typedef boost::tokenizer<boost::char_separator<char> > tokenizer;
|
||||
boost::char_separator<char> sep("|", "", boost::keep_empty_tokens);
|
||||
tokenizer tokens(str_bucket, sep);
|
||||
tokenizer::iterator iter = tokens.begin();
|
||||
|
||||
info->mType = (LLAssetType::EType)(atoi((*(iter++)).c_str()));
|
||||
// Note There is more elements in 'tokens' ...
|
||||
|
||||
info->mObjectID = LLUUID::null;
|
||||
info->mFromObject = TRUE;
|
||||
info->mType = (LLAssetType::EType) binary_bucket[0];
|
||||
}
|
||||
else
|
||||
{
|
||||
if (sizeof(S8) != binary_bucket_size)
|
||||
{
|
||||
LL_WARNS("Messaging") << "Malformed inventory offer from object" << LL_ENDL;
|
||||
delete info;
|
||||
break;
|
||||
}
|
||||
info->mType = (LLAssetType::EType) binary_bucket[0];
|
||||
info->mObjectID = LLUUID::null;
|
||||
info->mFromObject = TRUE;
|
||||
}
|
||||
/*RIDER*/ // The previous version of the protocol returned the wrong binary bucket... we
|
||||
// still might be able to figure out the type... even though the offer is not retrievable.
|
||||
|
||||
// Should be safe to remove once DRTSIM-451 fully deploys
|
||||
std::string str_bucket(reinterpret_cast<char *>(binary_bucket));
|
||||
std::string str_type(str_bucket.substr(0, str_bucket.find('|')));
|
||||
|
||||
std::stringstream type_convert(str_type);
|
||||
|
||||
S32 type;
|
||||
type_convert >> type;
|
||||
|
||||
// We could try AT_UNKNOWN which would be more accurate, but that causes an auto decline
|
||||
info->mType = static_cast<LLAssetType::EType>(type);
|
||||
// Don't break in the case of a bad binary bucket. Go ahead and show the
|
||||
// accept/decline popup even though it will not do anything.
|
||||
LL_WARNS("Messaging") << "Malformed inventory offer from object, type might be " << info->mType << LL_ENDL;
|
||||
}
|
||||
info->mObjectID = LLUUID::null;
|
||||
info->mFromObject = TRUE;
|
||||
}
|
||||
|
||||
info->mIM = dialog;
|
||||
info->mFromID = from_id;
|
||||
info->mFromGroup = from_group;
|
||||
info->mTransactionID = session_id;
|
||||
info->mFolderID = gInventory.findCategoryUUIDForType(LLFolderType::assetTypeToFolderType(info->mType));
|
||||
|
||||
info->mTransactionID = session_id.notNull() ? session_id : aux_id;
|
||||
|
||||
info->mFromName = name;
|
||||
info->mDesc = message;
|
||||
info->mHost = sender;
|
||||
@@ -1897,6 +1895,11 @@ void LLIMProcessing::requestOfflineMessages()
|
||||
|
||||
void LLIMProcessing::requestOfflineMessagesCoro(const LLCoroResponder& responder)
|
||||
{
|
||||
if (LLApp::isQuitting() || !gAgent.getRegion())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
auto status = responder.getStatus();
|
||||
|
||||
if (!responder.isGoodStatus(status)) // success = httpResults["success"].asBoolean();
|
||||
@@ -1945,8 +1948,6 @@ void LLIMProcessing::requestOfflineMessagesCoro(const LLCoroResponder& responder
|
||||
|
||||
LL_INFOS("Messaging") << "Processing offline messages." << LL_ENDL;
|
||||
|
||||
std::vector<U8> data;
|
||||
S32 binary_bucket_size = 0;
|
||||
LLHost sender = gAgent.getRegion()->getHost();
|
||||
|
||||
LLSD::array_iterator i = messages.beginArray();
|
||||
@@ -1955,12 +1956,31 @@ void LLIMProcessing::requestOfflineMessagesCoro(const LLCoroResponder& responder
|
||||
{
|
||||
const LLSD &message_data(*i);
|
||||
|
||||
LLVector3 position(message_data["local_x"].asReal(), message_data["local_y"].asReal(), message_data["local_z"].asReal());
|
||||
data = message_data["binary_bucket"].asBinary();
|
||||
binary_bucket_size = data.size(); // message_data["count"] always 0
|
||||
U32 parent_estate_id = message_data.has("parent_estate_id") ? message_data["parent_estate_id"].asInteger() : 1; // 1 - IMMainland
|
||||
/* RIDER: Many fields in this message are using a '_' rather than the standard '-'. This
|
||||
* should be changed but would require tight coordination with the simulator.
|
||||
*/
|
||||
LLVector3 position;
|
||||
if (message_data.has("position"))
|
||||
{
|
||||
position.setValue(message_data["position"]);
|
||||
}
|
||||
else
|
||||
{
|
||||
position.set(message_data["local_x"].asReal(), message_data["local_y"].asReal(), message_data["local_z"].asReal());
|
||||
}
|
||||
|
||||
// Todo: once dirtsim-369 releases, remove one of the int/str options
|
||||
std::vector<U8> bin_bucket;
|
||||
if (message_data.has("binary_bucket"))
|
||||
{
|
||||
bin_bucket = message_data["binary_bucket"].asBinary();
|
||||
}
|
||||
#if 0
|
||||
else
|
||||
{
|
||||
bin_bucket.push_back(0);
|
||||
}
|
||||
#endif
|
||||
// Todo: once drtsim-451 releases, remove the string option
|
||||
BOOL from_group;
|
||||
if (message_data["from_group"].isInteger())
|
||||
{
|
||||
@@ -1973,20 +1993,21 @@ void LLIMProcessing::requestOfflineMessagesCoro(const LLCoroResponder& responder
|
||||
|
||||
auto agentName = message_data["from_agent_name"].asString();
|
||||
auto message = message_data["message"].asString();
|
||||
LLIMProcessing::processNewMessage(message_data["from_agent_id"].asUUID(),
|
||||
LLIMProcessing::processNewMessage(
|
||||
message_data["from_agent_id"].asUUID(),
|
||||
from_group,
|
||||
message_data["to_agent_id"].asUUID(),
|
||||
IM_OFFLINE,
|
||||
(EInstantMessage)message_data["dialog"].asInteger(),
|
||||
LLUUID::null, // session id, since there is none we can only use frienship/group invite caps
|
||||
message_data["timestamp"].asInteger(),
|
||||
message_data.has("offline") ? static_cast<U8>(message_data["offline"].asInteger()) : IM_OFFLINE,
|
||||
static_cast<EInstantMessage>(message_data["dialog"].asInteger()),
|
||||
message_data["transaction-id"].asUUID(),
|
||||
static_cast<U32>(message_data["timestamp"].asInteger()),
|
||||
agentName,
|
||||
message,
|
||||
parent_estate_id,
|
||||
message_data.has("parent_estate_id") ? static_cast<U32>(message_data["parent_estate_id"].asInteger()) : 1U, // 1 - IMMainland
|
||||
message_data["region_id"].asUUID(),
|
||||
position,
|
||||
&data[0],
|
||||
binary_bucket_size,
|
||||
bin_bucket.data(),
|
||||
bin_bucket.size(),
|
||||
sender,
|
||||
message_data["asset_id"].asUUID()); // not necessarily an asset
|
||||
}
|
||||
|
||||
@@ -1138,23 +1138,23 @@ void LLIMMgr::noteMutedUsers(LLFloaterIMPanel* floater,
|
||||
}
|
||||
}
|
||||
|
||||
void LLIMMgr::processIMTypingStart(const LLIMInfo* im_info)
|
||||
void LLIMMgr::processIMTypingStart(const LLUUID& from_id, const EInstantMessage im_type)
|
||||
{
|
||||
processIMTypingCore(im_info, TRUE);
|
||||
processIMTypingCore(from_id, im_type, TRUE);
|
||||
}
|
||||
|
||||
void LLIMMgr::processIMTypingStop(const LLIMInfo* im_info)
|
||||
void LLIMMgr::processIMTypingStop(const LLUUID& from_id, const EInstantMessage im_type)
|
||||
{
|
||||
processIMTypingCore(im_info, FALSE);
|
||||
processIMTypingCore(from_id, im_type, FALSE);
|
||||
}
|
||||
|
||||
void LLIMMgr::processIMTypingCore(const LLIMInfo* im_info, BOOL typing)
|
||||
void LLIMMgr::processIMTypingCore(const LLUUID& from_id, const EInstantMessage im_type, BOOL typing)
|
||||
{
|
||||
LLUUID session_id = computeSessionID(im_info->mIMType, im_info->mFromID);
|
||||
LLFloaterIMPanel* floater = findFloaterBySession(session_id);
|
||||
if (floater)
|
||||
LLUUID session_id = computeSessionID(im_type, from_id);
|
||||
LLFloaterIMPanel* im_floater = findFloaterBySession(session_id);
|
||||
if (im_floater)
|
||||
{
|
||||
floater->processIMTyping(im_info, typing);
|
||||
im_floater->processIMTyping(from_id, typing);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1275,10 +1275,10 @@ LLFloaterChatterBox* LLIMMgr::getFloater()
|
||||
return LLFloaterChatterBox::getInstance(LLSD());
|
||||
}
|
||||
|
||||
class LLViewerChatterBoxSessionStartReply : public LLHTTPNode
|
||||
class LLViewerChatterBoxSessionStartReply final : public LLHTTPNode
|
||||
{
|
||||
public:
|
||||
virtual void describe(Description& desc) const
|
||||
void describe(Description& desc) const override
|
||||
{
|
||||
desc.shortInfo("Used for receiving a reply to a request to initialize an ChatterBox session");
|
||||
desc.postAPI();
|
||||
@@ -1287,18 +1287,15 @@ public:
|
||||
desc.source(__FILE__, __LINE__);
|
||||
}
|
||||
|
||||
virtual void post(ResponsePtr response,
|
||||
void post(ResponsePtr response,
|
||||
const LLSD& context,
|
||||
const LLSD& input) const
|
||||
const LLSD& input) const override
|
||||
{
|
||||
LLSD body;
|
||||
LLUUID temp_session_id;
|
||||
LLUUID session_id;
|
||||
bool success;
|
||||
|
||||
body = input["body"];
|
||||
success = body["success"].asBoolean();
|
||||
temp_session_id = body["temp_session_id"].asUUID();
|
||||
LLSD body = input["body"];
|
||||
bool success = body["success"].asBoolean();
|
||||
LLUUID temp_session_id = body["temp_session_id"].asUUID();
|
||||
|
||||
if ( success )
|
||||
{
|
||||
@@ -1336,10 +1333,10 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
class LLViewerChatterBoxSessionEventReply : public LLHTTPNode
|
||||
class LLViewerChatterBoxSessionEventReply final : public LLHTTPNode
|
||||
{
|
||||
public:
|
||||
virtual void describe(Description& desc) const
|
||||
void describe(Description& desc) const override
|
||||
{
|
||||
desc.shortInfo("Used for receiving a reply to a ChatterBox session event");
|
||||
desc.postAPI();
|
||||
@@ -1348,24 +1345,18 @@ public:
|
||||
desc.source(__FILE__, __LINE__);
|
||||
}
|
||||
|
||||
virtual void post(ResponsePtr response,
|
||||
void post(ResponsePtr response,
|
||||
const LLSD& context,
|
||||
const LLSD& input) const
|
||||
const LLSD& input) const override
|
||||
{
|
||||
LLUUID session_id;
|
||||
bool success;
|
||||
|
||||
LLSD body = input["body"];
|
||||
success = body["success"].asBoolean();
|
||||
session_id = body["session_id"].asUUID();
|
||||
bool success = body["success"].asBoolean();
|
||||
LLUUID session_id = body["session_id"].asUUID();
|
||||
|
||||
if ( !success )
|
||||
{
|
||||
//throw an error dialog
|
||||
LLFloaterIMPanel* floater =
|
||||
gIMMgr->findFloaterBySession(session_id);
|
||||
|
||||
if (floater)
|
||||
if (auto* floater = gIMMgr->findFloaterBySession(session_id))
|
||||
{
|
||||
floater->showSessionEventError(
|
||||
body["event"].asString(),
|
||||
@@ -1378,46 +1369,40 @@ public:
|
||||
class LLViewerForceCloseChatterBoxSession: public LLHTTPNode
|
||||
{
|
||||
public:
|
||||
virtual void post(ResponsePtr response,
|
||||
void post(ResponsePtr response,
|
||||
const LLSD& context,
|
||||
const LLSD& input) const
|
||||
const LLSD& input) const override
|
||||
{
|
||||
LLUUID session_id;
|
||||
std::string reason;
|
||||
LLUUID session_id = input["body"]["session_id"].asUUID();
|
||||
std::string reason = input["body"]["reason"].asString();
|
||||
|
||||
session_id = input["body"]["session_id"].asUUID();
|
||||
reason = input["body"]["reason"].asString();
|
||||
|
||||
LLFloaterIMPanel* floater =
|
||||
gIMMgr ->findFloaterBySession(session_id);
|
||||
|
||||
if ( floater )
|
||||
if (auto* floater = gIMMgr ->findFloaterBySession(session_id))
|
||||
{
|
||||
floater->showSessionForceClose(reason);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
class LLViewerChatterBoxSessionAgentListUpdates : public LLHTTPNode
|
||||
class LLViewerChatterBoxSessionAgentListUpdates final : public LLHTTPNode
|
||||
{
|
||||
public:
|
||||
virtual void post(
|
||||
void post(
|
||||
ResponsePtr responder,
|
||||
const LLSD& context,
|
||||
const LLSD& input) const
|
||||
const LLSD& input) const override
|
||||
{
|
||||
const LLUUID& session_id = input["body"]["session_id"].asUUID();
|
||||
gIMMgr->processAgentListUpdates(session_id, input["body"]);
|
||||
}
|
||||
};
|
||||
|
||||
class LLViewerChatterBoxSessionUpdate : public LLHTTPNode
|
||||
class LLViewerChatterBoxSessionUpdate final : public LLHTTPNode
|
||||
{
|
||||
public:
|
||||
virtual void post(
|
||||
void post(
|
||||
ResponsePtr responder,
|
||||
const LLSD& context,
|
||||
const LLSD& input) const
|
||||
const LLSD& input) const override
|
||||
{
|
||||
LLUUID session_id = input["body"]["session_id"].asUUID();
|
||||
LLFloaterIMPanel* im_floater = gIMMgr->findFloaterBySession(session_id);
|
||||
@@ -1445,14 +1430,14 @@ void leave_group_chat(const LLUUID& from_id, const LLUUID& session_id)
|
||||
gIMMgr->removeSession(session_id);
|
||||
}
|
||||
|
||||
class LLViewerChatterBoxInvitation : public LLHTTPNode
|
||||
class LLViewerChatterBoxInvitation final : public LLHTTPNode
|
||||
{
|
||||
public:
|
||||
|
||||
virtual void post(
|
||||
void post(
|
||||
ResponsePtr response,
|
||||
const LLSD& context,
|
||||
const LLSD& input) const
|
||||
const LLSD& input) const override
|
||||
{
|
||||
//for backwards compatiblity reasons...we need to still
|
||||
//check for 'text' or 'voice' invitations...bleh
|
||||
@@ -1582,10 +1567,9 @@ public:
|
||||
LLFloaterChat::addChat(chat, TRUE, is_this_agent);
|
||||
|
||||
//K now we want to accept the invitation
|
||||
std::string url = gAgent.getRegion()->getCapability(
|
||||
"ChatSessionRequest");
|
||||
std::string url = gAgent.getRegionCapability("ChatSessionRequest");
|
||||
|
||||
if ( url != "" )
|
||||
if (!url.empty())
|
||||
{
|
||||
LLSD data;
|
||||
data["method"] = "accept invitation";
|
||||
|
||||
@@ -42,7 +42,7 @@
|
||||
class LLFloaterChatterBox;
|
||||
class LLFloaterIMPanel;
|
||||
|
||||
class LLIMMgr : public LLSingleton<LLIMMgr>
|
||||
class LLIMMgr final : public LLSingleton<LLIMMgr>
|
||||
{
|
||||
public:
|
||||
enum EInvitationType
|
||||
@@ -121,8 +121,8 @@ public:
|
||||
void updateFloaterSessionID(const LLUUID& old_session_id,
|
||||
const LLUUID& new_session_id);
|
||||
|
||||
void processIMTypingStart(const LLIMInfo* im_info);
|
||||
void processIMTypingStop(const LLIMInfo* im_info);
|
||||
void processIMTypingStart(const LLUUID& from_id, const EInstantMessage im_type);
|
||||
void processIMTypingStop(const LLUUID& from_id, const EInstantMessage im_type);
|
||||
|
||||
void clearNewIMNotification();
|
||||
|
||||
@@ -209,7 +209,7 @@ private:
|
||||
void noteOfflineUsers(LLFloaterIMPanel* panel, const uuid_vec_t& ids);
|
||||
void noteMutedUsers(LLFloaterIMPanel* panel, const uuid_vec_t& ids);
|
||||
|
||||
void processIMTypingCore(const LLIMInfo* im_info, BOOL typing);
|
||||
void processIMTypingCore(const LLUUID& from_id, const EInstantMessage im_type, BOOL typing);
|
||||
|
||||
private:
|
||||
std::set<LLHandle<LLFloater> > mFloaters;
|
||||
|
||||
@@ -3152,7 +3152,7 @@ void LLFolderBridge::performAction(LLInventoryModel* model, std::string action)
|
||||
else if ("marketplace_copy_id" == action)
|
||||
{
|
||||
auto id = LLMarketplaceData::instance().getListingID(mUUID);
|
||||
gViewerWindow->getWindow()->copyTextToClipboard(utf8str_to_wstring(std::to_string(id)));
|
||||
gViewerWindow->getWindow()->copyTextToClipboard(utf8str_to_wstring(fmt::to_string(id)));
|
||||
}
|
||||
// <singu> Move displaced inventory to lost and found
|
||||
else if ("move_to_lost_and_found" == action)
|
||||
@@ -3889,6 +3889,9 @@ void build_context_menu_folder_options(LLInventoryModel* model, const LLUUID& mU
|
||||
const LLInventoryCategory* category = model->getCategory(mUUID);
|
||||
if(!category) return;
|
||||
|
||||
items.push_back(std::string("Open Folder In New Window"));
|
||||
items.push_back(std::string("Copy Folder UUID"));
|
||||
|
||||
const LLUUID trash_id = model->findCategoryUUIDForType(LLFolderType::FT_TRASH);
|
||||
if (trash_id == mUUID) return;
|
||||
if (model->isObjectDescendentOf(mUUID, trash_id)) return;
|
||||
@@ -3902,9 +3905,6 @@ void build_context_menu_folder_options(LLInventoryModel* model, const LLUUID& mU
|
||||
const LLUUID listings_folder = gInventory.findCategoryUUIDForType(LLFolderType::FT_MARKETPLACE_LISTINGS, false);
|
||||
if (listings_folder.notNull() && gInventory.isObjectDescendentOf(mUUID, listings_folder)) return;
|
||||
|
||||
items.push_back(std::string("Open Folder In New Window"));
|
||||
items.push_back(std::string("Copy Folder UUID"));
|
||||
|
||||
LLFolderType::EType type = category->getPreferredType();
|
||||
const bool is_system_folder = LLFolderType::lookupIsProtectedType(type);
|
||||
// calling card related functionality for folders.
|
||||
|
||||
@@ -36,35 +36,132 @@
|
||||
#include "lllogchat.h"
|
||||
#include "llappviewer.h"
|
||||
#include "llfloaterchat.h"
|
||||
#include "llsdserialize.h"
|
||||
|
||||
static std::string get_log_dir_file(const std::string& filename)
|
||||
{
|
||||
return gDirUtilp->getExpandedFilename(LL_PATH_PER_ACCOUNT_CHAT_LOGS, filename);
|
||||
}
|
||||
|
||||
//static
|
||||
std::string LLLogChat::makeLogFileName(std::string filename)
|
||||
std::string LLLogChat::makeLogFileNameInternal(std::string filename)
|
||||
{
|
||||
if (gSavedPerAccountSettings.getBOOL("LogFileNamewithDate"))
|
||||
static const LLCachedControl<bool> with_date(gSavedPerAccountSettings, "LogFileNamewithDate");
|
||||
if (with_date)
|
||||
{
|
||||
time_t now;
|
||||
time(&now);
|
||||
char dbuffer[100]; /* Flawfinder: ignore */
|
||||
if (filename == "chat")
|
||||
{
|
||||
static const LLCachedControl<std::string> local_chat_date_format(gSavedPerAccountSettings, "LogFileLocalChatDateFormat", "-%Y-%m-%d");
|
||||
strftime(dbuffer, 100, local_chat_date_format().c_str(), localtime(&now));
|
||||
}
|
||||
else
|
||||
{
|
||||
static const LLCachedControl<std::string> ims_date_format(gSavedPerAccountSettings, "LogFileIMsDateFormat", "-%Y-%m");
|
||||
strftime(dbuffer, 100, ims_date_format().c_str(), localtime(&now));
|
||||
}
|
||||
filename += dbuffer;
|
||||
std::array<char, 100> dbuffer;
|
||||
static const LLCachedControl<std::string> local_chat_date_format(gSavedPerAccountSettings, "LogFileLocalChatDateFormat", "-%Y-%m-%d");
|
||||
static const LLCachedControl<std::string> ims_date_format(gSavedPerAccountSettings, "LogFileIMsDateFormat", "-%Y-%m");
|
||||
strftime(dbuffer.data(), dbuffer.size(), (filename == "chat" ? local_chat_date_format : ims_date_format)().c_str(), localtime(&now));
|
||||
filename += dbuffer.data();
|
||||
}
|
||||
cleanFileName(filename);
|
||||
return get_log_dir_file(filename + ".txt");
|
||||
}
|
||||
|
||||
bool LLLogChat::migrateFile(const std::string& old_name, const std::string& filename)
|
||||
{
|
||||
std::string oldfile = makeLogFileNameInternal(old_name);
|
||||
if (!LLFile::isfile(oldfile)) return false; // An old file by this name doesn't exist
|
||||
|
||||
if (LLFile::isfile(filename)) // A file by the new name also exists, but wasn't being tracked yet
|
||||
{
|
||||
auto&& new_untracked_log = llifstream(filename);
|
||||
auto&& tracked_log = llofstream(oldfile, llofstream::out|llofstream::app);
|
||||
// Append new to old and find out if it failed
|
||||
bool failed = !(tracked_log << new_untracked_log.rdbuf());
|
||||
// Close streams
|
||||
new_untracked_log.close();
|
||||
tracked_log.close();
|
||||
if (failed || LLFile::remove(filename)) // Delete the untracked new file so that reclaiming its name won't fail
|
||||
return true; // We failed to remove it or update the old file, let's just use the new file and leave the old one alone
|
||||
}
|
||||
|
||||
LLFile::rename(oldfile, filename); // Move the existing file to the new name
|
||||
return true; // Report success
|
||||
}
|
||||
|
||||
static LLSD sIDMap;
|
||||
|
||||
static std::string get_ids_map_file() { return get_log_dir_file("ids_to_names.json"); }
|
||||
void LLLogChat::initializeIDMap()
|
||||
{
|
||||
const auto map_file = get_ids_map_file();
|
||||
bool write = true; // Do we want to write back to map_file?
|
||||
if (LLFile::isfile(map_file)) // If we've already made this file, load our map from it
|
||||
{
|
||||
if (auto&& fstr = llifstream(map_file))
|
||||
{
|
||||
LLSDSerialize::fromNotation(sIDMap, fstr, LLSDSerialize::SIZE_UNLIMITED);
|
||||
fstr.close();
|
||||
}
|
||||
write = false; // Don't write what we just read
|
||||
}
|
||||
|
||||
if (gCacheName) // Load what we can from name cache to initialize or update the map and its file
|
||||
{
|
||||
bool empty = sIDMap.size() == 0; // Opt out of searching the map for IDs we added if we started with none
|
||||
for (const auto& r : gCacheName->getReverseMap()) // For every name id pair
|
||||
{
|
||||
const auto id = r.second.asString();
|
||||
const auto& name = r.first;
|
||||
const auto filename = makeLogFileNameInternal(name);
|
||||
bool id_known = !empty && sIDMap.has(id); // Is this ID known?
|
||||
if (id_known ? name != sIDMap[id].asStringRef() // If names don't match
|
||||
&& migrateFile(sIDMap[id].asStringRef(), filename) // Do we need to migrate an existing log?
|
||||
: LLFile::isfile(filename)) // Otherwise if there's a log file for them but they're not in the map yet
|
||||
{
|
||||
if (id_known) write = true; // We updated, write
|
||||
sIDMap[id] = name; // Add them to the map
|
||||
}
|
||||
}
|
||||
|
||||
if (write)
|
||||
if (auto&& fstr = llofstream(map_file))
|
||||
{
|
||||
LLSDSerialize::toPrettyNotation(sIDMap, fstr);
|
||||
fstr.close();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//static
|
||||
std::string LLLogChat::makeLogFileName(const std::string& username, const LLUUID& id)
|
||||
{
|
||||
const auto name = username.empty() ? id.asString() : username; // Fall back on ID if the grid sucks and we have no name
|
||||
std::string filename = makeLogFileNameInternal(name);
|
||||
if (id.notNull() && !LLFile::isfile(filename)) // No existing file by this user's current name, check for possible file rename
|
||||
{
|
||||
auto& entry = sIDMap[id.asString()];
|
||||
const bool empty = !entry.size();
|
||||
if (empty || entry != name) // If we haven't seen this entry yet, or the name is different than we remember
|
||||
{
|
||||
if (empty) // We didn't see this entry on load
|
||||
{
|
||||
// Ideally, we would look up the old names here via server request
|
||||
// In lieu of that, our reverse cache has old names and new names that we've gained since our initialization of the ID map
|
||||
for (const auto& r : gCacheName->getReverseMap())
|
||||
if (r.second == id && migrateFile(r.first, filename))
|
||||
break;
|
||||
}
|
||||
else migrateFile(entry.asStringRef(), filename); // We've seen this entry before, migrate old file if it exists
|
||||
|
||||
entry = name; // Update the entry to point to the new name
|
||||
|
||||
if (auto&& fstr = llofstream(get_ids_map_file())) // Write back to our map file
|
||||
{
|
||||
LLSDSerialize::toPrettyNotation(sIDMap, fstr);
|
||||
fstr.close();
|
||||
}
|
||||
}
|
||||
}
|
||||
filename = cleanFileName(filename);
|
||||
filename = gDirUtilp->getExpandedFilename(LL_PATH_PER_ACCOUNT_CHAT_LOGS,filename);
|
||||
filename += ".txt";
|
||||
return filename;
|
||||
}
|
||||
|
||||
std::string LLLogChat::cleanFileName(std::string filename)
|
||||
void LLLogChat::cleanFileName(std::string& filename)
|
||||
{
|
||||
std::string invalidChars = "\"\'\\/?*:<>|[]{}~"; // Cannot match glob or illegal filename chars
|
||||
S32 position = filename.find_first_of(invalidChars);
|
||||
@@ -73,7 +170,6 @@ std::string LLLogChat::cleanFileName(std::string filename)
|
||||
filename[position] = '_';
|
||||
position = filename.find_first_of(invalidChars, position);
|
||||
}
|
||||
return filename;
|
||||
}
|
||||
|
||||
static void time_format(std::string& out, const char* fmt, const std::tm* time)
|
||||
@@ -92,6 +188,7 @@ static void time_format(std::string& out, const char* fmt, const std::tm* time)
|
||||
charvector.resize(1+size); // Use the String Stone
|
||||
format_the_time();
|
||||
}
|
||||
#undef format_the_time
|
||||
out.assign(charvector.data());
|
||||
}
|
||||
|
||||
@@ -117,15 +214,15 @@ std::string LLLogChat::timestamp(bool withdate)
|
||||
|
||||
|
||||
//static
|
||||
void LLLogChat::saveHistory(std::string const& filename, std::string line)
|
||||
void LLLogChat::saveHistory(const std::string& name, const LLUUID& id, const std::string& line)
|
||||
{
|
||||
if(!filename.size())
|
||||
if(name.empty() && id.isNull())
|
||||
{
|
||||
LL_INFOS() << "Filename is Empty!" << LL_ENDL;
|
||||
return;
|
||||
}
|
||||
|
||||
LLFILE* fp = LLFile::fopen(LLLogChat::makeLogFileName(filename), "a"); /*Flawfinder: ignore*/
|
||||
LLFILE* fp = LLFile::fopen(LLLogChat::makeLogFileName(name, id), "a"); /*Flawfinder: ignore*/
|
||||
if (!fp)
|
||||
{
|
||||
LL_INFOS() << "Couldn't open chat history log!" << LL_ENDL;
|
||||
@@ -140,10 +237,9 @@ void LLLogChat::saveHistory(std::string const& filename, std::string line)
|
||||
|
||||
static long const LOG_RECALL_BUFSIZ = 2048;
|
||||
|
||||
void LLLogChat::loadHistory(std::string const& filename , void (*callback)(ELogLineType, std::string, void*), void* userdata)
|
||||
void LLLogChat::loadHistory(const std::string& name, const LLUUID& id, std::function<void (ELogLineType, const std::string&)> callback)
|
||||
{
|
||||
bool filename_empty = filename.empty();
|
||||
if (filename_empty)
|
||||
if (name.empty() && id.isNull())
|
||||
{
|
||||
LL_WARNS() << "filename is empty!" << LL_ENDL;
|
||||
}
|
||||
@@ -154,7 +250,7 @@ void LLLogChat::loadHistory(std::string const& filename , void (*callback)(ELogL
|
||||
if (lines == 0) break;
|
||||
|
||||
// Open the log file.
|
||||
LLFILE* fptr = LLFile::fopen(makeLogFileName(filename), "rb");
|
||||
LLFILE* fptr = LLFile::fopen(makeLogFileName(name, id), "rb");
|
||||
if (!fptr) break;
|
||||
|
||||
// Set pos to point to the last character of the file, if any.
|
||||
@@ -199,20 +295,15 @@ void LLLogChat::loadHistory(std::string const& filename , void (*callback)(ELogL
|
||||
// Read lines from the file one by one until we reach the end of the file.
|
||||
while (fgets(buffer, LOG_RECALL_BUFSIZ, fptr))
|
||||
{
|
||||
size_t len = strlen(buffer);
|
||||
int i = len - 1;
|
||||
while (i >= 0 && (buffer[i] == '\r' || buffer[i] == '\n')) // strip newline chars from the end of the string
|
||||
{
|
||||
buffer[i] = '\0';
|
||||
i--;
|
||||
}
|
||||
callback(LOG_LINE, buffer, userdata);
|
||||
// strip newline chars from the end of the string
|
||||
for (S32 i = strlen(buffer) - 1; i >= 0 && (buffer[i] == '\r' || buffer[i] == '\n'); --i)
|
||||
buffer[i] = '\0';
|
||||
callback(LOG_LINE, buffer);
|
||||
}
|
||||
|
||||
fclose(fptr);
|
||||
callback(LOG_END, LLStringUtil::null, userdata);
|
||||
callback(LOG_END, LLStringUtil::null);
|
||||
return;
|
||||
}
|
||||
callback(LOG_EMPTY, LLStringUtil::null, userdata);
|
||||
callback(LOG_EMPTY, LLStringUtil::null);
|
||||
}
|
||||
|
||||
|
||||
@@ -45,14 +45,16 @@ public:
|
||||
LOG_LINE,
|
||||
LOG_END
|
||||
};
|
||||
static void initializeIDMap();
|
||||
static std::string timestamp(bool withdate = false);
|
||||
static std::string makeLogFileName(std::string filename);
|
||||
static void saveHistory(std::string const& filename, std::string line);
|
||||
static void loadHistory(std::string const& filename,
|
||||
void (*callback)(ELogLineType,std::string,void*),
|
||||
void* userdata);
|
||||
static std::string makeLogFileName(const std::string& name, const LLUUID& id);
|
||||
static void saveHistory(const std::string& name, const LLUUID& id, const std::string& line);
|
||||
static void loadHistory(const std::string& name, const LLUUID& id,
|
||||
std::function<void (ELogLineType, const std::string&)> callback);
|
||||
private:
|
||||
static std::string cleanFileName(std::string filename);
|
||||
static std::string makeLogFileNameInternal(std::string filename);
|
||||
static bool migrateFile(const std::string& old_name, const std::string& filename);
|
||||
static void cleanFileName(std::string& filename);
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
@@ -28,13 +28,6 @@
|
||||
|
||||
#include "llmediadataclient.h"
|
||||
|
||||
#if LL_MSVC
|
||||
// disable boost::lexical_cast warning
|
||||
#pragma warning (disable:4702)
|
||||
#endif
|
||||
|
||||
#include <boost/lexical_cast.hpp>
|
||||
|
||||
#include "llhttpstatuscodes.h"
|
||||
#include "llsdutil.h"
|
||||
#include "llmediaentry.h"
|
||||
|
||||
@@ -148,7 +148,7 @@ struct CommWrapper
|
||||
|
||||
struct MenuFloaterDict final : public LLSingleton<MenuFloaterDict>
|
||||
{
|
||||
typedef std::map<const std::string, std::pair<std::function<void ()>, std::function<bool ()> > > menu_floater_map_t;
|
||||
typedef std::map<const std::string, std::pair<std::function<void ()>, std::function<bool ()>>> menu_floater_map_t;
|
||||
menu_floater_map_t mEntries;
|
||||
|
||||
MenuFloaterDict()
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user