Compare commits

...
Author SHA1 Message Date
Ed Hennis a7add7ce15 Merge remote-tracking branch 'XRPLF/develop' into ximinez/acquireAsyncDispatch
* XRPLF/develop: (22 commits)
  chore: Bump version to 3.4.1 and make pkg_release 2
  build: Reduce number of conan logs (8548)
  chore: Fix readability-redundant-lambda-parameter-list (8544)
  fix: Reject Batch inner txs with the wrong wrapper (fixBatchV1_2)
  ci: Update Nexus packaging URL
  fix: Assorted integer-arithmetic hardening in the payment engine and ledger helpers
  fix: Change mpt subscription msg type back to `transaction` (8539)
  chore: Update clang-tidy image to v23 (8536)
  feat: Integrate Permissioned Domain & Credential Checks for Lending Protocol (6517)
  refactor: Group binaries in subdirectories (8535)
  chore: Split multiple-in-one into individual tests (8025)
  refactor: Migrate handlers to rpc-spec (B) (8484)
  build: Use images with Clang 23 except for clang-tidy (8530)
  chore: Update pre-commit hooks and image (8528)
  fix: Fix MPT partial payment overflow (8302)
  build: Use LLVM 23 (8522)
  refactor: Extract escrow lock helpers and paychan test helpers (7882)
  fix: Validate vetoed parameter type in feature RPC (7583)
  refactor: Use CheckEntry everywhere (8349)
  build: Make conan retry with Conan Center's source backups (8524)
  ...
2026-10-09 20:16:11 -04:00
Ayaz Salikhov 6d6ab2d067 Merge remote-tracking branch 'upstream/release/3.4.x' into develop 2026-10-10 00:20:39 +01:00
Ayaz Salikhov 00e6407514 chore: Bump version to 3.4.1 and make pkg_release 2 2026-10-09 23:50:58 +01:00
Ayaz Salikhov 00c06edffb Merge remote-tracking branch 'upstream/release/3.4.x' into develop 2026-10-09 22:45:18 +01:00
Ayaz Salikhov de5053ae0d build: Reduce number of conan logs (#8548) 2026-10-09 16:33:41 +00:00
Ayaz Salikhov 1940ec5c2a chore: Fix readability-redundant-lambda-parameter-list (#8544) 2026-10-09 16:20:45 +00:00
Denis Angell 19c94c73f4 fix: Reject Batch inner txs with the wrong wrapper (fixBatchV1_2) 2026-10-09 16:04:36 +01:00
Bart cd005ff60d ci: Update Nexus packaging URL 2026-10-09 16:04:36 +01:00
Gregory Tsipenyuk 578224f2e6 fix: Assorted integer-arithmetic hardening in the payment engine and ledger helpers 2026-10-09 16:04:35 +01:00
Shawn Xie 3857ce21cd fix: Change mpt subscription msg type back to transaction (#8539) 2026-10-09 13:33:13 +00:00
Ayaz Salikhov aa490df46b chore: Update clang-tidy image to v23 (#8536) 2026-10-09 10:19:07 +00:00
88c1f1e7ac feat: Integrate Permissioned Domain & Credential Checks for Lending Protocol (#6517)
Signed-off-by: JCW <[email protected]>
Co-authored-by: Vito <[email protected]>
Co-authored-by: Ed Hennis <[email protected]>
2026-10-09 10:18:31 +00:00
Ayaz SalikhovandCopilot Autofix powered by AI ede8af8191 refactor: Group binaries in subdirectories (#8535)
Co-authored-by: Copilot Autofix powered by AI <[email protected]>
2026-10-08 12:34:06 +00:00
Alex Kremer 3c24b605a1 chore: Split multiple-in-one into individual tests (#8025) 2026-10-08 09:57:38 +00:00
Alex Kremer d343b542f1 refactor: Migrate handlers to rpc-spec (B) (#8484) 2026-10-07 13:46:37 +00:00
Ayaz Salikhov 7acd719bf7 build: Use images with Clang 23 except for clang-tidy (#8530) 2026-10-07 13:08:20 +00:00
Ayaz Salikhov b4564d5301 chore: Update pre-commit hooks and image (#8528) 2026-10-07 10:59:37 +00:00
Shawn Xie 60195e6d37 fix: Fix MPT partial payment overflow (#8302) 2026-10-06 23:16:13 +00:00
Ed Hennis 1a1924dd30 Merge remote-tracking branch 'XRPLF/develop' into ximinez/acquireAsyncDispatch
* XRPLF/develop: (281 commits)
  refactor: Use NegativeUNLEntry everywhere (8365)
  build: Make clang-tools custom in Nix, to match what's being built (8521)
  refactor: Migrate handlers to rpc-spec (A) (8345)
  test: Declare, not define, entry instantiations in SLEBase test (8357)
  test: Add more tests for granular permissions (8459)
  fix: Enforce that MPT issuance flags are never cleared (8152)
  feat: Allow lending transactions in Batch (8244)
  feat: Add full support for all objects in `ledger_entry` (6319)
  build: Define XRPL_ASAN, XRPL_TSAN, and XRPL_UBSAN compile definitions (8483)
  refactor: Use LedgerHashesEntry everywhere (8369)
  refactor: Use EscrowEntry everywhere (8354)
  chore: Update nix flake file (8479)
  refactor: Use FeeSettingsEntry everywhere (8370)
  fix: Add string type validation for channel_id and signature (7582)
  test: Migrate three beast suites from beast::unit_test to gtest (7993)
  refactor: Build Throw messages with std::format (8474)
  feat: Implement Confidential mpt holder key update (8266)
  fix: Do not block MPToken deletion on unrelated confidential balances (8209)
  fix: Enable the large Number mantissa with MPTokensV2 (8330)
  chore: Add ignore revs for recent style changes (8463)
  ...
2026-10-06 18:52:40 -04:00
Ayaz Salikhov 3d526d456e build: Use LLVM 23 (#8522) 2026-10-06 21:19:57 +00:00
Denis AngellandMayukha Vadari f05c9f7913 refactor: Extract escrow lock helpers and paychan test helpers (#7882)
Co-authored-by: Mayukha Vadari <[email protected]>
2026-10-06 19:58:52 +00:00
Harshit GuptaandMayukha Vadari c2a4bc3aa1 fix: Validate vetoed parameter type in feature RPC (#7583)
Co-authored-by: Mayukha Vadari <[email protected]>
2026-10-06 19:44:56 +00:00
Mayukha Vadari 718185e3b2 refactor: Use CheckEntry everywhere (#8349) 2026-10-06 19:26:35 +00:00
Ayaz Salikhov 1d7783bb86 build: Make conan retry with Conan Center's source backups (#8524) 2026-10-06 19:23:38 +00:00
Mayukha Vadari 9fd2c552f5 refactor: Use AmendmentsEntry everywhere (#8368) 2026-10-06 17:59:44 +00:00
Ayaz Salikhov 70b8fd301b chore: Update docker images; link Conan-built tools with a static runtime (#8520) 2026-10-06 16:47:35 +00:00
Mayukha Vadari e6564f553d refactor: Use NegativeUNLEntry everywhere (#8365) 2026-10-06 14:23:24 +00:00
Ayaz Salikhov ed96e60ce3 build: Make clang-tools custom in Nix, to match what's being built (#8521) 2026-10-06 13:59:12 +00:00
Alex Kremer 2ebd745a1b refactor: Migrate handlers to rpc-spec (A) (#8345) 2026-10-06 13:19:20 +00:00
Mayukha Vadari cfcbe45b60 test: Declare, not define, entry instantiations in SLEBase test (#8357) 2026-10-06 12:12:22 +00:00
yinyiqian1andBart 9cbf78ba99 test: Add more tests for granular permissions (#8459)
Co-authored-by: Bart <[email protected]>
2026-10-05 23:18:58 +00:00
Timur Yalymov b8d8738f81 fix: Enforce that MPT issuance flags are never cleared (#8152) 2026-10-05 23:17:36 +00:00
63c97e719f feat: Allow lending transactions in Batch (#8244)
Co-authored-by: Cursor <[email protected]>
Co-authored-by: Vito Tumas <[email protected]>
2026-10-05 23:17:26 +00:00
3ac26f23c7 feat: Add full support for all objects in ledger_entry (#6319)
Co-authored-by: Timur Yalymov <[email protected]>
Co-authored-by: Cursor <[email protected]>
Co-authored-by: Vito Tumas <[email protected]>
Co-authored-by: Ayaz Salikhov <[email protected]>
2026-10-05 23:17:14 +00:00
BartandBart ff9410bc56 build: Define XRPL_ASAN, XRPL_TSAN, and XRPL_UBSAN compile definitions (#8483)
Co-authored-by: Bart <[email protected]>
2026-10-05 23:15:08 +00:00
Mayukha Vadari 1798262d7a refactor: Use LedgerHashesEntry everywhere (#8369) 2026-10-05 18:15:02 +00:00
Mayukha Vadari cd633b9ac9 refactor: Use EscrowEntry everywhere (#8354) 2026-10-05 17:51:18 +00:00
Ayaz Salikhov 5c5f7d315a chore: Update nix flake file (#8479) 2026-10-05 16:58:41 +00:00
Mayukha Vadari 0f7493ce50 refactor: Use FeeSettingsEntry everywhere (#8370) 2026-10-05 16:56:41 +00:00
Harshit Gupta 40f61f828a fix: Add string type validation for channel_id and signature (#7582) 2026-10-05 16:55:14 +00:00
Mayukha Vadari 108277f4b7 test: Migrate three beast suites from beast::unit_test to gtest (#7993) 2026-10-05 15:28:05 +00:00
Ed Hennis 99859d2458 Fix doxygen style issue 2026-08-05 22:54:41 -04:00
Ed Hennis 7642bc6671 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-08-05 12:17:07 -04:00
Ed Hennis add33d853c Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-07-14 20:13:11 -04:00
Ed Hennis be0baf1b53 Fix new header to use "#pragma once" 2026-07-10 11:41:11 -04:00
Ed Hennis b394730bd0 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-07-09 19:50:02 -04:00
Ed Hennis 8290eb3024 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-19 16:53:50 -04:00
Ed Hennis d537684df5 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-19 10:15:30 -04:00
Ed Hennis 4085361251 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-19 05:16:07 -04:00
Ed Hennis 1de7c130b0 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-15 21:43:33 -04:00
Ed Hennis 2a678a1157 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-14 20:39:23 -04:00
Ed Hennis 5c254aadf2 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-13 22:32:06 -04:00
Ed Hennis ad2db1962e Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-13 12:03:54 -04:00
Ed Hennis 4dae405762 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-12 19:19:01 -04:00
Ed Hennis b21b3596f8 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-12 16:26:24 -04:00
Ed Hennis d648539b62 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-11 13:34:26 -04:00
Ed Hennis 50644c6d30 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-07 18:10:17 -04:00
Ed Hennis 88c248077e Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-07 14:18:43 -04:00
Ed Hennis bad40d7e10 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-07 13:28:46 -04:00
Ed Hennis 74d0c375ec Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-06 22:34:37 -04:00
Ed Hennis 200ab3f694 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-06 14:18:16 -04:00
Ed Hennis a7a4357022 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-05 16:46:58 -04:00
Ed Hennis e0230a1e22 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-05 10:50:49 -04:00
Ed Hennis 5f1a98397c Merge remote-tracking branch 'XRPLF/develop' into ximinez/acquireAsyncDispatch
* XRPLF/develop:
  ci: Rewrite clang-tidy workflow(s) in a reusable manner (7062)
  chore: Ignore identifier-naming update in git blame (7066)
  refactor: Enable clang-tidy `readability-identifier-naming` check (6571)
2026-05-05 00:26:38 -04:00
Ed Hennis c8ca624974 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-05-01 13:59:18 -04:00
Ed Hennis 4489cda841 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-28 16:23:47 -04:00
Ed Hennis 784774005e Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-25 14:45:58 -04:00
Ed Hennis 904b39a3d3 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-23 15:56:15 -04:00
Ed Hennis eadfabfe4f Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-22 23:40:40 -04:00
Ed Hennis d991f81e87 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-22 14:49:17 -04:00
Ed Hennis a34a96e233 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-22 13:10:48 -04:00
Ed Hennis a3a277518b Merge remote-tracking branch 'XRPLF/develop' into ximinez/acquireAsyncDispatch
* XRPLF/develop:
  chore: Add -fix to clang-tidy invocation (6990)
  chore: Remove empty Taker.h (6984)
  chore: Enable clang-tidy modernize checks (6975)
  ci: Upload clang-tidy git diff (6983)
  fix: Add rounding to Vault invariants (6217) (6955)
2026-04-21 18:54:46 -04:00
Ed Hennis 8438698c54 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-20 17:49:51 -04:00
Ed Hennis 0597047d79 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-20 15:45:08 -04:00
Ed Hennis 992c6f525d Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-20 11:39:10 -04:00
Ed Hennis 9a870c36e2 Merge remote-tracking branch 'XRPLF/develop' into ximinez/acquireAsyncDispatch
* XRPLF/develop:
  chore: Enable clang-tidy include cleaner (6947)
  fix: Change AMMClawback return code to tecNO_PERMISSION (6946)
  ci: [DEPENDABOT] bump actions/upload-pages-artifact from 4.0.0 to 5.0.0 (6927)
  ci: [DEPENDABOT] bump actions/upload-artifact from 7.0.0 to 7.0.1 (6928)
  chore: Enable clang-tidy readability checks (6930)
2026-04-17 18:13:20 -04:00
Ed Hennis a4462e65bc Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-16 13:44:42 -04:00
Ed Hennis f0596c0a5d Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-15 19:06:33 -04:00
Ed Hennis dd99bc3ce8 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-15 14:29:00 -04:00
Ed Hennis 25cd7730e5 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-13 20:28:47 -04:00
Ed Hennis 8dcbcb22c2 Merge branch 'develop' into ximinez/acquireAsyncDispatch 2026-04-10 12:12:54 -04:00
Ed Hennis f44dfc89cc refactor: acquireAsync will dispatch a job, not the other way around
- Improve job queue collision checks and logging
    - Improve logging related to ledger acquisition and operating mode
      changes
    - Class "CanProcess" to keep track of processing of distinct items
2026-04-10 10:31:21 -04:00
419 changed files with 10228 additions and 6081 deletions

No files matched your search

+16
View File
@@ -5,7 +5,10 @@ Checks: "-*,
-bugprone-exception-escape, -bugprone-exception-escape,
-bugprone-implicit-widening-of-multiplication-result, -bugprone-implicit-widening-of-multiplication-result,
-bugprone-narrowing-conversions, -bugprone-narrowing-conversions,
-bugprone-signed-bitwise,
-bugprone-std-exception-baseclass,
-bugprone-throwing-static-initialization, -bugprone-throwing-static-initialization,
-bugprone-unhandled-code-paths,
cppcoreguidelines-*, cppcoreguidelines-*,
-cppcoreguidelines-avoid-c-arrays, -cppcoreguidelines-avoid-c-arrays,
@@ -14,6 +17,7 @@ Checks: "-*,
-cppcoreguidelines-avoid-magic-numbers, -cppcoreguidelines-avoid-magic-numbers,
-cppcoreguidelines-avoid-non-const-global-variables, -cppcoreguidelines-avoid-non-const-global-variables,
-cppcoreguidelines-c-copy-assignment-signature, -cppcoreguidelines-c-copy-assignment-signature,
-cppcoreguidelines-explicit-constructor,
-cppcoreguidelines-interfaces-global-init, -cppcoreguidelines-interfaces-global-init,
-cppcoreguidelines-macro-usage, -cppcoreguidelines-macro-usage,
-cppcoreguidelines-missing-std-forward, -cppcoreguidelines-missing-std-forward,
@@ -32,6 +36,7 @@ Checks: "-*,
llvm-namespace-comment, llvm-namespace-comment,
misc-*, misc-*,
-misc-explicit-constructor,
-misc-multiple-inheritance, -misc-multiple-inheritance,
-misc-no-recursion, -misc-no-recursion,
-misc-non-private-member-variables-in-classes, -misc-non-private-member-variables-in-classes,
@@ -45,6 +50,8 @@ Checks: "-*,
-modernize-avoid-c-style-cast, -modernize-avoid-c-style-cast,
-modernize-return-braced-init-list, -modernize-return-braced-init-list,
-modernize-use-integer-sign-comparison, -modernize-use-integer-sign-comparison,
-modernize-use-string-view,
-modernize-use-structured-binding,
-modernize-use-trailing-return-type, -modernize-use-trailing-return-type,
performance-*, performance-*,
@@ -53,6 +60,7 @@ Checks: "-*,
-performance-noexcept-move-constructor, -performance-noexcept-move-constructor,
-performance-unnecessary-copy-initialization, -performance-unnecessary-copy-initialization,
-performance-unnecessary-value-param, -performance-unnecessary-value-param,
-performance-use-std-move,
readability-*, readability-*,
-readability-avoid-const-params-in-decls, -readability-avoid-const-params-in-decls,
@@ -65,7 +73,11 @@ Checks: "-*,
-readability-named-parameter, -readability-named-parameter,
-readability-qualified-auto, -readability-qualified-auto,
-readability-redundant-access-specifiers, -readability-redundant-access-specifiers,
-readability-redundant-nested-if,
-readability-redundant-qualified-alias,
-readability-static-accessed-through-instance, -readability-static-accessed-through-instance,
-readability-trailing-comma,
-readability-trivial-switch,
-readability-uppercase-literal-suffix -readability-uppercase-literal-suffix
" "
# --- # ---
@@ -81,6 +93,10 @@ CheckOptions:
bugprone-unsafe-functions.ReportMoreUnsafeFunctions: true bugprone-unsafe-functions.ReportMoreUnsafeFunctions: true
bugprone-unused-return-value.CheckedReturnTypes: ::std::error_code;::std::error_condition;::std::errc bugprone-unused-return-value.CheckedReturnTypes: ::std::error_code;::std::error_condition;::std::errc
# New in clang-tidy 23; disabled until the code is updated
misc-const-correctness.AnalyzeAutoVariables: false
misc-const-correctness.AnalyzeLambdas: false
misc-const-correctness.AnalyzeParameters: false
misc-include-cleaner.IgnoreHeaders: ".*/(detail|impl)/.*;.*fwd\\.h(pp)?;time.h;stdlib.h;sqlite3.h;netinet/in\\.h;sys/resource\\.h;sys/sysinfo\\.h;linux/sysinfo\\.h;__chrono/.*;bits/.*;_abort\\.h;boost/.*;openssl/obj_mac\\.h" misc-include-cleaner.IgnoreHeaders: ".*/(detail|impl)/.*;.*fwd\\.h(pp)?;time.h;stdlib.h;sqlite3.h;netinet/in\\.h;sys/resource\\.h;sys/sysinfo\\.h;linux/sysinfo\\.h;__chrono/.*;bits/.*;_abort\\.h;boost/.*;openssl/obj_mac\\.h"
readability-braces-around-statements.ShortStatementLines: 2 readability-braces-around-statements.ShortStatementLines: 2
+72
View File
@@ -108,3 +108,75 @@ endfunction()
function(patch_nix_binary target) function(patch_nix_binary target)
endfunction() endfunction()
function(rpcspec_generate_instantiations)
set(options)
set(oneValueArgs OUT_VAR VALUE_TYPE VIEW_HEADER INCLUDE_DIR)
set(multiValueArgs HANDLERS)
cmake_parse_arguments(
THIS_FUNCTION_PREFIX
"${options}"
"${oneValueArgs}"
"${multiValueArgs}"
${ARGN}
)
endfunction()
function(corrosion_import_crate)
set(options
ALL_FEATURES
NO_DEFAULT_FEATURES
NO_STD
NO_LINKER_OVERRIDE
NO_USES_TERMINAL
LOCKED
FROZEN
)
set(oneValueArgs MANIFEST_PATH PROFILE IMPORTED_CRATES)
set(multiValueArgs
CRATE_TYPES
CRATES
FEATURES
FLAGS
OVERRIDE_CRATE_TYPE
)
cmake_parse_arguments(
THIS_FUNCTION_PREFIX
"${options}"
"${oneValueArgs}"
"${multiValueArgs}"
${ARGN}
)
endfunction()
function(corrosion_set_env_vars target_name env_var)
endfunction()
function(corrosion_add_cxxbridge cxx_target)
set(options)
set(oneValueArgs CRATE)
set(multiValueArgs FILES)
cmake_parse_arguments(
THIS_FUNCTION_PREFIX
"${options}"
"${oneValueArgs}"
"${multiValueArgs}"
${ARGN}
)
endfunction()
function(_unlink_libgcc_s crate)
endfunction()
function(add_xrpl_crate name)
set(options)
set(oneValueArgs CRATE)
set(multiValueArgs FILES)
cmake_parse_arguments(
THIS_FUNCTION_PREFIX
"${options}"
"${oneValueArgs}"
"${multiValueArgs}"
${ARGN}
)
endfunction()
+22 -5
View File
@@ -15,9 +15,9 @@ inputs:
required: false required: false
default: "false" default: "false"
log_verbosity: log_verbosity:
description: "The logging verbosity." description: 'The logging verbosity ("quiet", "verbose"), or empty to use the Conan defaults.'
required: false required: false
default: "verbose" default: ""
sanitizers: sanitizers:
description: "The sanitizers to enable." description: "The sanitizers to enable."
required: false required: false
@@ -35,6 +35,16 @@ runs:
LOG_VERBOSITY: ${{ inputs.log_verbosity }} LOG_VERBOSITY: ${{ inputs.log_verbosity }}
SANITIZERS: ${{ inputs.sanitizers }} SANITIZERS: ${{ inputs.sanitizers }}
run: | run: |
# By default, leave the verbosity unset, so CMake configure output is
# shown, but compile commands and Boost's b2 debug output (~85k lines
# when "verbose") are not.
VERBOSITY_ARGS=()
if [[ -n "${LOG_VERBOSITY}" ]]; then
VERBOSITY_ARGS=(
--conf:all tools.build:verbosity="${LOG_VERBOSITY}"
--conf:all tools.compilation:verbosity="${LOG_VERBOSITY}"
)
fi
conan install \ conan install \
--profile:all ci \ --profile:all ci \
--build="${BUILD_OPTION}" \ --build="${BUILD_OPTION}" \
@@ -42,6 +52,13 @@ runs:
--options:host='&:xrpld=True' \ --options:host='&:xrpld=True' \
--settings:all build_type="${BUILD_TYPE}" \ --settings:all build_type="${BUILD_TYPE}" \
--conf:all tools.build:jobs=${BUILD_NPROC} \ --conf:all tools.build:jobs=${BUILD_NPROC} \
--conf:all tools.build:verbosity="${LOG_VERBOSITY}" \ "${VERBOSITY_ARGS[@]}" \
--conf:all tools.compilation:verbosity="${LOG_VERBOSITY}" \ --format=json \
. . >"${RUNNER_TEMP}/conan-graph.json"
# Tools that run during the build may only load glibc from the Nix store,
# as their package ID survives a GCC runtime update.
- name: Check build-context packages for Nix store dependencies (Linux)
if: ${{ runner.os == 'Linux' }}
shell: bash
run: ./bin/nix/check-build-context-runtime.sh "${RUNNER_TEMP}/conan-graph.json"
+4 -4
View File
@@ -1,5 +1,5 @@
{ {
"image_tag": "sha-060957e", "image_tag": "sha-3d526d4",
"configs": { "configs": {
"ubuntu": [ "ubuntu": [
{ {
@@ -74,7 +74,7 @@
"extra_cmake_args": "-Dvalidator_keys=ON", "extra_cmake_args": "-Dvalidator_keys=ON",
"package": { "package": {
"type": "deb", "type": "deb",
"image": "ghcr.io/xrplf/xrpld/packaging-debian:sha-3a2d19f" "image": "ghcr.io/xrplf/xrpld/packaging-debian:sha-e6055dd"
} }
}, },
{ {
@@ -86,7 +86,7 @@
"extra_cmake_args": "-Dvalidator_keys=ON -Dassert=ON", "extra_cmake_args": "-Dvalidator_keys=ON -Dassert=ON",
"package": { "package": {
"type": "deb", "type": "deb",
"image": "ghcr.io/xrplf/xrpld/packaging-debian:sha-3a2d19f", "image": "ghcr.io/xrplf/xrpld/packaging-debian:sha-e6055dd",
"variant": "assert" "variant": "assert"
} }
} }
@@ -101,7 +101,7 @@
"extra_cmake_args": "-Dvalidator_keys=ON", "extra_cmake_args": "-Dvalidator_keys=ON",
"package": { "package": {
"type": "rpm", "type": "rpm",
"image": "ghcr.io/xrplf/xrpld/packaging-rhel:sha-3a2d19f" "image": "ghcr.io/xrplf/xrpld/packaging-rhel:sha-e6055dd"
} }
} }
] ]
+3 -4
View File
@@ -12,8 +12,7 @@ on:
- "!nix/docker/README.md" - "!nix/docker/README.md"
- "!nix/devshell.nix" - "!nix/devshell.nix"
- "!nix/check-tools/**" - "!nix/check-tools/**"
- "bin/default-loader-path.sh" - "bin/nix/default-loader-path.sh"
- "bin/install-sanitizer-libs.sh"
pull_request: pull_request:
paths: paths:
- ".github/workflows/build-nix-images.yml" - ".github/workflows/build-nix-images.yml"
@@ -25,8 +24,8 @@ on:
- "!nix/devshell.nix" - "!nix/devshell.nix"
- "!nix/check-tools/**" - "!nix/check-tools/**"
- "bin/check-tools.sh" - "bin/check-tools.sh"
- "bin/default-loader-path.sh" - "bin/nix/default-loader-path.sh"
- "bin/install-sanitizer-libs.sh" - "bin/install/sanitizer-libs.sh"
workflow_dispatch: workflow_dispatch:
concurrency: concurrency:
+2 -3
View File
@@ -5,13 +5,12 @@ on:
branches: branches:
- develop - develop
paths: paths:
- ".github/workflows/build-packaging-images.yml" - "bin/install/packaging-tools.sh"
- "bin/install-packaging-tools.sh"
- "package/images/packaging/**" - "package/images/packaging/**"
pull_request: pull_request:
paths: paths:
- ".github/workflows/build-packaging-images.yml" - ".github/workflows/build-packaging-images.yml"
- "bin/install-packaging-tools.sh" - "bin/install/packaging-tools.sh"
- "package/images/packaging/**" - "package/images/packaging/**"
workflow_dispatch: workflow_dispatch:
@@ -5,7 +5,6 @@ on:
branches: branches:
- develop - develop
paths: paths:
- ".github/workflows/build-pre-commit-image.yml"
- "bin/pre-commit/Dockerfile" - "bin/pre-commit/Dockerfile"
- "rust-toolchain.toml" - "rust-toolchain.toml"
pull_request: pull_request:
+1 -1
View File
@@ -34,7 +34,7 @@ permissions:
jobs: jobs:
audit: audit:
runs-on: ubuntu-latest runs-on: ubuntu-latest
container: ghcr.io/xrplf/xrpld/nix-ubuntu:sha-060957e container: ghcr.io/xrplf/xrpld/nix-ubuntu:sha-3d526d4
permissions: permissions:
contents: read contents: read
# Needed to open an issue on scheduled failures. # Needed to open an issue on scheduled failures.
+1 -2
View File
@@ -93,9 +93,8 @@ jobs:
.github/workflows/reusable-upload-recipe.yml .github/workflows/reusable-upload-recipe.yml
.clang-tidy .clang-tidy
.codecov.yml .codecov.yml
bin/check-nix-store-refs.sh
bin/check-tools.sh bin/check-tools.sh
bin/default-loader-path.sh bin/nix/**
cfg/** cfg/**
cmake/** cmake/**
conan/** conan/**
+1 -2
View File
@@ -31,9 +31,8 @@ on:
- ".github/workflows/reusable-upload-recipe.yml" - ".github/workflows/reusable-upload-recipe.yml"
- ".clang-tidy" - ".clang-tidy"
- ".codecov.yml" - ".codecov.yml"
- "bin/check-nix-store-refs.sh"
- "bin/check-tools.sh" - "bin/check-tools.sh"
- "bin/default-loader-path.sh" - "bin/nix/**"
- "cfg/**" - "cfg/**"
- "cmake/**" - "cmake/**"
- "conan/**" - "conan/**"
+1 -1
View File
@@ -17,4 +17,4 @@ jobs:
uses: XRPLF/actions/.github/workflows/pre-commit.yml@279ec358f4a1be4088be3e024b07916fa97c75b6 uses: XRPLF/actions/.github/workflows/pre-commit.yml@279ec358f4a1be4088be3e024b07916fa97c75b6
with: with:
runs_on: ubuntu-latest runs_on: ubuntu-latest
container: '{ "image": "ghcr.io/xrplf/xrpld/pre-commit:sha-473fe44" }' container: '{ "image": "ghcr.io/xrplf/xrpld/pre-commit:sha-70b8fd3" }'
+1 -1
View File
@@ -41,7 +41,7 @@ env:
jobs: jobs:
build: build:
runs-on: ubuntu-latest runs-on: ubuntu-latest
container: ghcr.io/xrplf/xrpld/nix-ubuntu:sha-060957e container: ghcr.io/xrplf/xrpld/nix-ubuntu:sha-3d526d4
steps: steps:
- name: Checkout repository - name: Checkout repository
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
@@ -186,9 +186,6 @@ jobs:
with: with:
build_nproc: ${{ steps.nproc.outputs.nproc }} build_nproc: ${{ steps.nproc.outputs.nproc }}
build_type: ${{ inputs.build_type }} build_type: ${{ inputs.build_type }}
# Set the verbosity to "quiet" for Windows to avoid an excessive
# amount of logs. For other OSes, the "verbose" logs are more useful.
log_verbosity: ${{ runner.os == 'Windows' && 'quiet' || 'verbose' }}
sanitizers: ${{ inputs.sanitizers }} sanitizers: ${{ inputs.sanitizers }}
- name: Configure CMake - name: Configure CMake
@@ -257,20 +254,20 @@ jobs:
# cache included, since what it holds is what gets uploaded and reused. # cache included, since what it holds is what gets uploaded and reused.
- name: Check the build output for Nix store references (Nix toolchain) - name: Check the build output for Nix store references (Nix toolchain)
if: ${{ inputs.toolchain == 'nix' }} if: ${{ inputs.toolchain == 'nix' }}
run: ./bin/check-nix-store-refs.sh "${BUILD_DIR}" run: ./bin/nix/check-nix-store-refs.sh "${BUILD_DIR}"
- name: Check the Conan cache for Nix store references (Nix toolchain) - name: Check the Conan cache for Nix store references (Nix toolchain)
if: ${{ inputs.toolchain == 'nix' }} if: ${{ inputs.toolchain == 'nix' }}
run: ./bin/check-nix-store-refs.sh "${CONAN_HOME}" run: ./bin/nix/check-nix-store-refs.sh "${CONAN_HOME}"
# Only what PatchNixBinary.cmake retargets: the toolchain in the Linux # Only what PatchNixBinary.cmake retargets: the toolchain in the Linux
# images always references the store. Same condition it uses. # images always references the store. Same condition it uses.
- name: Check for Nix store references (Linux) - name: Check for Nix store references (Linux)
if: ${{ runner.os == 'Linux' && env.SANITIZERS_ENABLED == 'false' }} if: ${{ runner.os == 'Linux' && env.SANITIZERS_ENABLED == 'false' }}
run: | run: |
./bin/check-nix-store-refs.sh "${BUILD_DIR}/xrpld" ./bin/nix/check-nix-store-refs.sh "${BUILD_DIR}/xrpld"
./bin/check-nix-store-refs.sh "${BUILD_DIR}/xrpl_tests" ./bin/nix/check-nix-store-refs.sh "${BUILD_DIR}/xrpl_tests"
./bin/check-nix-store-refs.sh "${BUILD_DIR}/xrpld_tests" ./bin/nix/check-nix-store-refs.sh "${BUILD_DIR}/xrpld_tests"
- name: Show ccache statistics - name: Show ccache statistics
if: ${{ inputs.ccache_enabled }} if: ${{ inputs.ccache_enabled }}
+1 -2
View File
@@ -34,7 +34,7 @@ jobs:
needs: [determine-files] needs: [determine-files]
if: ${{ needs.determine-files.outputs.cpp_changed_files != '' || needs.determine-files.outputs.need_full_run == 'true' }} if: ${{ needs.determine-files.outputs.cpp_changed_files != '' || needs.determine-files.outputs.need_full_run == 'true' }}
runs-on: ["self-hosted", "Linux", "X64", "heavy"] runs-on: ["self-hosted", "Linux", "X64", "heavy"]
container: "ghcr.io/xrplf/xrpld/nix-debian:sha-060957e" container: "ghcr.io/xrplf/xrpld/nix-debian:sha-3d526d4"
permissions: permissions:
contents: read contents: read
issues: write issues: write
@@ -73,7 +73,6 @@ jobs:
with: with:
build_nproc: ${{ steps.nproc.outputs.nproc }} build_nproc: ${{ steps.nproc.outputs.nproc }}
build_type: ${{ env.BUILD_TYPE }} build_type: ${{ env.BUILD_TYPE }}
log_verbosity: verbose
- name: Configure CMake - name: Configure CMake
working-directory: ${{ env.BUILD_DIR }} working-directory: ${{ env.BUILD_DIR }}
+3 -3
View File
@@ -28,7 +28,7 @@ permissions:
jobs: jobs:
clippy: clippy:
runs-on: ubuntu-latest runs-on: ubuntu-latest
container: ghcr.io/xrplf/xrpld/nix-ubuntu:sha-060957e container: ghcr.io/xrplf/xrpld/nix-ubuntu:sha-3d526d4
steps: steps:
- name: Checkout repository - name: Checkout repository
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
@@ -41,7 +41,7 @@ jobs:
coverage: coverage:
runs-on: ubuntu-latest runs-on: ubuntu-latest
container: ghcr.io/xrplf/xrpld/nix-ubuntu:sha-060957e container: ghcr.io/xrplf/xrpld/nix-ubuntu:sha-3d526d4
steps: steps:
- name: Checkout repository - name: Checkout repository
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
@@ -70,7 +70,7 @@ jobs:
doc: doc:
runs-on: ubuntu-latest runs-on: ubuntu-latest
container: ghcr.io/xrplf/xrpld/nix-ubuntu:sha-060957e container: ghcr.io/xrplf/xrpld/nix-ubuntu:sha-3d526d4
steps: steps:
- name: Checkout repository - name: Checkout repository
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
+1 -1
View File
@@ -40,7 +40,7 @@ defaults:
jobs: jobs:
upload: upload:
runs-on: ubuntu-latest runs-on: ubuntu-latest
container: ghcr.io/xrplf/xrpld/nix-ubuntu:sha-060957e container: ghcr.io/xrplf/xrpld/nix-ubuntu:sha-3d526d4
env: env:
REMOTE_NAME: ${{ inputs.remote_name }} REMOTE_NAME: ${{ inputs.remote_name }}
CONAN_LOGIN_USERNAME_XRPLF: ${{ secrets.remote_username }} CONAN_LOGIN_USERNAME_XRPLF: ${{ secrets.remote_username }}
+1 -4
View File
@@ -108,14 +108,11 @@ jobs:
build_nproc: ${{ steps.nproc.outputs.nproc }} build_nproc: ${{ steps.nproc.outputs.nproc }}
build_type: ${{ matrix.build_type }} build_type: ${{ matrix.build_type }}
force_build: ${{ github.event_name == 'schedule' || github.event.inputs.force_source_build == 'true' }} force_build: ${{ github.event_name == 'schedule' || github.event.inputs.force_source_build == 'true' }}
# Set the verbosity to "quiet" for Windows to avoid an excessive
# amount of logs. For other OSes, the "verbose" logs are more useful.
log_verbosity: ${{ runner.os == 'Windows' && 'quiet' || 'verbose' }}
sanitizers: ${{ matrix.sanitizers }} sanitizers: ${{ matrix.sanitizers }}
- name: Check the Conan cache for Nix store references (Nix toolchain) - name: Check the Conan cache for Nix store references (Nix toolchain)
if: ${{ matrix.toolchain == 'nix' }} if: ${{ matrix.toolchain == 'nix' }}
run: ./bin/check-nix-store-refs.sh "${CONAN_HOME}" run: ./bin/nix/check-nix-store-refs.sh "${CONAN_HOME}"
- name: Log into Conan remote - name: Log into Conan remote
if: ${{ github.repository == 'XRPLF/rippled' && (github.event_name == 'push' || github.event_name == 'workflow_dispatch') }} if: ${{ github.repository == 'XRPLF/rippled' && (github.event_name == 'push' || github.event_name == 'workflow_dispatch') }}
+6 -5
View File
@@ -60,7 +60,7 @@ repos:
types_or: [c++, c] types_or: [c++, c]
- repo: https://github.com/pre-commit/mirrors-clang-format - repo: https://github.com/pre-commit/mirrors-clang-format
rev: e2b496dc2bd8340c2524cb9a2d2a943cde1bb6df # frozen: v23.1.1 rev: a9a8a861f30ed207ead7d5a3b7e8032283ba5da7 # frozen: v23.1.2
hooks: hooks:
- id: clang-format - id: clang-format
args: [--style=file] args: [--style=file]
@@ -82,9 +82,10 @@ repos:
files: ^crates/.*\.rs$ files: ^crates/.*\.rs$
- repo: https://github.com/BlankSpruce/gersemi-pre-commit - repo: https://github.com/BlankSpruce/gersemi-pre-commit
rev: f1c4833f8cf23c6d952673abc73525411a5719e8 # frozen: 0.29.1 rev: 28010ddd6016e1a0f7bd232acb6536ef996ae897 # frozen: 0.29.2
hooks: hooks:
- id: gersemi - id: gersemi
args: [-i, --warnings-as-errors]
- repo: https://github.com/rbubley/mirrors-prettier - repo: https://github.com/rbubley/mirrors-prettier
rev: ef4a397f916211b4a39ccf9d3d9cbb6562157251 # frozen: v3.9.9 rev: ef4a397f916211b4a39ccf9d3d9cbb6562157251 # frozen: v3.9.9
@@ -95,19 +96,19 @@ repos:
# Scoped to package/: the rest of the repo's Python has pre-existing findings, # Scoped to package/: the rest of the repo's Python has pre-existing findings,
# so widening these is its own change. # so widening these is its own change.
- repo: https://github.com/astral-sh/ruff-pre-commit - repo: https://github.com/astral-sh/ruff-pre-commit
rev: a56c0b927e6465d37cae3e97d35d4d18ab2b96cd # frozen: v0.16.9 rev: f12be1ebaa5351c1fc76472de98db2c3446c8253 # frozen: v0.16.10
hooks: hooks:
- id: ruff-check - id: ruff-check
args: [--fix] args: [--fix]
files: ^package/.*\.py$ files: ^package/.*\.py$
- repo: https://github.com/psf/black-pre-commit-mirror - repo: https://github.com/psf/black-pre-commit-mirror
rev: 4160603246a6b365d4a2af661c6d71b0a0f50478 # frozen: 26.5.1 rev: 96ae3e5802f3fe2d551e703e18f0a367d1a81ac2 # frozen: 26.10.0
hooks: hooks:
- id: black - id: black
- repo: https://github.com/pre-commit/mirrors-mypy - repo: https://github.com/pre-commit/mirrors-mypy
rev: 7ff8d35ae36a7d2b968f2f90b4c723e292e594ee # frozen: v2.3.1 rev: 2834ec6639549dd6796205c8f011dedcd587288b # frozen: v2.4.0
hooks: hooks:
- id: mypy - id: mypy
args: [--strict] args: [--strict]
+12 -1
View File
@@ -28,7 +28,17 @@ Version 3.5.0 is not yet released.
### Additions in 3.5.0 ### Additions in 3.5.0
- `subscribe`, `unsubscribe`: Added an optional `mpt_issuances` request field, an array of MPT issuance IDs (hex strings). Subscribers receive a message with `type` `mptTransaction` for each validated transaction whose metadata affects a subscribed issuance; the message has the same fields as the `transactions` stream. MPT issuance subscriptions count toward the per-connection subscription limit. An empty array, a non-array value, or an invalid ID returns `invalidParams`. ([#5671](https://github.com/XRPLF/rippled/pull/5671)) - `subscribe`, `unsubscribe`: Added an optional `mpt_issuances` request field, an array of MPT issuance IDs (hex strings). Subscribers receive the same `transaction` message as the `transactions` stream for each validated transaction whose metadata affects a subscribed issuance. MPT issuance subscriptions count toward the per-connection subscription limit. An empty array, a non-array value, or an invalid ID returns `invalidParams`. ([#5671](https://github.com/XRPLF/rippled/pull/5671))
- `ledger_entry`: Add full support for checks, NFT offers, payment channels, and signer lists. ([#6319](https://github.com/XRPLF/rippled/pull/6319))
### Bugfixes in 3.5.0
- `channel_authorize`: The `channel_id` field now returns an `invalidParams` error if the value is not a string. [#7582](https://github.com/XRPLF/rippled/pull/7582)
- `channel_verify`: The `channel_id` and `signature` fields now return an `invalidParams` error if the value is not a string. [#7582](https://github.com/XRPLF/rippled/pull/7582)
### Bugfixes in 3.5.0
- `feature`: The admin-only `vetoed` field now returns `invalidParams` unless its value is a boolean. [#7583](https://github.com/XRPLF/rippled/pull/7583)
## XRP Ledger server version 3.4.0 ## XRP Ledger server version 3.4.0
@@ -50,6 +60,7 @@ Version 3.4.0 is not yet released. These changes are available in the 3.4.0 beta
- `account_lines`: The `peer` field now returns an error if the value is not a string. [#7728](https://github.com/XRPLF/rippled/pull/7728) - `account_lines`: The `peer` field now returns an error if the value is not a string. [#7728](https://github.com/XRPLF/rippled/pull/7728)
- `ledger`: `delivered_amount` is now included in the metadata of successful `AccountDelete` transactions when transactions are expanded (`expand`, or admin-only `full`). Previously it was only added for `Payment` and `CheckCash`, which made `ledger` inconsistent with `tx` and `account_tx`. [#5706](https://github.com/XRPLF/rippled/pull/5706) - `ledger`: `delivered_amount` is now included in the metadata of successful `AccountDelete` transactions when transactions are expanded (`expand`, or admin-only `full`). Previously it was only added for `Payment` and `CheckCash`, which made `ledger` inconsistent with `tx` and `account_tx`. [#5706](https://github.com/XRPLF/rippled/pull/5706)
- `noripple_check`: The `transactions` field is no longer included in error responses; it is still returned (possibly as an empty array) whenever `transactions` is `true` and the request succeeds. A malformed `account` is now rejected before the ledger is looked up, so that error response no longer carries the `ledger_hash`, `ledger_index`, and `validated` fields ([#6303](https://github.com/XRPLF/rippled/pull/6303)). - `noripple_check`: The `transactions` field is no longer included in error responses; it is still returned (possibly as an empty array) whenever `transactions` is `true` and the request succeeds. A malformed `account` is now rejected before the ledger is looked up, so that error response no longer carries the `ledger_hash`, `ledger_index`, and `validated` fields ([#6303](https://github.com/XRPLF/rippled/pull/6303)).
- `transaction_entry`: An object or an array in `tx_hash` now returns `malformedRequest`, like any other value that is not a hex hash, instead of an `internal` error.
## XRP Ledger server version 3.3.0 ## XRP Ledger server version 3.3.0
+17 -6
View File
@@ -20,9 +20,11 @@
# development setups, but not in the macOS CI environment. They are checked # development setups, but not in the macOS CI environment. They are checked
# everywhere except when running in CI on macOS. # everywhere except when running in CI on macOS.
# #
# Tools that Nix also exposes under a version-suffixed name (`clang-tidy-22`, # Tools that Nix also exposes under a version-suffixed name
# `g++-15`, ...) are probed under both names: a suffixed name can break while # (`clang-tidy-<v>`, `g++-<v>`, ...) are probed under both names:
# the plain one still works (see mkVersionedToolLinks in nix/packages.nix). # a suffixed name can break while the plain one still works
# (see mkVersionedToolLinks in nix/packages.nix).
# The suffix is the major version of the plain `clang` / `gcc` on PATH.
# #
# Tools scoped to a single dev shell rather than to commonPackages are checked # Tools scoped to a single dev shell rather than to commonPackages are checked
# only in that shell, keyed off XRPL_DEVSHELL. # only in that shell, keyed off XRPL_DEVSHELL.
@@ -34,9 +36,16 @@
set -uo pipefail set -uo pipefail
# Version suffixes of the Nix tool links, tracking nix/packages.nix. # major_version <compiler>
gcc_version=15 # Major version of a compiler on PATH, or "unknown" when it isn't there.
llvm_version=22 major_version() {
local version
version="$("$1" -dumpversion 2>/dev/null)" || version=""
version="${version%%.*}"
printf '%s' "${version:-unknown}"
}
llvm_version="$(major_version clang)"
missing=() missing=()
checked=0 checked=0
@@ -112,6 +121,7 @@ if [ "${os}" = "linux" ] || [ "${os}" = "macos" ]; then
check ClangBuildAnalyzer check ClangBuildAnalyzer
check curl check curl
check file check file
check jq
check less check less
check make check make
# net-tools netstat reports "net-tools X.Y"; macOS ships BSD netstat with no # net-tools netstat reports "net-tools X.Y"; macOS ships BSD netstat with no
@@ -180,6 +190,7 @@ fi
if [ "${os}" = "linux" ]; then if [ "${os}" = "linux" ]; then
echo echo
echo "GCC toolchain:" echo "GCC toolchain:"
gcc_version="$(major_version gcc)"
check gcc check gcc
check "gcc-${gcc_version}" check "gcc-${gcc_version}"
check g++ check g++
File renamed without changes.
File renamed without changes.
+65
View File
@@ -0,0 +1,65 @@
#!/usr/bin/env bash
# Fail if a binary of a build-context Conan package loads anything from the Nix
# store other than glibc, or cannot resolve a library at all.
#
# Only binaries linked by the Nix toolchain are checked, i.e. those recording a
# store path as their interpreter or RUNPATH. Prebuilt upstream binaries (such
# as the ones the cmake package ships) use the system loader instead.
#
# Build-context packages provide the tools that run during the build (protoc,
# grpc_cpp_plugin, ...). Their package ID does not change when a Nix toolchain
# update moves the GCC runtime to a new store path, so a cached binary has to
# get by with the pinned glibc alone. See docs/build/nix.md.
#
# Usage: bin/nix/check-build-context-runtime.sh <graph.json>
# <graph.json> is the output of `conan install --format=json`.
set -euo pipefail
if [ "$#" -ne 1 ]; then
echo "usage: $0 <graph.json>" >&2
exit 2
fi
if [ "$(uname -s)" != "Linux" ]; then
echo "$0: Linux only" >&2
exit 2
fi
folders="$(jq -r '.graph.nodes[] | select(.context == "build" and .package_folder) | .package_folder' "$1" | sort -u)"
checked=0
failed=0
while IFS= read -r file; do
case "$(file -b "${file}")" in
ELF*) ;;
*) continue ;;
esac
[[ "$(readelf -ldW "${file}")" == */nix/store/* ]] || continue
checked=$((checked + 1))
# `ldd` lists the interpreter and every library as the loader resolves them.
if deps="$(ldd "${file}" 2>&1)"; then
bad="$(printf '%s\n' "${deps}" |
grep -E 'not found|/nix/store/' |
grep -vE '/nix/store/[^/]+-glibc-[^/]+/' || true)"
else
case "${deps}" in
*"not a dynamic executable"*) continue ;;
esac
bad="${deps}"
fi
if [ -n "${bad}" ]; then
failed=$((failed + 1))
echo "::error file=${file}::loads a library from the Nix store other than glibc"
echo "${file}"
echo "${bad}" | sed 's/^/ /'
fi
done < <(
# shellcheck disable=SC2086 # one folder per line, no spaces in Conan paths
[ -z "${folders}" ] || find ${folders} -type f \( -perm -u+x -o -name '*.so*' \)
)
echo "Build-context packages: checked ${checked} binaries, ${failed} failed."
[ "${failed}" -eq 0 ]
@@ -10,7 +10,7 @@
# alone; the scripts in a Conan cache are all git hook samples and autotools # alone; the scripts in a Conan cache are all git hook samples and autotools
# scratch, 36 false positives to 0 real. # scratch, 36 false positives to 0 real.
# #
# Usage: bin/check-nix-store-refs.sh <path> # Usage: bin/nix/check-nix-store-refs.sh <path>
set -euo pipefail set -euo pipefail
File renamed without changes.
+1 -1
View File
@@ -23,7 +23,7 @@ apt-get clean
rm -rf /var/lib/apt/lists/* rm -rf /var/lib/apt/lists/*
EOF EOF
ARG PRE_COMMIT_VERSION=4.6.0 ARG PRE_COMMIT_VERSION=4.6.2
RUN pip install --no-cache --break-system-packages \ RUN pip install --no-cache --break-system-packages \
pre-commit==${PRE_COMMIT_VERSION} pre-commit==${PRE_COMMIT_VERSION}
+20 -7
View File
@@ -26,8 +26,6 @@ import sys
import tempfile import tempfile
from pathlib import Path from pathlib import Path
CLANG_TIDY_VERSION = 22
# Extensions run-clang-tidy can analyse: `.cpp` translation units and, thanks to # Extensions run-clang-tidy can analyse: `.cpp` translation units and, thanks to
# the `verify_headers` build option, `.h`/`.hpp` headers (each has its own # the `verify_headers` build option, `.h`/`.hpp` headers (each has its own
# compile_commands.json entry). `.ipp` fragments have no entry and are skipped. # compile_commands.json entry). `.ipp` fragments have no entry and are skipped.
@@ -39,8 +37,21 @@ TIDY_EXTENSIONS = {".cpp", ".h", ".hpp"}
FILEPATH_RE = re.compile(r"^(\s*(?:-\s+)?FilePath:\s*)'((?:[^']|'')*)'\s*$") FILEPATH_RE = re.compile(r"^(\s*(?:-\s+)?FilePath:\s*)'((?:[^']|'')*)'\s*$")
def find_tool(name: str) -> str | None: def clang_tidy_major() -> str | None:
for candidate in (f"{name}-{CLANG_TIDY_VERSION}", name): """Major version of the `clang-tidy` on PATH, which run-clang-tidy invokes."""
if not (clang_tidy := shutil.which("clang-tidy")):
return None
output = subprocess.run(
[clang_tidy, "--version"], capture_output=True, text=True
).stdout
m = re.search(r"LLVM version (\d+)", output)
return m.group(1) if m else None
def find_tool(name: str, version: str | None) -> str | None:
"""Prefer `<name>-<version>`, so a host tool of another version can't win."""
candidates = ([f"{name}-{version}"] if version else []) + [name]
for candidate in candidates:
if path := shutil.which(candidate): if path := shutil.which(candidate):
return path return path
return None return None
@@ -103,8 +114,9 @@ def main():
if not files: if not files:
return 0 return 0
run_clang_tidy = find_tool("run-clang-tidy") version = clang_tidy_major()
clang_apply_replacements = find_tool("clang-apply-replacements") run_clang_tidy = find_tool("run-clang-tidy", version)
clang_apply_replacements = find_tool("clang-apply-replacements", version)
missing = [ missing = [
name name
for name, path in ( for name, path in (
@@ -114,9 +126,10 @@ def main():
if not path if not path
] ]
if missing: if missing:
tried = f" (tried the '-{version}' suffix too)" if version else ""
print( print(
f"clang-tidy check failed: TIDY is enabled but {' and '.join(missing)} " f"clang-tidy check failed: TIDY is enabled but {' and '.join(missing)} "
f"was not found in PATH (tried the '-{CLANG_TIDY_VERSION}' suffix too).", f"was not found in PATH{tried}.",
file=sys.stderr, file=sys.stderr,
) )
return 1 return 1
+2 -2
View File
@@ -17,7 +17,7 @@
(runtime libraries resolved through the rpath) are skipped too. (runtime libraries resolved through the rpath) are skipped too.
Everywhere else `patch_nix_binary` is a no-op. Everywhere else `patch_nix_binary` is a no-op.
The default loader is resolved by bin/default-loader-path.sh. The default loader is resolved by bin/nix/default-loader-path.sh.
#]===================================================================] #]===================================================================]
include_guard(GLOBAL) include_guard(GLOBAL)
@@ -25,7 +25,7 @@ include_guard(GLOBAL)
include(CompilationEnv) include(CompilationEnv)
# Resolves the system default ELF loader path for the current architecture. # Resolves the system default ELF loader path for the current architecture.
set(_loader_path_script "${CMAKE_SOURCE_DIR}/bin/default-loader-path.sh") set(_loader_path_script "${CMAKE_SOURCE_DIR}/bin/nix/default-loader-path.sh")
if( if(
is_linux is_linux
+9
View File
@@ -292,6 +292,14 @@ if(xrpld)
) )
target_sources(xrpld PRIVATE ${sources}) target_sources(xrpld PRIVATE ${sources})
rpcspec_generate_instantiations(
OUT_VAR rpcspec_instantiations
VALUE_TYPE "::json::Value"
VIEW_HEADER "xrpld/rpc/detail/JsonObjectView.hpp"
HANDLERS book_changes ledger transaction_entry
)
target_sources(xrpld PRIVATE ${rpcspec_instantiations})
if(tests) if(tests)
file( file(
GLOB_RECURSE sources GLOB_RECURSE sources
@@ -322,6 +330,7 @@ if(xrpld)
# antithesis_instrumentation.h, which is not exported as INTERFACE # antithesis_instrumentation.h, which is not exported as INTERFACE
target_include_directories( target_include_directories(
xrpld xrpld
SYSTEM
PRIVATE ${CMAKE_SOURCE_DIR}/external/antithesis-sdk PRIVATE ${CMAKE_SOURCE_DIR}/external/antithesis-sdk
) )
endif() endif()
+6 -1
View File
@@ -77,19 +77,24 @@ if(is_clang)
message(STATUS " Ignorelist: ${ignorelist_path}") message(STATUS " Ignorelist: ${ignorelist_path}")
endif() endif()
# Define SANITIZERS macro for BuildInfo.cpp # Define the SANITIZERS macro for BuildInfo.cpp, plus one of XRPL_ASAN,
# XRPL_TSAN and XRPL_UBSAN per active sanitizer, so that code can test for a
# specific one with #ifdef instead of parsing the dot-joined SANITIZERS string.
set(sanitizers_list) set(sanitizers_list)
if(SANITIZERS MATCHES "address") if(SANITIZERS MATCHES "address")
set(enable_asan ON) set(enable_asan ON)
list(APPEND sanitizers_list "ASAN") list(APPEND sanitizers_list "ASAN")
target_compile_definitions(common INTERFACE XRPL_ASAN)
endif() endif()
if(SANITIZERS MATCHES "thread") if(SANITIZERS MATCHES "thread")
set(enable_tsan ON) set(enable_tsan ON)
list(APPEND sanitizers_list "TSAN") list(APPEND sanitizers_list "TSAN")
target_compile_definitions(common INTERFACE XRPL_TSAN)
endif() endif()
if(SANITIZERS MATCHES "undefinedbehavior") if(SANITIZERS MATCHES "undefinedbehavior")
set(enable_ubsan ON) set(enable_ubsan ON)
list(APPEND sanitizers_list "UBSAN") list(APPEND sanitizers_list "UBSAN")
target_compile_definitions(common INTERFACE XRPL_UBSAN)
endif() endif()
if(sanitizers_list) if(sanitizers_list)
+6 -2
View File
@@ -3,7 +3,7 @@
"requires": [ "requires": [
"zlib/1.3.2#1cb806da49011867778ffb6ac7190fcb%1782392402.122708", "zlib/1.3.2#1cb806da49011867778ffb6ac7190fcb%1782392402.122708",
"xxhash/0.8.3#681d36a0a6111fc56e5e45ea182c19cc%1782392402.420688", "xxhash/0.8.3#681d36a0a6111fc56e5e45ea182c19cc%1782392402.420688",
"xrpl-rpc-spec/0.1.19#870b2d3abcfbbf13b61c2d3c69495060%1790348286.187549", "xrpl-rpc-spec/0.1.21#d536f87a2ae7d313452746cfa3ac4404%1790869005.122975",
"sqlite3/3.53.0#324ada52333108388a9a6108bfa96734%1782392403.185447", "sqlite3/3.53.0#324ada52333108388a9a6108bfa96734%1782392403.185447",
"soci/4.0.3#e726491a03468795453f7c83fc924a96%1782392402.679521", "soci/4.0.3#e726491a03468795453f7c83fc924a96%1782392402.679521",
"snappy/1.1.10#968fef506ff261592ec30c574d4a7809%1782307151.633168", "snappy/1.1.10#968fef506ff261592ec30c574d4a7809%1782307151.633168",
@@ -20,7 +20,7 @@
"libarchive/3.8.7#c446109bd1f1d8ba7936c94189bc50e6%1782392403.066892", "libarchive/3.8.7#c446109bd1f1d8ba7936c94189bc50e6%1782392403.066892",
"jemalloc/5.3.1#1fc58d55316041f10fbc1e8a2eae632a%1776700028.228", "jemalloc/5.3.1#1fc58d55316041f10fbc1e8a2eae632a%1776700028.228",
"gtest/1.17.0#5224b3b3ff3b4ce1133cbdd27d53ee7d%1782392402.791979", "gtest/1.17.0#5224b3b3ff3b4ce1133cbdd27d53ee7d%1782392402.791979",
"grpc/1.81.1#b87796a4269034856cbc1a2522db16eb%1788275071.530512", "grpc/1.81.1#aaa93ab6cda2f2baa6a84490582c8adf%1791284951.826256",
"fast_float/8.2.10#f6f28d6bb22112078e7dbda611caf681%1785888854.601666", "fast_float/8.2.10#f6f28d6bb22112078e7dbda611caf681%1785888854.601666",
"ed25519/2015.03#ae761bdc52730a843f0809bdf6c1b1f6%1782307148.15562", "ed25519/2015.03#ae761bdc52730a843f0809bdf6c1b1f6%1782307148.15562",
"date/3.0.4#862e11e80030356b53c2c38599ceb32b%1782392402.538492", "date/3.0.4#862e11e80030356b53c2c38599ceb32b%1782392402.538492",
@@ -34,11 +34,15 @@
"build_requires": [ "build_requires": [
"zlib/1.3.2#1cb806da49011867778ffb6ac7190fcb%1782392402.122708", "zlib/1.3.2#1cb806da49011867778ffb6ac7190fcb%1782392402.122708",
"strawberryperl/5.32.1.1#8d114504d172cfea8ea1662d09b6333e%1782395692.540639", "strawberryperl/5.32.1.1#8d114504d172cfea8ea1662d09b6333e%1782395692.540639",
"re2/20251105#8579cfd0bda4daf0683f9e3898f964b4%1782392402.431897",
"protobuf/6.33.5#ff253ead763bd8d9904a52979cd21e81%1782392410.233933", "protobuf/6.33.5#ff253ead763bd8d9904a52979cd21e81%1782392410.233933",
"openssl/3.6.3#f806de8933e3bf6f01016c6a888cee2e%1783945160.863288",
"nasm/2.16.01#31e26f2ee3c4346ecd347911bd126904%1782395690.33162", "nasm/2.16.01#31e26f2ee3c4346ecd347911bd126904%1782395690.33162",
"msys2/cci.latest#d22fe7b2808f5fd34d0a7923ace9c54f%1770657326.649", "msys2/cci.latest#d22fe7b2808f5fd34d0a7923ace9c54f%1770657326.649",
"m4/1.4.19#1727f439cf74e83826ec96d0b4904eee%1784541921.659", "m4/1.4.19#1727f439cf74e83826ec96d0b4904eee%1784541921.659",
"grpc/1.81.1#aaa93ab6cda2f2baa6a84490582c8adf%1791284951.826256",
"cmake/4.3.3#840cf00ea09777e05c2050a50a82c722%1782392418.696091", "cmake/4.3.3#840cf00ea09777e05c2050a50a82c722%1782392418.696091",
"c-ares/1.34.6#545240bb1c40e2cacd4362d6b8967650%1782392402.681654",
"b2/5.4.2#ffd6084a119587e70f11cd45d1a386e2%1782392402.624226", "b2/5.4.2#ffd6084a119587e70f11cd45d1a386e2%1782392402.624226",
"automake/1.16.5#b91b7c384c3deaa9d535be02da14d04f%1755524470.56", "automake/1.16.5#b91b7c384c3deaa9d535be02da14d04f%1755524470.56",
"autoconf/2.71#51077f068e61700d65bb05541ea1e4b0%1731054366.86", "autoconf/2.71#51077f068e61700d65bb05541ea1e4b0%1731054366.86",
+9 -1
View File
@@ -3,5 +3,13 @@
core:non_interactive=True core:non_interactive=True
core.download:parallel={{ os.cpu_count() }} core.download:parallel={{ os.cpu_count() }}
core.upload:parallel={{ os.cpu_count() }} core.upload:parallel={{ os.cpu_count() }}
tools.files.download:retry=5 # Fall back to Conan Center's source backups when a recipe's upstream URL is down
# (e.g. the GNU FTP mirrors), see
# https://github.com/conan-io/conan-center-index/issues/28147#issuecomment-3183544772
# The backups are only tried once every upstream URL has used up its retries,
# so keep the retries low.
core.sources:download_urls=["origin", "https://c3i.jfrog.io/artifactory/conan-center-backup-sources"]
tools.files.download:retry=1
tools.files.download:retry_wait=10 tools.files.download:retry_wait=10
# Fail fast on unreachable hosts (default connect timeout is 30s), keep the 60s read timeout.
core.net.http:timeout=(5, 60)
+31 -4
View File
@@ -29,9 +29,9 @@ os.version={{ min_macos_version }}
[conf] [conf]
{# The Boost recipe builds with b2, which doesn't use Conan's toolchain files. #} {# The Boost recipe builds with b2, which doesn't use Conan's toolchain files. #}
{# Instead it hand-rolls the compiler for user-config.jam, #} {# Instead it hand-rolls the compiler for user-config.jam, #}
{# and its fallback probes a version-suffixed binary (e.g. `g++-15`) before plain `g++`. #} {# and its fallback probes a version-suffixed binary (e.g. `g++-<major>`) before plain `g++`. #}
{# Inside the Nix shell the wrapper only provides `g++`/`gcc` (no `-15` suffix), #} {# Inside the Nix shell the wrapper only provides `g++`/`gcc` (no `-<major>` suffix), #}
{# so on a host that also has a system `g++-15` the probe escapes Nix #} {# so on a host that also has a system `g++-<major>` the probe escapes Nix #}
{# and picks the system compiler, which is mismatched with the Nix libraries #} {# and picks the system compiler, which is mismatched with the Nix libraries #}
{# and breaks the build (e.g. Boost.Stacktrace link checks fail). #} {# and breaks the build (e.g. Boost.Stacktrace link checks fail). #}
{# Pinning the executables here short-circuits that probe so Boost (and the rest of the toolchain) #} {# Pinning the executables here short-circuits that probe so Boost (and the rest of the toolchain) #}
@@ -49,8 +49,31 @@ tools.build:compiler_executables={'c':'{{ cc_exe }}','cpp':'{{ cxx_exe }}'}
user.package:cppstd_version=23 user.package:cppstd_version=23
tools.info.package_id:confs+=["user.package:cppstd_version"] tools.info.package_id:confs+=["user.package:cppstd_version"]
{% if os == "Macos" %} {% if os == "Linux" and context == "build" %}
{# Build-context executables (protoc, grpc_cpp_plugin, build tools) run during the build #}
{# and would otherwise load libstdc++/libgcc from a Nix store path #}
{# that might change with a Nix toolchain update. #}
{# --as-needed drops the ones they link but don't use, #}
{# such as libatomic for grpc_cpp_plugin on arm64. #}
{% set static_runtime_flags = ["-static-libstdc++", "-static-libgcc", "-Wl,--as-needed"] %}
tools.build:exelinkflags+={{ static_runtime_flags }}
tools.info.package_id:confs+=["tools.build:exelinkflags"]
{% endif %}
{% if os == "Linux" and context == "build" %}
{# b2 links itself with its own script, which ignores exelinkflags #}
{# and only takes CXXFLAGS when use_cxx_env is set (see [buildenv] below). #}
[options]
b2/*:use_cxx_env=True
{% endif %}
[buildenv] [buildenv]
{# gRPC emits thousands of compiler warnings that we cannot act on. #}
{# CMake picks up CXXFLAGS, and unlike tools.build:cxxflags, #}
{# this is not part of the package ID, so binaries stay shareable. #}
grpc/*:CXXFLAGS=-w
{% if os == "Macos" %}
{# os.version adds -mmacosx-version-min to compiler command lines, #} {# os.version adds -mmacosx-version-min to compiler command lines, #}
{# but Boost.Context's b2 assembly (.S) rule ignores it, #} {# but Boost.Context's b2 assembly (.S) rule ignores it, #}
{# so those objects keep the host SDK version and still warn at link time. #} {# so those objects keep the host SDK version and still warn at link time. #}
@@ -58,3 +81,7 @@ tools.info.package_id:confs+=["user.package:cppstd_version"]
{# Scoped to boost/* since it is the only gap. #} {# Scoped to boost/* since it is the only gap. #}
boost/*:MACOSX_DEPLOYMENT_TARGET={{ min_macos_version }} boost/*:MACOSX_DEPLOYMENT_TARGET={{ min_macos_version }}
{% endif %} {% endif %}
{% if os == "Linux" and context == "build" %}
b2/*:CXXFLAGS={{ static_runtime_flags | join(" ") }}
{% endif %}
+3
View File
@@ -5,6 +5,9 @@ include(default)
{% if not sanitizers %} {% if not sanitizers %}
{# Sanitizers not configured; no additional settings needed #} {# Sanitizers not configured; no additional settings needed #}
{% elif context == "build" %}
{# Build-context packages are tools we run, not code we test, #}
{# so don't instrument them #}
{% else %} {% else %}
{% if compiler == "msvc" %} {% if compiler == "msvc" %}
+8 -3
View File
@@ -40,7 +40,7 @@ class Xrpl(ConanFile):
"nudb/2.0.9", "nudb/2.0.9",
"openssl/3.6.3", "openssl/3.6.3",
"soci/4.0.3", "soci/4.0.3",
"xrpl-rpc-spec/0.1.19", "xrpl-rpc-spec/0.1.21",
"zlib/1.3.2", "zlib/1.3.2",
] ]
@@ -49,7 +49,8 @@ class Xrpl(ConanFile):
] ]
tool_requires = [ tool_requires = [
"protobuf/6.33.5", "grpc/<host_version>",
"protobuf/<host_version>",
] ]
default_options = { default_options = {
@@ -123,6 +124,10 @@ class Xrpl(ConanFile):
"xxhash/*:shared": False, "xxhash/*:shared": False,
} }
# default_options only reach the host context;
# give tool_requires (and their dependencies) the same dependency options.
default_build_options = {k: v for k, v in default_options.items() if "/" in k}
def set_version(self): def set_version(self):
self.version = self.version or DEV_VERSION self.version = self.version or DEV_VERSION
@@ -149,7 +154,7 @@ class Xrpl(ConanFile):
self.requires("xxhash/0.8.3", transitive_headers=True) self.requires("xxhash/0.8.3", transitive_headers=True)
exports_sources = ( exports_sources = (
"bin/default-loader-path.sh", "bin/nix/default-loader-path.sh",
"CMakeLists.txt", "CMakeLists.txt",
"cfg/*", "cfg/*",
"cmake/*", "cmake/*",
+5 -6
View File
@@ -80,13 +80,12 @@ function(add_xrpl_crate name)
# `cc` picks its runtime flag from `crt-static` alone, so it compiles a # `cc` picks its runtime flag from `crt-static` alone, so it compiles a
# crate's C++ with `-MT`; Debug needs `-MTd` (to match cmake/XrplCompiler.cmake). # crate's C++ with `-MT`; Debug needs `-MTd` (to match cmake/XrplCompiler.cmake).
if(is_msvc) if(is_msvc)
corrosion_set_env_vars( corrosion_set_env_vars(${ARG_CRATE} "$<$<CONFIG:Debug>:CXXFLAGS=-MTd>")
${ARG_CRATE}
"$<$<CONFIG:Debug>:CXXFLAGS=-MTd>"
)
endif() endif()
corrosion_add_cxxbridge(${name}_cxxbridge CRATE ${ARG_CRATE} FILES corrosion_add_cxxbridge(
${ARG_FILES} ${name}_cxxbridge
CRATE ${ARG_CRATE}
FILES ${ARG_FILES}
) )
# Generated cxxbridge headers don't exist at configure time; CMake 3.28+ # Generated cxxbridge headers don't exist at configure time; CMake 3.28+
# validates INTERFACE_SOURCES on consuming targets. Clear it to skip the # validates INTERFACE_SOURCES on consuming targets. Clear it to skip the
+9 -7
View File
@@ -10,14 +10,15 @@ This document explains how to set one up.
support it — see [compiler support for C++23][cpp23-support]. support it — see [compiler support for C++23][cpp23-support].
The versions currently tested in CI are: The versions currently tested in CI are:
| Compiler | Version | | Compiler | Version |
| ----------- | ------------------ | | ----------- | ------------------------------- |
| GCC | 15.2 | | GCC | `gccVersion` in [packages.nix] |
| Clang | 22 | | Clang | `llvmVersion` in [packages.nix] |
| Apple Clang | 21 | | Apple Clang | 21 |
| MSVC | Visual Studio 2026 | | MSVC | Visual Studio 2026 |
LLVM tools (`clang-tidy` and `clang-format`) are also pinned to version 22. LLVM tools (`clang-tidy` and `clang-format`)
come from the same LLVM release as Clang.
### Older compilers ### Older compilers
@@ -156,3 +157,4 @@ version out of the box — run it via `run-clang-tidy`. No separate installation
is needed. is needed.
[cpp23-support]: https://en.cppreference.com/w/cpp/compiler_support/23 [cpp23-support]: https://en.cppreference.com/w/cpp/compiler_support/23
[packages.nix]: ../../nix/packages.nix
+21 -9
View File
@@ -183,24 +183,36 @@ at link or run time.
> configuration CI covers, and no dependency binaries are published for it. > configuration CI covers, and no dependency binaries are published for it.
This is checked rather than assumed. This is checked rather than assumed.
[`bin/check-nix-store-refs.sh`](../../bin/check-nix-store-refs.sh) takes one file [`bin/nix/check-nix-store-refs.sh`](../../bin/nix/check-nix-store-refs.sh) takes one
or directory and fails if a binary under it resolves a store path at run time. file or directory and fails if a binary under it resolves a store path at run time.
CI runs it over the build output and the Conan cache, and again in the upload job CI runs it over the build output and the Conan cache, and again in the upload job
before anything is published. You can run it yourself: before anything is published. You can run it yourself:
```bash ```bash
bin/check-nix-store-refs.sh build bin/nix/check-nix-store-refs.sh build
bin/check-nix-store-refs.sh ~/.conan2-nix bin/nix/check-nix-store-refs.sh ~/.conan2-nix
``` ```
It works on Linux too, but asserts something narrower there: the toolchain always It works on Linux too, but asserts something narrower there: the toolchain always
writes the store into `PT_INTERP` and `RUNPATH`, and CI builds inside an image writes the store into `PT_INTERP` and `RUNPATH`. That is fine for the pinned
whose store is fixed for its lifetime, so that is fine. Only the binaries glibc, whose path does not move, but not for the GCC runtime, which moves with
[`PatchNixBinary.cmake`](../../cmake/PatchNixBinary.cmake) retargets to the every GCC update. So [`conan/profiles/default`](../../conan/profiles/default)
system loader have to be clean, and those are what CI checks: links build-context packages, whose executables run during the build, with
`-static-libstdc++ -static-libgcc -Wl,--as-needed`, and
[`conan/profiles/sanitizers`](../../conan/profiles/sanitizers) does not
instrument them. CI checks that they load nothing from the store but glibc, from
the graph `conan install --format=json` writes:
```bash ```bash
bin/check-nix-store-refs.sh build/xrpld bin/nix/check-build-context-runtime.sh graph.json
```
Only the binaries [`PatchNixBinary.cmake`](../../cmake/PatchNixBinary.cmake)
retargets to the system loader have to be fully clean, and those are what CI
checks:
```bash
bin/nix/check-nix-store-refs.sh build/xrpld
``` ```
### The libresolv stub ### The libresolv stub
+3 -3
View File
@@ -178,11 +178,11 @@ A binary stops starting after a `nix flake update`, or after
dyld[57271]: Library not loaded: /nix/store/…-libresolv-93/lib/libresolv.9.dylib dyld[57271]: Library not loaded: /nix/store/…-libresolv-93/lib/libresolv.9.dylib
``` ```
[`bin/check-nix-store-refs.sh`](../../bin/check-nix-store-refs.sh) finds the same [`bin/nix/check-nix-store-refs.sh`](../../bin/nix/check-nix-store-refs.sh) finds the
thing without having to run anything, and names the file: same thing without having to run anything, and names the file:
``` ```
$ bin/check-nix-store-refs.sh ~/.conan2-nix $ bin/nix/check-nix-store-refs.sh ~/.conan2-nix
::error file=/Users/you/.conan2-nix/p/b/c-area24ded30c388c/p/bin/adig::references the Nix store at run time ::error file=/Users/you/.conan2-nix/p/b/c-area24ded30c388c/p/bin/adig::references the Nix store at run time
/Users/you/.conan2-nix/p/b/c-area24ded30c388c/p/bin/adig /Users/you/.conan2-nix/p/b/c-area24ded30c388c/p/bin/adig
/nix/store/p4lp3xq4imd1qzqh08x8vcq2zfhi7rca-libresolv-93/lib/libresolv.9.dylib /nix/store/p4lp3xq4imd1qzqh08x8vcq2zfhi7rca-libresolv-93/lib/libresolv.9.dylib
+1 -1
View File
@@ -6,7 +6,7 @@ project(antithesis-sdk-cpp VERSION 0.4.4 LANGUAGES CXX)
add_library(antithesis-sdk-cpp INTERFACE antithesis_sdk.h) add_library(antithesis-sdk-cpp INTERFACE antithesis_sdk.h)
# Note, both sections below created by xrpld project # Note, both sections below created by xrpld project
target_include_directories(antithesis-sdk-cpp INTERFACE target_include_directories(antithesis-sdk-cpp SYSTEM INTERFACE
$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}> $<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}> $<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}>
) )
Generated
+6 -6
View File
@@ -2,11 +2,11 @@
"nodes": { "nodes": {
"nixpkgs": { "nixpkgs": {
"locked": { "locked": {
"lastModified": 1781173989, "lastModified": 1791130267,
"narHash": "sha256-fnzKKPvS+oieI/pTzotA5tkoM47EB1NpaBcgk4R97hE=", "narHash": "sha256-1sjwcQMcgAbmiip/VivBSiK8p2bTkQGOvCuO7vnwfx4=",
"owner": "NixOS", "owner": "NixOS",
"repo": "nixpkgs", "repo": "nixpkgs",
"rev": "8c91a71d13451abc40eb9dae8910f972f979852f", "rev": "9013764fcc0ea99fa16cf7aa7decf8a5c3889dd2",
"type": "github" "type": "github"
}, },
"original": { "original": {
@@ -47,11 +47,11 @@
] ]
}, },
"locked": { "locked": {
"lastModified": 1784611586, "lastModified": 1791189933,
"narHash": "sha256-OfqgY+0hp/zseZB7uyH0U8kIDPS4scZZCyAurEplvG0=", "narHash": "sha256-Y8eN7ki0Urx4Ojf4w1xSpWg8uk/3lJqK+E0Oth77rH0=",
"owner": "oxalica", "owner": "oxalica",
"repo": "rust-overlay", "repo": "rust-overlay",
"rev": "14f58845249f3552a89b07772626b8d3c632fa86", "rev": "e60029353d0c48d216bc4b065168ccd4079c166f",
"type": "github" "type": "github"
}, },
"original": { "original": {
+118
View File
@@ -0,0 +1,118 @@
#pragma once
#include <functional>
#include <mutex>
#include <set>
/**
* RAII class to check if an Item is already being processed on another thread,
* as indicated by it's presence in a Collection.
*
* If the Item is not in the Collection, it will be added under lock in the
* ctor, and removed under lock in the dtor. The object will be considered
* "usable" and evaluate to `true`.
*
* If the Item is in the Collection, no changes will be made to the collection,
* and the CanProcess object will be considered "unusable".
*
* It's up to the caller to decide what "usable" and "unusable" mean. (e.g.
* Process or skip a block of code, or set a flag.)
*
* The current use is to avoid lock contention that would be involved in
* processing something associated with the Item.
*
* Examples:
*
* void IncomingLedgers::acquireAsync(LedgerHash const& hash, ...)
* {
* if (CanProcess check{acquiresMutex_, pendingAcquires_, hash})
* {
* acquire(hash, ...);
* }
* }
*
* bool
* NetworkOPsImp::recvValidation(
* std::shared_ptr<STValidation> const& val,
* std::string const& source)
* {
* CanProcess check(
* validationsMutex_, pendingValidations_, val->getLedgerHash());
* BypassAccept bypassAccept =
* check ? BypassAccept::no : BypassAccept::yes;
* handleNewValidation(app_, val, source, bypassAccept, m_journal);
* }
*
*/
class CanProcess
{
public:
template <class Mutex, class Collection, class Item>
CanProcess(Mutex& mtx, Collection& collection, Item const& item)
: cleanup_(insert(mtx, collection, item))
{
}
~CanProcess()
{
if (cleanup_)
cleanup_();
}
CanProcess(CanProcess const&) = delete;
CanProcess&
operator=(CanProcess const&) = delete;
explicit
operator bool() const
{
return static_cast<bool>(cleanup_);
}
private:
template <bool useIterator, class Mutex, class Collection, class Item>
std::function<void()>
doInsert(Mutex& mtx, Collection& collection, Item const& item)
{
std::unique_lock<Mutex> lock(mtx);
// TODO: Use structured binding once LLVM 16 is the minimum supported
// version. See also: https://github.com/llvm/llvm-project/issues/48582
// https://github.com/llvm/llvm-project/commit/127bf44385424891eb04cff8e52d3f157fc2cb7c
auto const insertResult = collection.insert(item);
auto const it = insertResult.first;
if (!insertResult.second)
return {};
if constexpr (useIterator)
return [&, it]() {
std::unique_lock<Mutex> lock(mtx);
collection.erase(it);
};
else
return [&]() {
std::unique_lock<Mutex> lock(mtx);
collection.erase(item);
};
}
// Generic insert() function doesn't use iterators because they may get
// invalidated
template <class Mutex, class Collection, class Item>
std::function<void()>
insert(Mutex& mtx, Collection& collection, Item const& item)
{
return doInsert<false>(mtx, collection, item);
}
// Specialize insert() for std::set, which does not invalidate iterators for
// insert and erase
template <class Mutex, class Item>
std::function<void()>
insert(Mutex& mtx, std::set<Item>& collection, Item const& item)
{
return doInsert<true>(mtx, collection, item);
}
// If set, then the item is "usable"
std::function<void()> cleanup_;
};
+75
View File
@@ -3,9 +3,84 @@
#include <algorithm> #include <algorithm>
#include <cassert> #include <cassert>
#include <cstddef> #include <cstddef>
#include <cstdint>
#include <limits>
#include <optional>
namespace xrpl { namespace xrpl {
/**
* Add two signed 64-bit integers, returning std::nullopt when the exact
* mathematical sum is not representable in std::int64_t.
*/
[[nodiscard]] constexpr std::optional<std::int64_t>
checkedAdd(std::int64_t a, std::int64_t b) noexcept
{
using L = std::numeric_limits<std::int64_t>;
if ((b > 0 && a > L::max() - b) || (b < 0 && a < L::min() - b))
return std::nullopt;
return a + b;
}
/**
* Subtract two signed 64-bit integers, returning std::nullopt when the exact
* mathematical difference is not representable in std::int64_t.
*/
[[nodiscard]] constexpr std::optional<std::int64_t>
checkedSub(std::int64_t a, std::int64_t b) noexcept
{
using L = std::numeric_limits<std::int64_t>;
if ((b > 0 && a < L::min() + b) || (b < 0 && a > L::max() + b))
return std::nullopt;
return a - b;
}
static_assert(checkedAdd(0, 0) == 0);
static_assert(checkedAdd(1, -1) == 0);
static_assert(checkedAdd(-5, 2) == -3);
static_assert(!checkedAdd(std::numeric_limits<std::int64_t>::max(), 1).has_value());
static_assert(!checkedAdd(std::numeric_limits<std::int64_t>::min(), -1).has_value());
static_assert(
checkedAdd(std::numeric_limits<std::int64_t>::max() - 1, 1) ==
std::numeric_limits<std::int64_t>::max());
static_assert(
checkedAdd(
std::numeric_limits<std::int64_t>::min(),
std::numeric_limits<std::int64_t>::max()) == -1);
static_assert(
checkedAdd(
std::numeric_limits<std::int64_t>::max(),
std::numeric_limits<std::int64_t>::min()) == -1);
static_assert(
!checkedAdd(std::numeric_limits<std::int64_t>::max(), std::numeric_limits<std::int64_t>::max())
.has_value());
static_assert(
!checkedAdd(std::numeric_limits<std::int64_t>::min(), std::numeric_limits<std::int64_t>::min())
.has_value());
static_assert(checkedSub(0, 0) == 0);
static_assert(checkedSub(1, 1) == 0);
static_assert(checkedSub(-5, 2) == -7);
static_assert(checkedSub(-5, -2) == -3);
static_assert(!checkedSub(std::numeric_limits<std::int64_t>::min(), 1).has_value());
static_assert(!checkedSub(std::numeric_limits<std::int64_t>::max(), -1).has_value());
static_assert(
checkedSub(std::numeric_limits<std::int64_t>::min() + 1, 1) ==
std::numeric_limits<std::int64_t>::min());
static_assert(
checkedSub(-1, std::numeric_limits<std::int64_t>::max()) ==
std::numeric_limits<std::int64_t>::min());
static_assert(
!checkedSub(std::numeric_limits<std::int64_t>::max(), std::numeric_limits<std::int64_t>::min())
.has_value());
static_assert(
!checkedSub(std::numeric_limits<std::int64_t>::min(), std::numeric_limits<std::int64_t>::max())
.has_value());
/** /**
* Calculate one number divided by another number in percentage. * Calculate one number divided by another number in percentage.
* The result is rounded up to the next integer, and capped in the range [0,100] * The result is rounded up to the next integer, and capped in the range [0,100]
+1 -1
View File
@@ -36,7 +36,7 @@ template <typename T>
concept SomeChar = std::same_as<std::remove_cvref_t<T>, int8_t> || concept SomeChar = std::same_as<std::remove_cvref_t<T>, int8_t> ||
std::same_as<std::remove_cvref_t<T>, char> || std::same_as<std::remove_cvref_t<T>, uint8_t>; std::same_as<std::remove_cvref_t<T>, char> || std::same_as<std::remove_cvref_t<T>, uint8_t>;
inline constexpr std::array<std::optional<int>, 256> const kDigitLookupTable = []() { inline constexpr std::array<std::optional<int>, 256> const kDigitLookupTable = [] {
std::array<std::optional<int>, 256> t{}; std::array<std::optional<int>, 256> t{};
for (int i = 0; i < 10; ++i) for (int i = 0; i < 10; ++i)
+2 -2
View File
@@ -783,7 +783,7 @@ TaggedCache<Key, T, IsKeyCache, SharedWeakUnionPointer, SharedPointerType, Hash,
std::atomic<int>& allRemovals, std::atomic<int>& allRemovals,
std::scoped_lock<std::recursive_mutex> const&) std::scoped_lock<std::recursive_mutex> const&)
{ {
return std::thread([&, this]() { return std::thread([&, this] {
int cacheRemovals = 0; int cacheRemovals = 0;
int mapRemovals = 0; int mapRemovals = 0;
@@ -863,7 +863,7 @@ TaggedCache<Key, T, IsKeyCache, SharedWeakUnionPointer, SharedPointerType, Hash,
std::atomic<int>& allRemovals, std::atomic<int>& allRemovals,
std::scoped_lock<std::recursive_mutex> const&) std::scoped_lock<std::recursive_mutex> const&)
{ {
return std::thread([&, this]() { return std::thread([&, this] {
// NOLINTBEGIN https://github.com/XRPLF/rippled/issues/7056 // NOLINTBEGIN https://github.com/XRPLF/rippled/issues/7056
int cacheRemovals = 0; int cacheRemovals = 0;
int mapRemovals = 0; int mapRemovals = 0;
@@ -17,7 +17,7 @@
namespace xrpl { namespace xrpl {
template <typename Key> template <typename Key>
static std::size_t std::size_t
extract(Key const& key) extract(Key const& key)
{ {
return key; return key;
@@ -1604,7 +1604,7 @@ AgedOrderedContainer<IsMulti, IsMap, Key, T, Clock, Compare, Allocator>::erase(
beast::detail::AgedContainerIterator<IsConst, Iterator> pos) beast::detail::AgedContainerIterator<IsConst, Iterator> pos)
requires(!IsBoostReverseIterator<Iterator>::value) requires(!IsBoostReverseIterator<Iterator>::value)
{ {
unlinkAndDeleteElement(&*((pos++).iterator())); unlinkAndDeleteElement(&*(pos++).iterator());
return beast::detail::AgedContainerIterator<false, Iterator>(pos.iterator()); return beast::detail::AgedContainerIterator<false, Iterator>(pos.iterator());
} }
@@ -1617,7 +1617,7 @@ AgedOrderedContainer<IsMulti, IsMap, Key, T, Clock, Compare, Allocator>::erase(
requires(!IsBoostReverseIterator<Iterator>::value) requires(!IsBoostReverseIterator<Iterator>::value)
{ {
for (; first != last;) for (; first != last;)
unlinkAndDeleteElement(&*((first++).iterator())); unlinkAndDeleteElement(&*(first++).iterator());
return beast::detail::AgedContainerIterator<false, Iterator>(first.iterator()); return beast::detail::AgedContainerIterator<false, Iterator>(first.iterator());
} }
@@ -2404,7 +2404,7 @@ beast::detail::AgedContainerIterator<false, Iterator>
AgedUnorderedContainer<IsMulti, IsMap, Key, T, Clock, Hash, KeyEqual, Allocator>::erase( AgedUnorderedContainer<IsMulti, IsMap, Key, T, Clock, Hash, KeyEqual, Allocator>::erase(
beast::detail::AgedContainerIterator<IsConst, Iterator> pos) beast::detail::AgedContainerIterator<IsConst, Iterator> pos)
{ {
unlinkAndDeleteElement(&*((pos++).iterator())); unlinkAndDeleteElement(&*(pos++).iterator());
return beast::detail::AgedContainerIterator<false, Iterator>(pos.iterator()); return beast::detail::AgedContainerIterator<false, Iterator>(pos.iterator());
} }
@@ -2424,7 +2424,7 @@ AgedUnorderedContainer<IsMulti, IsMap, Key, T, Clock, Hash, KeyEqual, Allocator>
beast::detail::AgedContainerIterator<IsConst, Iterator> last) beast::detail::AgedContainerIterator<IsConst, Iterator> last)
{ {
for (; first != last;) for (; first != last;)
unlinkAndDeleteElement(&*((first++).iterator())); unlinkAndDeleteElement(&*(first++).iterator());
return beast::detail::AgedContainerIterator<false, Iterator>(first.iterator()); return beast::detail::AgedContainerIterator<false, Iterator>(first.iterator());
} }
+1 -1
View File
@@ -390,7 +390,7 @@ void
hash_append(Hasher& h, boost::container::flat_set<Key, Compare, Alloc> const& v) noexcept hash_append(Hasher& h, boost::container::flat_set<Key, Compare, Alloc> const& v) noexcept
requires(IsContiguouslyHashable<Key, Hasher>::value) requires(IsContiguouslyHashable<Key, Hasher>::value)
{ {
h(&(v.begin()), v.size() * sizeof(Key)); h(&v.begin(), v.size() * sizeof(Key));
} }
// tuple // tuple
+1 -1
View File
@@ -8,7 +8,7 @@ namespace beast::insight {
class HookImpl : public std::enable_shared_from_this<HookImpl> class HookImpl : public std::enable_shared_from_this<HookImpl>
{ {
public: public:
using HandlerType = std::function<void(void)>; using HandlerType = std::function<void()>;
virtual ~HookImpl() = 0; virtual ~HookImpl() = 0;
}; };
+2 -2
View File
@@ -61,7 +61,7 @@ isMulticast(Address const& addr)
inline bool inline bool
isPrivate(Address const& addr) isPrivate(Address const& addr)
{ {
return (addr.is_v4()) ? isPrivate(addr.to_v4()) : isPrivate(addr.to_v6()); return addr.is_v4() ? isPrivate(addr.to_v4()) : isPrivate(addr.to_v6());
} }
/** /**
@@ -70,7 +70,7 @@ isPrivate(Address const& addr)
inline bool inline bool
isPublic(Address const& addr) isPublic(Address const& addr)
{ {
return (addr.is_v4()) ? isPublic(addr.to_v4()) : isPublic(addr.to_v6()); return addr.is_v4() ? isPublic(addr.to_v4()) : isPublic(addr.to_v6());
} }
} // namespace ip } // namespace ip
+1 -1
View File
@@ -34,7 +34,7 @@ typeName()
name += " volatile"; name += " volatile";
if (std::is_lvalue_reference_v<T>) if (std::is_lvalue_reference_v<T>)
{ {
name += "&"; name += '&';
} }
else if (std::is_rvalue_reference_v<T>) else if (std::is_rvalue_reference_v<T>)
{ {
+1 -1
View File
@@ -20,7 +20,7 @@ namespace beast::unit_test {
namespace detail { namespace detail {
template <class String> template <class String>
static std::string std::string
makeReason(String const& reason, char const* file, int line) makeReason(String const& reason, char const* file, int line)
{ {
std::string s(reason); std::string s(reason);
+3 -3
View File
@@ -47,8 +47,8 @@ public:
template <class F, class... Args> template <class F, class... Args>
explicit Thread(Suite& s, F&& f, Args&&... args) : s_(&s) explicit Thread(Suite& s, F&& f, Args&&... args) : s_(&s)
{ {
std::function<void(void)> b = [f = std::forward<F>(f), std::function<void()> b = [f = std::forward<F>(f),
... args = std::forward<Args>(args)]() mutable { ... args = std::forward<Args>(args)] mutable {
std::invoke(f, args...); std::invoke(f, args...);
}; };
t_ = std::thread(&Thread::run, this, std::move(b)); t_ = std::thread(&Thread::run, this, std::move(b));
@@ -94,7 +94,7 @@ public:
private: private:
void void
run(std::function<void(void)> f) run(std::function<void()> f)
{ {
try try
{ {
+2 -2
View File
@@ -54,7 +54,7 @@ JobQueue::Coro::post()
} }
// sp keeps 'this' alive // sp keeps 'this' alive
if (jq_.addJob(type_, name_, [this, sp = shared_from_this()]() { resume(); })) if (jq_.addJob(type_, name_, [this, sp = shared_from_this()] { resume(); }))
{ {
return true; return true;
} }
@@ -130,7 +130,7 @@ inline void
JobQueue::Coro::join() JobQueue::Coro::join()
{ {
std::unique_lock<std::mutex> lk(mutexRun_); std::unique_lock<std::mutex> lk(mutexRun_);
cv_.wait(lk, [this]() { return !running_; }); cv_.wait(lk, [this] { return !running_; });
} }
} // namespace xrpl } // namespace xrpl
+1 -1
View File
@@ -221,7 +221,7 @@ public:
/** /**
* Add a suppression peer and get message's relay status. * Add a suppression peer and get message's relay status.
* Return pair: * Return pair:
* element 1: true if the peer is added. * element 1: true if the key is added.
* element 2: optional is seated to the relay time point or * element 2: optional is seated to the relay time point or
* is unseated if has not relayed yet. * is unseated if has not relayed yet.
*/ */
@@ -1,11 +1,17 @@
#pragma once #pragma once
#include <xrpl/basics/base_uint.h>
#include <xrpl/basics/chrono.h>
#include <xrpl/beast/utility/Journal.h> #include <xrpl/beast/utility/Journal.h>
#include <xrpl/ledger/ApplyView.h> #include <xrpl/ledger/ApplyView.h>
#include <xrpl/ledger/ReadView.h> #include <xrpl/ledger/ReadView.h>
#include <xrpl/ledger/entries/SLEBase.h> #include <xrpl/ledger/entries/SLEBase.h>
#include <xrpl/protocol/Indexes.h> #include <xrpl/protocol/Indexes.h>
#include <xrpl/protocol/LedgerFormats.h> #include <xrpl/protocol/LedgerFormats.h>
#include <xrpl/protocol/SField.h>
#include <map>
#include <set>
namespace xrpl { namespace xrpl {
@@ -25,6 +31,52 @@ public:
: Base(keylet::amendments(), view, j) : Base(keylet::amendments(), view, j)
{ {
} }
/**
* Returns the set of amendments this entry reports as enabled.
*
* @return the set of enabled amendments.
*/
[[nodiscard]] std::set<UInt256>
enabledAmendments() const
{
std::set<UInt256> amendments;
if (this->exists() && (*this)->isFieldPresent(sfAmendments))
{
auto const& v = (*this)->getFieldV256(sfAmendments);
amendments.insert_range(v);
}
return amendments;
}
/**
* Returns a map of amendments that have achieved majority, to the time
* majority was reached.
*
* @return a map of amendment to the time majority was reached.
*/
[[nodiscard]] std::map<UInt256, NetClock::time_point>
majorityAmendments() const
{
std::map<UInt256, NetClock::time_point> ret;
if (this->exists() && (*this)->isFieldPresent(sfMajorities))
{
using TimePoint = NetClock::time_point;
using Duration = TimePoint::duration;
auto const majorities = (*this)->getFieldArray(sfMajorities);
for (auto const& m : majorities)
{
ret[m.getFieldH256(sfAmendment)] = TimePoint(Duration(m.getFieldU32(sfCloseTime)));
}
}
return ret;
}
}; };
using AmendmentsEntryR = AmendmentsEntry<ReadView>; using AmendmentsEntryR = AmendmentsEntry<ReadView>;
@@ -1,11 +1,17 @@
#pragma once #pragma once
#include <xrpl/basics/base_uint.h>
#include <xrpl/beast/utility/Journal.h> #include <xrpl/beast/utility/Journal.h>
#include <xrpl/ledger/ApplyView.h> #include <xrpl/ledger/ApplyView.h>
#include <xrpl/ledger/ReadView.h> #include <xrpl/ledger/ReadView.h>
#include <xrpl/ledger/entries/SLEBase.h> #include <xrpl/ledger/entries/SLEBase.h>
#include <xrpl/protocol/Indexes.h> #include <xrpl/protocol/Indexes.h>
#include <xrpl/protocol/LedgerFormats.h> #include <xrpl/protocol/LedgerFormats.h>
#include <xrpl/protocol/SField.h>
#include <xrpl/protocol/STVector256.h>
#include <cstddef>
#include <optional>
namespace xrpl { namespace xrpl {
@@ -25,6 +31,31 @@ public:
: Base(keylet::skip(), view, j) : Base(keylet::skip(), view, j)
{ {
} }
/**
* Looks up a hash `diff` slots back from the most recent entry in the
* sfHashes vector (diff == 0 is the most recent entry).
*
* Callers decide which skip list entry to read and how to translate a
* target ledger sequence into `diff`; this only does the bounds check
* and vector indexing shared by both the recent (stride 1) and distant
* (stride 256) skip lists.
*
* @param diff how many slots back from the most recent hash to look up;
* 0 is the most recent hash.
* @return the hash at that slot, or std::nullopt if the entry does not
* exist or `diff` is out of range.
*/
[[nodiscard]] std::optional<UInt256>
hashAt(std::size_t diff) const
{
if (!this->exists())
return std::nullopt;
STVector256 const vec = (*this)->getFieldV256(sfHashes);
if (vec.size() > diff)
return vec[vec.size() - diff - 1];
return std::nullopt;
}
}; };
using LedgerHashesEntryR = LedgerHashesEntry<ReadView>; using LedgerHashesEntryR = LedgerHashesEntry<ReadView>;
+10 -12
View File
@@ -353,7 +353,7 @@ changeSpotPriceQuality(
} }
if (auto const nTakerPaysPropose = (-b + root2(res)) / (2 * a); nTakerPaysPropose > 0) if (auto const nTakerPaysPropose = (-b + root2(res)) / (2 * a); nTakerPaysPropose > 0)
{ {
auto const nTakerPays = [&]() { auto const nTakerPays = [&] {
// The fee might make the AMM offer quality less than CLOB // The fee might make the AMM offer quality less than CLOB
// quality. Therefore, AMM offer has to satisfy this constraint: // quality. Therefore, AMM offer has to satisfy this constraint:
// o / i >= q. Substituting o with swapAssetIn() gives: i <= O / // o / i >= q. Substituting o with swapAssetIn() gives: i <= O /
@@ -372,8 +372,8 @@ changeSpotPriceQuality(
auto const takerPays = auto const takerPays =
toAmount<TIn>(getAsset(pool.in), nTakerPays, Number::RoundingMode::Upward); toAmount<TIn>(getAsset(pool.in), nTakerPays, Number::RoundingMode::Upward);
// should not fail // should not fail
if (auto amounts = TAmounts<TIn, TOut>{takerPays, swapAssetIn(pool, takerPays, tfee)}; auto amounts = TAmounts<TIn, TOut>{takerPays, swapAssetIn(pool, takerPays, tfee)};
Quality{amounts} < quality && if (Quality{amounts} < quality &&
!withinRelativeDistance(Quality{amounts}, quality, Number(1, -7))) !withinRelativeDistance(Quality{amounts}, quality, Number(1, -7)))
{ {
JLOG(j.error()) << "changeSpotPriceQuality failed: " << to_string(pool.in) << " " JLOG(j.error()) << "changeSpotPriceQuality failed: " << to_string(pool.in) << " "
@@ -382,21 +382,19 @@ changeSpotPriceQuality(
<< " " << to_string(amounts.out); << " " << to_string(amounts.out);
Throw<std::runtime_error>("changeSpotPriceQuality failed"); Throw<std::runtime_error>("changeSpotPriceQuality failed");
} }
else
{ JLOG(j.trace()) << "changeSpotPriceQuality succeeded: " << to_string(pool.in) << " "
JLOG(j.trace()) << "changeSpotPriceQuality succeeded: " << to_string(pool.in) << " " << to_string(pool.out) << " "
<< to_string(pool.out) << " " << " " << quality << " " << tfee << " " << to_string(amounts.in) << " "
<< " " << quality << " " << tfee << " " << to_string(amounts.in) << to_string(amounts.out);
<< " " << to_string(amounts.out); return amounts;
return amounts;
}
} }
JLOG(j.trace()) << "changeSpotPriceQuality calc failed: " << to_string(pool.in) << " " JLOG(j.trace()) << "changeSpotPriceQuality calc failed: " << to_string(pool.in) << " "
<< to_string(pool.out) << " " << quality << " " << tfee; << to_string(pool.out) << " " << quality << " " << tfee;
return std::nullopt; return std::nullopt;
} }
auto amounts = [&]() { auto amounts = [&] {
bool const inIntegral = getAsset(pool.in).integral(); bool const inIntegral = getAsset(pool.in).integral();
bool const outIntegral = getAsset(pool.out).integral(); bool const outIntegral = getAsset(pool.out).integral();
+291 -3
View File
@@ -2,8 +2,10 @@
#include <xrpl/basics/Log.h> #include <xrpl/basics/Log.h>
#include <xrpl/beast/utility/Journal.h> #include <xrpl/beast/utility/Journal.h>
#include <xrpl/beast/utility/Zero.h>
#include <xrpl/beast/utility/instrumentation.h> #include <xrpl/beast/utility/instrumentation.h>
#include <xrpl/ledger/ApplyView.h> #include <xrpl/ledger/ApplyView.h>
#include <xrpl/ledger/ReadView.h>
#include <xrpl/ledger/helpers/AccountRootHelpers.h> #include <xrpl/ledger/helpers/AccountRootHelpers.h>
#include <xrpl/ledger/helpers/MPTokenHelpers.h> #include <xrpl/ledger/helpers/MPTokenHelpers.h>
#include <xrpl/ledger/helpers/RippleStateHelpers.h> #include <xrpl/ledger/helpers/RippleStateHelpers.h>
@@ -27,6 +29,291 @@
namespace xrpl { namespace xrpl {
/**
* Validate that @p account may lock @p amount of a token for later delivery
* to @p dest.
*
* The lock-side counterpart of escrowUnlockPreclaimHelper: every issuer
* control (locking opt-in, authorization, freeze/lock, transferability,
* spendable balance) that gates locking token value lives here, so any
* transactor that locks funds applies the same rules. The signature is
* view-based rather than PreclaimContext-based so it can also run from
* doApply.
*/
template <ValidIssueType T>
TER
escrowLockPreclaimHelper(
ReadView const& view,
AccountID const& account,
AccountID const& dest,
STAmount const& amount,
beast::Journal j);
template <>
inline TER
escrowLockPreclaimHelper<Issue>(
ReadView const& view,
AccountID const& account,
AccountID const& dest,
STAmount const& amount,
beast::Journal j)
{
auto const& issue = amount.get<Issue>();
auto const& issuer = amount.getIssuer();
// If the issuer is the same as the account, return tecNO_PERMISSION
if (issuer == account)
return tecNO_PERMISSION;
// If the lsfAllowTrustLineLocking is not enabled, return tecNO_PERMISSION
auto const sleIssuer = view.read(keylet::account(issuer));
if (!sleIssuer)
return tecNO_ISSUER;
if (!sleIssuer->isFlag(lsfAllowTrustLineLocking))
return tecNO_PERMISSION;
// If the account does not have a trustline to the issuer, return tecNO_LINE
auto const sleRippleState = view.read(keylet::trustLine(account, issuer, issue.currency));
if (!sleRippleState)
return tecNO_LINE;
STAmount const balance = (*sleRippleState)[sfBalance];
// If balance is positive, issuer must have higher address than account
if (balance > beast::kZero && issuer < account)
return tecNO_PERMISSION; // LCOV_EXCL_LINE
// If balance is negative, issuer must have lower address than account
if (balance < beast::kZero && issuer > account)
return tecNO_PERMISSION; // LCOV_EXCL_LINE
// If the issuer has requireAuth set, check if the account is authorized
if (auto const ter = requireAuth(view, issue, account); !isTesSuccess(ter))
return ter;
// If the issuer has requireAuth set, check if the destination is authorized
if (auto const ter = requireAuth(view, issue, dest); !isTesSuccess(ter))
return ter;
// If the issuer has frozen the account, return tecFROZEN
if (isFrozen(view, account, issue))
return tecFROZEN;
// If the issuer has frozen the destination, return tecFROZEN
if (isFrozen(view, dest, issue))
return tecFROZEN;
STAmount const spendableAmount =
accountHolds(view, account, issue.currency, issuer, FreezeHandling::IgnoreFreeze, j);
// If the balance is less than or equal to 0, return tecINSUFFICIENT_FUNDS
if (spendableAmount <= beast::kZero)
return tecINSUFFICIENT_FUNDS;
// If the spendable amount is less than the amount, return
// tecINSUFFICIENT_FUNDS
if (spendableAmount < amount)
return tecINSUFFICIENT_FUNDS;
// If the amount is not addable to the balance, return tecPRECISION_LOSS
if (!canAdd(spendableAmount, amount))
return tecPRECISION_LOSS;
return tesSUCCESS;
}
template <>
inline TER
escrowLockPreclaimHelper<MPTIssue>(
ReadView const& view,
AccountID const& account,
AccountID const& dest,
STAmount const& amount,
beast::Journal j)
{
AccountID const issuer = amount.getIssuer();
// If the issuer is the same as the account, return tecNO_PERMISSION
if (issuer == account)
return tecNO_PERMISSION;
// If the mpt does not exist, return tecOBJECT_NOT_FOUND
auto const issuanceKey = keylet::mptokenIssuance(amount.get<MPTIssue>().getMptID());
auto const sleIssuance = view.read(issuanceKey);
if (!sleIssuance)
return tecOBJECT_NOT_FOUND;
// If the lsfMPTCanEscrow is not enabled, return tecNO_PERMISSION
if (!sleIssuance->isFlag(lsfMPTCanEscrow))
return tecNO_PERMISSION;
// If the issuer is not the same as the issuer of the mpt, return
// tecNO_PERMISSION
if (sleIssuance->getAccountID(sfIssuer) != issuer)
return tecNO_PERMISSION; // LCOV_EXCL_LINE
// If the account does not have the mpt, return tecOBJECT_NOT_FOUND
if (!view.exists(keylet::mptoken(issuanceKey.key, account)))
return tecOBJECT_NOT_FOUND;
// If the issuer has requireAuth set, check if the account is
// authorized
auto const& mptIssue = amount.get<MPTIssue>();
if (auto const ter = requireAuth(view, mptIssue, account, AuthType::WeakAuth);
!isTesSuccess(ter))
return ter;
// If the issuer has requireAuth set, check if the destination is
// authorized
if (auto const ter = requireAuth(view, mptIssue, dest, AuthType::WeakAuth); !isTesSuccess(ter))
return ter;
// If the issuer has frozen the account, return tecLOCKED
if (isFrozen(view, account, *sleIssuance))
return tecLOCKED;
// If the issuer has frozen the destination, return tecLOCKED
if (isFrozen(view, dest, *sleIssuance))
return tecLOCKED;
// If the mpt cannot be transferred, return tecNO_AUTH
if (auto const ter = canTransfer(view, mptIssue, account, dest); !isTesSuccess(ter))
return ter;
STAmount const spendableAmount = accountHolds(
view,
account,
amount.get<MPTIssue>(),
FreezeHandling::IgnoreFreeze,
AuthHandling::IgnoreAuth,
j);
// If the balance is less than or equal to 0, return tecINSUFFICIENT_FUNDS
if (spendableAmount <= beast::kZero)
return tecINSUFFICIENT_FUNDS;
// If the spendable amount is less than the amount, return
// tecINSUFFICIENT_FUNDS
if (spendableAmount < amount)
return tecINSUFFICIENT_FUNDS;
return tesSUCCESS;
}
template <ValidIssueType T>
TER
escrowLockApplyHelper(
ApplyView& view,
AccountID const& issuer,
AccountID const& sender,
STAmount const& amount,
beast::Journal journal);
template <>
inline TER
escrowLockApplyHelper<Issue>(
ApplyView& view,
AccountID const& issuer,
AccountID const& sender,
STAmount const& amount,
beast::Journal journal)
{
// Defensive: Issuer cannot create an escrow
if (issuer == sender)
return tecINTERNAL; // LCOV_EXCL_LINE
auto const ter =
directSendNoFee(view, sender, issuer, amount, !amount.holds<MPTIssue>(), journal);
if (!isTesSuccess(ter))
return ter; // LCOV_EXCL_LINE
return tesSUCCESS;
}
template <>
inline TER
escrowLockApplyHelper<MPTIssue>(
ApplyView& view,
AccountID const& issuer,
AccountID const& sender,
STAmount const& amount,
beast::Journal journal)
{
// Defensive: Issuer cannot create an escrow
if (issuer == sender)
return tecINTERNAL; // LCOV_EXCL_LINE
auto const ter = lockEscrowMPT(view, sender, amount, journal);
if (!isTesSuccess(ter))
return ter; // LCOV_EXCL_LINE
return tesSUCCESS;
}
template <ValidIssueType T>
TER
escrowUnlockPreclaimHelper(
ReadView const& view,
AccountID const& account,
STAmount const& amount,
bool checkFreeze = true);
template <>
inline TER
escrowUnlockPreclaimHelper<Issue>(
ReadView const& view,
AccountID const& account,
STAmount const& amount,
bool checkFreeze)
{
AccountID const& issuer = amount.getIssuer();
// If the issuer is the same as the account, return tesSUCCESS
if (issuer == account)
return tesSUCCESS;
// If the issuer has requireAuth set, check if the destination is authorized
if (auto const ter = requireAuth(view, amount.get<Issue>(), account); !isTesSuccess(ter))
return ter;
// If the issuer has deep frozen the destination, return tecFROZEN
if (checkFreeze &&
isDeepFrozen(view, account, amount.get<Issue>().currency, amount.getIssuer()))
return tecFROZEN;
return tesSUCCESS;
}
template <>
inline TER
escrowUnlockPreclaimHelper<MPTIssue>(
ReadView const& view,
AccountID const& account,
STAmount const& amount,
bool checkFreeze)
{
AccountID const& issuer = amount.getIssuer();
// If the issuer is the same as the account, return tesSUCCESS
if (issuer == account)
return tesSUCCESS;
// If the mpt does not exist, return tecOBJECT_NOT_FOUND
auto const issuanceKey = keylet::mptokenIssuance(amount.get<MPTIssue>().getMptID());
auto const sleIssuance = view.read(issuanceKey);
if (!sleIssuance)
return tecOBJECT_NOT_FOUND;
// If the issuer has requireAuth set, check if the account is
// authorized
auto const& mptIssue = amount.get<MPTIssue>();
if (auto const ter = requireAuth(view, mptIssue, account, AuthType::WeakAuth);
!isTesSuccess(ter))
return ter;
// If the issuer has frozen the account, return tecLOCKED
if (checkFreeze && isFrozen(view, account, *sleIssuance))
return tecLOCKED;
return tesSUCCESS;
}
//------------------------------------------------------------------------------
template <ValidIssueType T> template <ValidIssueType T>
TER TER
escrowUnlockApplyHelper( escrowUnlockApplyHelper(
@@ -55,9 +342,6 @@ escrowUnlockApplyHelper<Issue>(
bool createAsset, bool createAsset,
beast::Journal journal) beast::Journal journal)
{ {
auto const& issue = amount.get<Issue>();
Keylet const trustLineKey = keylet::trustLine(receiver, issue);
bool const recvLow = issuer > receiver;
bool const senderIssuer = issuer == sender; bool const senderIssuer = issuer == sender;
bool const receiverIssuer = issuer == receiver; bool const receiverIssuer = issuer == receiver;
@@ -67,6 +351,10 @@ escrowUnlockApplyHelper<Issue>(
if (receiverIssuer) if (receiverIssuer)
return tesSUCCESS; return tesSUCCESS;
auto const& issue = amount.get<Issue>();
Keylet const trustLineKey = keylet::trustLine(receiver, issue);
bool const recvLow = issuer > receiver;
if (!ctx.view.exists(trustLineKey) && createAsset) if (!ctx.view.exists(trustLineKey) && createAsset)
{ {
// Can the account cover the trust line's reserve? // Can the account cover the trust line's reserve?
+1 -1
View File
@@ -103,7 +103,7 @@ public:
void void
asyncHandshake(HandshakeType type, Callback cbFunc) asyncHandshake(HandshakeType type, Callback cbFunc)
{ {
if ((type == SslSocket::client) || (secure_)) if ((type == SslSocket::client) || secure_)
{ {
// must be ssl // must be ssl
secure_ = true; secure_ = true;
+1 -1
View File
@@ -67,7 +67,7 @@ class EncodedBlob
public: public:
explicit EncodedBlob(std::shared_ptr<NodeObject> const& obj) explicit EncodedBlob(std::shared_ptr<NodeObject> const& obj)
: size_([&obj]() { : size_([&obj] {
XRPL_ASSERT(obj, "xrpl::node_store::EncodedBlob::EncodedBlob : non-null input"); XRPL_ASSERT(obj, "xrpl::node_store::EncodedBlob::EncodedBlob : non-null input");
if (!obj) if (!obj)
+1 -1
View File
@@ -55,7 +55,7 @@ hash_append(Hasher& h, Book const& b)
using beast::hash_append; using beast::hash_append;
hash_append(h, b.in, b.out); hash_append(h, b.in, b.out);
if (b.domain) if (b.domain)
hash_append(h, *(b.domain)); hash_append(h, *b.domain);
} }
Book Book
+4 -1
View File
@@ -208,7 +208,10 @@ enum LedgerEntryType : std::uint16_t {
\ \
LEDGER_OBJECT(Sponsorship, \ LEDGER_OBJECT(Sponsorship, \
LSF_FLAG(lsfSponsorshipRequireSignForFee, 0x00010000) \ LSF_FLAG(lsfSponsorshipRequireSignForFee, 0x00010000) \
LSF_FLAG(lsfSponsorshipRequireSignForReserve, 0x00020000)) LSF_FLAG(lsfSponsorshipRequireSignForReserve, 0x00020000)) \
\
LEDGER_OBJECT(LoanBroker, \
LSF_FLAG(lsfLoanBrokerPrivate, 0x00010000))
// clang-format on // clang-format on
+2
View File
@@ -40,6 +40,8 @@ struct LedgerHeader
// If validated is false, it means "not yet validated." // If validated is false, it means "not yet validated."
// Once validated is true, it will never be set false at a later time. // Once validated is true, it will never be set false at a later time.
// NOTE: If you are accessing this directly, you are probably doing it
// wrong. Use LedgerMaster::isValidated().
// VFALCO TODO Make this not mutable // VFALCO TODO Make this not mutable
bool mutable validated = false; bool mutable validated = false;
bool accepted = false; bool accepted = false;
-28
View File
@@ -1,28 +0,0 @@
#pragma once
namespace xrpl {
/**
* @brief Enumeration of ledger shortcuts for specifying which ledger to use.
*
* These shortcuts provide a convenient way to reference commonly used ledgers
* without needing to specify their exact hash or sequence number.
*/
enum class LedgerShortcut {
/**
* The current working ledger (open, not yet closed)
*/
Current,
/**
* The most recently closed ledger (may not be validated)
*/
Closed,
/**
* The most recently validated ledger
*/
Validated
};
} // namespace xrpl
+1 -3
View File
@@ -457,9 +457,7 @@ private:
// The remove_cv and remove_reference are necessitated by the STBitString // The remove_cv and remove_reference are necessitated by the STBitString
// types. Their value() returns by const ref. We return those types // types. Their value() returns by const ref. We return those types
// by value. // by value.
template < template <typename T, typename V = std::remove_cvref_t<decltype(std::declval<T>().value())>>
typename T,
typename V = std::remove_cv_t<std::remove_reference_t<decltype(std::declval<T>().value())>>>
V V
getFieldByValue(SField const& field) const; getFieldByValue(SField const& field) const;
+1 -1
View File
@@ -188,7 +188,7 @@ private:
template <class LookupNodeID> template <class LookupNodeID>
STValidation::STValidation(SerialIter& sit, LookupNodeID&& lookupNodeID, DeserializeOptions options) STValidation::STValidation(SerialIter& sit, LookupNodeID&& lookupNodeID, DeserializeOptions options)
: STObject(validationFormat(), sit, sfValidation, options.requireCanonicalOrder) : STObject(validationFormat(), sit, sfValidation, options.requireCanonicalOrder)
, signingPubKey_([this]() { , signingPubKey_([this] {
auto const spk = getFieldVL(sfSigningPubKey); auto const spk = getFieldVL(sfSigningPubKey);
if (publicKeyType(makeSlice(spk)) != KeyType::Secp256k1) if (publicKeyType(makeSlice(spk)) != KeyType::Secp256k1)
+1 -1
View File
@@ -252,7 +252,7 @@ public:
{ {
auto success = (offset + (Bits / 8)) <= data_.size(); auto success = (offset + (Bits / 8)) <= data_.size();
if (success) if (success)
memcpy(data.begin(), &(data_.front()) + offset, (Bits / 8)); memcpy(data.begin(), &data_.front() + offset, (Bits / 8));
return success; return success;
} }
+1 -1
View File
@@ -449,7 +449,7 @@ public:
// Trait tells the requires-clause which types are allowed for construction. // Trait tells the requires-clause which types are allowed for construction.
template <typename T> template <typename T>
constexpr TERSubset(T rhs) constexpr TERSubset(T rhs)
requires(Trait<std::remove_cv_t<std::remove_reference_t<T>>>::value) requires(Trait<std::remove_cvref_t<T>>::value)
: code_(TERtoInt(rhs)) : code_(TERtoInt(rhs))
{ {
} }
+4
View File
@@ -226,6 +226,10 @@ inline constexpr FlagValue tfUniversalMask = ~tfUniversal;
TF_FLAG(tfLoanUnimpair, 0x00040000), \ TF_FLAG(tfLoanUnimpair, 0x00040000), \
MASK_ADJ(0)) \ MASK_ADJ(0)) \
\ \
TRANSACTION(LoanBrokerSet, \
TF_FLAG(tfLoanBrokerPrivate, 0x00010000), \
MASK_ADJ(0)) \
\
TRANSACTION(SponsorshipSet, \ TRANSACTION(SponsorshipSet, \
TF_FLAG(tfSponsorshipSetRequireSignForFee, 0x00010000) \ TF_FLAG(tfSponsorshipSetRequireSignForFee, 0x00010000) \
TF_FLAG(tfSponsorshipClearRequireSignForFee, 0x00020000) \ TF_FLAG(tfSponsorshipClearRequireSignForFee, 0x00020000) \
@@ -20,6 +20,7 @@ XRPL_FEATURE(SmartEscrow, Supported::No, VoteBehavior::DefaultN
XRPL_FEATURE(LendingProtocolV1_2, Supported::No, VoteBehavior::DefaultNo) XRPL_FEATURE(LendingProtocolV1_2, Supported::No, VoteBehavior::DefaultNo)
XRPL_FIX (Cleanup3_5_0, Supported::Yes, VoteBehavior::DefaultNo) XRPL_FIX (Cleanup3_5_0, Supported::Yes, VoteBehavior::DefaultNo)
XRPL_FEATURE(ConfidentialMPTKeyRotation, Supported::No, VoteBehavior::DefaultNo) XRPL_FEATURE(ConfidentialMPTKeyRotation, Supported::No, VoteBehavior::DefaultNo)
XRPL_FIX (BatchV1_2, Supported::Yes, VoteBehavior::DefaultYes)
XRPL_FIX (Cleanup3_4_0, Supported::Yes, VoteBehavior::DefaultNo) XRPL_FIX (Cleanup3_4_0, Supported::Yes, VoteBehavior::DefaultNo)
XRPL_FEATURE(Sponsor, Supported::Yes, VoteBehavior::DefaultNo) XRPL_FEATURE(Sponsor, Supported::Yes, VoteBehavior::DefaultNo)
XRPL_FEATURE(BatchV1_1, Supported::Yes, VoteBehavior::DefaultNo) XRPL_FEATURE(BatchV1_1, Supported::Yes, VoteBehavior::DefaultNo)
@@ -549,6 +549,7 @@ LEDGER_ENTRY(ltLOAN_BROKER, 0x0088, LoanBroker, loan_broker, ({
{sfCoverAvailable, SoeDefault}, {sfCoverAvailable, SoeDefault},
{sfCoverRateMinimum, SoeDefault}, {sfCoverRateMinimum, SoeDefault},
{sfCoverRateLiquidation, SoeDefault}, {sfCoverRateLiquidation, SoeDefault},
{sfDomainID, SoeOptional},
})) }))
/** A ledger object representing a loan between a Borrower and a Loan Broker /** A ledger object representing a loan between a Borrower and a Loan Broker
@@ -900,6 +900,7 @@ TRANSACTION(ttLOAN_BROKER_SET, 74, LoanBrokerSet,
{sfDebtMaximum, SoeOptional}, {sfDebtMaximum, SoeOptional},
{sfCoverRateMinimum, SoeOptional}, {sfCoverRateMinimum, SoeOptional},
{sfCoverRateLiquidation, SoeOptional}, {sfCoverRateLiquidation, SoeOptional},
{sfDomainID, SoeOptional},
})) }))
/** This transaction deletes a Loan Broker */ /** This transaction deletes a Loan Broker */
@@ -335,6 +335,30 @@ public:
{ {
return this->sle_->isFieldPresent(sfCoverRateLiquidation); return this->sle_->isFieldPresent(sfCoverRateLiquidation);
} }
/**
* @brief Get sfDomainID (SoeOptional)
* @return The field value, or std::nullopt if not present.
*/
[[nodiscard]]
protocol_autogen::Optional<SF_UINT256::type::value_type>
getDomainID() const
{
if (hasDomainID())
return this->sle_->at(sfDomainID);
return std::nullopt;
}
/**
* @brief Check if sfDomainID is present.
* @return True if the field is present, false otherwise.
*/
[[nodiscard]]
bool
hasDomainID() const
{
return this->sle_->isFieldPresent(sfDomainID);
}
}; };
/** /**
@@ -578,6 +602,17 @@ public:
return *this; return *this;
} }
/**
* @brief Set sfDomainID (SoeOptional)
* @return Reference to this builder for method chaining.
*/
LoanBrokerBuilder&
setDomainID(std::decay_t<typename SF_UINT256::type::value_type> const& value)
{
object_[sfDomainID] = value;
return *this;
}
/** /**
* @brief Build and return the completed LoanBroker wrapper. * @brief Build and return the completed LoanBroker wrapper.
* @param index The ledger entry index. * @param index The ledger entry index.
@@ -213,6 +213,32 @@ public:
{ {
return this->tx_->isFieldPresent(sfCoverRateLiquidation); return this->tx_->isFieldPresent(sfCoverRateLiquidation);
} }
/**
* @brief Get sfDomainID (SoeOptional)
* @return The field value, or std::nullopt if not present.
*/
[[nodiscard]]
protocol_autogen::Optional<SF_UINT256::type::value_type>
getDomainID() const
{
if (hasDomainID())
{
return this->tx_->at(sfDomainID);
}
return std::nullopt;
}
/**
* @brief Check if sfDomainID is present.
* @return True if the field is present, false otherwise.
*/
[[nodiscard]]
bool
hasDomainID() const
{
return this->tx_->isFieldPresent(sfDomainID);
}
}; };
/** /**
@@ -336,6 +362,17 @@ public:
return *this; return *this;
} }
/**
* @brief Set sfDomainID (SoeOptional)
* @return Reference to this builder for method chaining.
*/
LoanBrokerSetBuilder&
setDomainID(std::decay_t<typename SF_UINT256::type::value_type> const& value)
{
object_[sfDomainID] = value;
return *this;
}
/** /**
* @brief Build and return the LoanBrokerSet wrapper. * @brief Build and return the LoanBrokerSet wrapper.
* @param publicKey The public key for signing. * @param publicKey The public key for signing.
+1 -1
View File
@@ -178,7 +178,7 @@ public:
{ {
using namespace std::chrono_literals; using namespace std::chrono_literals;
LockedSociSession session = perf::measureDurationAndLog( LockedSociSession session = perf::measureDurationAndLog(
[&]() { return LockedSociSession(session_, lock_); }, "checkoutDb", 10ms, j_); [&] { return LockedSociSession(session_, lock_); }, "checkoutDb", 10ms, j_);
return session; return session;
} }
-16
View File
@@ -9,7 +9,6 @@
#include <xrpl/protocol/AccountID.h> #include <xrpl/protocol/AccountID.h>
#include <xrpl/protocol/ErrorCodes.h> #include <xrpl/protocol/ErrorCodes.h>
#include <xrpl/protocol/LedgerHeader.h> #include <xrpl/protocol/LedgerHeader.h>
#include <xrpl/protocol/LedgerShortcut.h>
#include <xrpl/protocol/Protocol.h> #include <xrpl/protocol/Protocol.h>
#include <xrpl/protocol/TxMeta.h> #include <xrpl/protocol/TxMeta.h>
#include <xrpl/protocol/TxSearched.h> #include <xrpl/protocol/TxSearched.h>
@@ -105,21 +104,6 @@ public:
using TxnMetaLedgerType = std::tuple<Blob, Blob, std::uint32_t>; using TxnMetaLedgerType = std::tuple<Blob, Blob, std::uint32_t>;
using MetaTxsList = std::vector<TxnMetaLedgerType>; using MetaTxsList = std::vector<TxnMetaLedgerType>;
using LedgerSequence = uint32_t;
using LedgerHash = UInt256;
using LedgerSpecifier = std::variant<LedgerRange, LedgerShortcut, LedgerSequence, LedgerHash>;
struct AccountTxArgs
{
AccountID account;
std::optional<LedgerSpecifier> ledger;
bool binary = false;
bool forward = false;
uint32_t limit = 0;
std::optional<AccountTxMarker> marker;
std::optional<DelegateFilter> delegate;
};
struct AccountTxResult struct AccountTxResult
{ {
std::variant<AccountTxs, MetaTxsList> transactions; std::variant<AccountTxs, MetaTxsList> transactions;
+1 -1
View File
@@ -279,7 +279,7 @@ public:
virtual bool virtual bool
unsubPeerStatus(std::uint64_t uListener) = 0; unsubPeerStatus(std::uint64_t uListener) = 0;
virtual void virtual void
pubPeerStatus(std::function<json::Value(void)> const&) = 0; pubPeerStatus(std::function<json::Value()> const&) = 0;
virtual bool virtual bool
subConsensus(Ref ispListener) = 0; subConsensus(Ref ispListener) = 0;
+1 -1
View File
@@ -196,7 +196,7 @@ public:
virtual bool virtual bool
isFull() = 0; isFull() = 0;
virtual void virtual void
setMode(OperatingMode om) = 0; setMode(OperatingMode om, char const* reason) = 0;
virtual bool virtual bool
isBlocked() = 0; isBlocked() = 0;
virtual bool virtual bool
+1 -1
View File
@@ -41,7 +41,7 @@ public:
} }
bool bool
prepare(std::size_t bytes, std::function<void(void)>) override prepare(std::size_t bytes, std::function<void()>) override
{ {
return true; return true;
} }
+2 -2
View File
@@ -47,7 +47,7 @@ public:
* empty vector. * empty vector.
*/ */
virtual std::pair<boost::tribool, std::vector<boost::asio::const_buffer>> virtual std::pair<boost::tribool, std::vector<boost::asio::const_buffer>>
prepare(std::size_t bytes, std::function<void(void)> resume) = 0; prepare(std::size_t bytes, std::function<void()> resume) = 0;
}; };
template <class Streambuf> template <class Streambuf>
@@ -62,7 +62,7 @@ public:
} }
std::pair<boost::tribool, std::vector<boost::asio::const_buffer>> std::pair<boost::tribool, std::vector<boost::asio::const_buffer>>
prepare(std::size_t bytes, std::function<void(void)>) override prepare(std::size_t bytes, std::function<void()>) override
{ {
if (sb_.size() == 0) if (sb_.size() == 0)
return {true, {}}; return {true, {}};
+1 -1
View File
@@ -34,7 +34,7 @@ public:
* @return `true` if the writer is ready to provide more data. * @return `true` if the writer is ready to provide more data.
*/ */
virtual bool virtual bool
prepare(std::size_t bytes, std::function<void(void)> resume) = 0; prepare(std::size_t bytes, std::function<void()> resume) = 0;
/** /**
* Returns a ConstBufferSequence representing the input sequence. * Returns a ConstBufferSequence representing the input sequence.
+2 -2
View File
@@ -342,10 +342,10 @@ BaseHTTPPeer<Handler, Impl>::doWriter(
bool keepAlive, bool keepAlive,
YieldContext doYield) YieldContext doYield)
{ {
std::function<void(void)> resume; std::function<void()> resume;
{ {
auto const p = impl().shared_from_this(); auto const p = impl().shared_from_this();
resume = std::function<void(void)>([this, p, writer, keepAlive]() { resume = std::function<void()>([this, p, writer, keepAlive] {
util::spawn(strand_, [p, writer, keepAlive](YieldContext doYield) { util::spawn(strand_, [p, writer, keepAlive](YieldContext doYield) {
p->doWriter(writer, keepAlive, doYield); p->doWriter(writer, keepAlive, doYield);
}); });
+1 -1
View File
@@ -99,7 +99,7 @@ private:
port_.protocol.contains("wss2") || port_.protocol.contains("peer")}; port_.protocol.contains("wss2") || port_.protocol.contains("peer")};
bool plain_{ bool plain_{
port_.protocol.contains("http") || port_.protocol.contains("ws") || port_.protocol.contains("http") || port_.protocol.contains("ws") ||
(port_.protocol.contains("ws2"))}; port_.protocol.contains("ws2")};
static constexpr std::chrono::milliseconds kInitialAcceptDelay{50}; static constexpr std::chrono::milliseconds kInitialAcceptDelay{50};
static constexpr std::chrono::milliseconds kMaxAcceptDelay{2000}; static constexpr std::chrono::milliseconds kMaxAcceptDelay{2000};
std::chrono::milliseconds acceptDelay_{kInitialAcceptDelay}; std::chrono::milliseconds acceptDelay_{kInitialAcceptDelay};
+2 -2
View File
@@ -60,7 +60,7 @@ private:
bool closed_ = false; bool closed_ = false;
std::condition_variable cv_; std::condition_variable cv_;
boost::container::flat_map<Work*, std::weak_ptr<Work>> map_; boost::container::flat_map<Work*, std::weak_ptr<Work>> map_;
std::function<void(void)> f_; std::function<void()> f_;
public: public:
IOList() = default; IOList() = default;
@@ -171,7 +171,7 @@ IOList::Work::destroy()
{ {
if (!ios_) if (!ios_)
return; return;
std::function<void(void)> f; std::function<void()> f;
{ {
std::scoped_lock const lock(ios_->m_); std::scoped_lock const lock(ios_->m_);
ios_->map_.erase(this); ios_->map_.erase(this);
+3 -1
View File
@@ -18,6 +18,8 @@
#include <xrpl/tx/invariants/SponsorshipInvariant.h> #include <xrpl/tx/invariants/SponsorshipInvariant.h>
#include <xrpl/tx/invariants/VaultInvariant.h> #include <xrpl/tx/invariants/VaultInvariant.h>
#include <boost/multiprecision/cpp_int.hpp>
#include <cstdint> #include <cstdint>
#include <set> #include <set>
#include <string> #include <string>
@@ -139,7 +141,7 @@ public:
*/ */
class XRPNotCreated class XRPNotCreated
{ {
std::int64_t drops_ = 0; boost::multiprecision::int128_t drops_ = 0;
public: public:
void void
@@ -42,6 +42,14 @@ class ValidMPTIssuance
*/ */
bool referenceHoldingMutated_ = false; bool referenceHoldingMutated_ = false;
/**
* Flags cleared on an existing MPTokenIssuance, except lsfMPTLocked,
* which tfMPTUnlock clears legitimately. Every other issuance flag is
* fixed at creation or set-once via MPTokenIssuanceSet, so any bit
* accumulated here is a bug. Enforced post-fixCleanup3_5_0.
*/
std::uint32_t issuanceFlagsCleared_ = 0;
/** /**
* MPTokens and RippleStates deleted during apply. finalize() checks each * MPTokens and RippleStates deleted during apply. finalize() checks each
* holder's AccountRoot to detect vault pseudo-account holdings deleted * holder's AccountRoot to detect vault pseudo-account holdings deleted
+43
View File
@@ -1,6 +1,8 @@
#pragma once #pragma once
#include <xrpl/basics/MathUtilities.h>
#include <xrpl/basics/base_uint.h> #include <xrpl/basics/base_uint.h>
#include <xrpl/basics/contract.h>
#include <xrpl/beast/utility/Journal.h> #include <xrpl/beast/utility/Journal.h>
#include <xrpl/beast/utility/Zero.h> #include <xrpl/beast/utility/Zero.h>
#include <xrpl/protocol/AccountID.h> #include <xrpl/protocol/AccountID.h>
@@ -23,6 +25,7 @@
#include <ostream> #include <ostream>
#include <stdexcept> #include <stdexcept>
#include <string> #include <string>
#include <type_traits>
#include <utility> #include <utility>
#include <vector> #include <vector>
@@ -502,6 +505,46 @@ public:
}; };
/** @endcond */ /** @endcond */
/** @cond INTERNAL */
template <class T>
[[nodiscard]] std::optional<T>
checkedStepAddOpt(T const& lhs, T const& rhs)
{
if constexpr (std::is_same_v<T, XRPAmount>)
{
if (auto const r = checkedAdd(lhs.drops(), rhs.drops()))
return XRPAmount{*r};
return std::nullopt;
}
else if constexpr (std::is_same_v<T, MPTAmount>)
{
if (auto const r = checkedAdd(lhs.value(), rhs.value()))
return MPTAmount{*r};
return std::nullopt;
}
else if constexpr (std::is_same_v<T, IOUAmount>)
{
// IOUAmount is Number-backed and throws on overflow.
return lhs + rhs;
}
else
{
// A new amount type must decide explicitly how to add; do not fall back
// to an unchecked add.
static_assert(sizeof(T) == 0, "checkedStepAddOpt: unsupported amount type");
}
}
template <class T>
[[nodiscard]] T
checkedStepAdd(T const& lhs, T const& rhs)
{
if (auto const r = checkedStepAddOpt(lhs, rhs))
return *r;
Throw<FlowException>(tecPATH_DRY);
}
/** @endcond */
/** @cond INTERNAL */ /** @cond INTERNAL */
// Check equal with tolerance // Check equal with tolerance
bool bool
+30 -9
View File
@@ -31,7 +31,6 @@
#include <cstdint> #include <cstdint>
#include <iterator> #include <iterator>
#include <memory> #include <memory>
#include <numeric>
#include <optional> #include <optional>
#include <tuple> #include <tuple>
#include <type_traits> #include <type_traits>
@@ -408,7 +407,7 @@ limitOut(
if (!qf || qf->isConst()) if (!qf || qf->isConst())
return remainingOut; return remainingOut;
auto const out = [&]() { auto const out = [&] {
auto const out = qf->outFromAvgQ(limitQuality); auto const out = qf->outFromAvgQ(limitQuality);
if (!out) if (!out)
return remainingOut; return remainingOut;
@@ -646,11 +645,21 @@ flow(
boost::container::flat_multiset<TOutAmt> savedOuts; boost::container::flat_multiset<TOutAmt> savedOuts;
savedOuts.reserve(maxTries); savedOuts.reserve(maxTries);
auto sum = [](auto const& col) { // Returns std::nullopt if the aggregate overflows; callers treat that as a
// dry path.
auto sum = [](auto const& col) -> std::optional<std::decay_t<decltype(*col.begin())>> {
using TResult = std::decay_t<decltype(*col.begin())>; using TResult = std::decay_t<decltype(*col.begin())>;
if (col.empty()) if (col.empty())
return TResult{beast::kZero}; return TResult{beast::kZero};
return std::accumulate(col.begin() + 1, col.end(), *col.begin()); TResult total = *col.begin();
for (auto it = col.begin() + 1; it != col.end(); ++it)
{
auto const next = checkedStepAddOpt(total, *it);
if (!next)
return std::nullopt;
total = *next;
}
return total;
}; };
// These offers only need to be removed if the payment is not // These offers only need to be removed if the payment is not
@@ -670,7 +679,7 @@ flow(
ammContext.setMultiPath(activeStrands.size() > 1); ammContext.setMultiPath(activeStrands.size() > 1);
// Limit only if one strand and limitQuality // Limit only if one strand and limitQuality
auto const limitRemainingOut = [&]() { auto const limitRemainingOut = [&] {
if (activeStrands.size() == 1 && limitQuality) if (activeStrands.size() == 1 && limitQuality)
{ {
if (auto const strand = activeStrands.get(0)) if (auto const strand = activeStrands.get(0))
@@ -749,9 +758,17 @@ flow(
{ {
savedIns.insert(best->in); savedIns.insert(best->in);
savedOuts.insert(best->out); savedOuts.insert(best->out);
remainingOut = outReq - sum(savedOuts); auto const sumOut = sum(savedOuts);
if (!sumOut)
return {tecPATH_DRY, std::move(ofrsToRmOnFail)};
remainingOut = outReq - *sumOut;
if (sendMax) if (sendMax)
remainingIn = *sendMax - sum(savedIns); {
auto const sumIn = sum(savedIns);
if (!sumIn)
return {tecPATH_DRY, std::move(ofrsToRmOnFail)};
remainingIn = *sendMax - *sumIn;
}
if (flowDebugInfo) if (flowDebugInfo)
{ {
@@ -786,8 +803,12 @@ flow(
break; break;
} }
auto const actualOut = sum(savedOuts); auto const actualOutOpt = sum(savedOuts);
auto const actualIn = sum(savedIns); auto const actualInOpt = sum(savedIns);
if (!actualOutOpt || !actualInOpt)
return {tecPATH_DRY, std::move(ofrsToRmOnFail)};
auto const actualOut = *actualOutOpt;
auto const actualIn = *actualInOpt;
JLOG(j.trace()) << "Total flow: in: " << to_string(actualIn) JLOG(j.trace()) << "Total flow: in: " << to_string(actualIn)
<< " out: " << to_string(actualOut); << " out: " << to_string(actualOut);
@@ -10,6 +10,7 @@
#include <xrpl/tx/ApplyContext.h> #include <xrpl/tx/ApplyContext.h>
#include <xrpl/tx/Transactor.h> #include <xrpl/tx/Transactor.h>
#include <cstdint>
#include <vector> #include <vector>
namespace xrpl { namespace xrpl {
@@ -32,6 +33,9 @@ public:
static std::vector<OptionaledField<STNumber>> const& static std::vector<OptionaledField<STNumber>> const&
getValueFields(); getValueFields();
static std::uint32_t
getFlagsMask(PreflightContext const& ctx);
static TER static TER
preclaim(PreclaimContext const& ctx); preclaim(PreclaimContext const& ctx);
@@ -57,6 +57,12 @@ public:
ReadView const& view, ReadView const& view,
beast::Journal const& j) override; beast::Journal const& j) override;
/**
* Inner transaction types that preflight rejects before LendingProtocolV1_2.
*
* Once the amendment is enabled the list only matters when replaying older
* ledgers. Remove it when LendingProtocolV1_2 is retired.
*/
static constexpr auto kDisabledTxTypes = std::to_array<TxType>({ static constexpr auto kDisabledTxTypes = std::to_array<TxType>({
ttVAULT_CREATE, ttVAULT_CREATE,
ttVAULT_SET, ttVAULT_SET,
+83 -80
View File
@@ -2,145 +2,148 @@ Detected OS: macos (Darwin arm64)
Core build tools: Core build tools:
✅ cmake ✅ cmake
cmake version 4.1.2 cmake version 4.4.3
/nix/store/gvabsb4yqb5xsqzqph54rijnn4zpihnp-cmake-4.1.2/bin/cmake /nix/store/q85csxf4s4shx89zif097h1ql4ax1rrz-cmake-4.4.3/bin/cmake
✅ conan ✅ conan
Conan version 2.28.1 Conan version 2.33.0
/nix/store/9jiyxmkpwmn6dcqs0765s83riw3l5ail-conan-2.28.1/bin/conan /nix/store/rp0zf22rx3iwnhxp4d53ncirn4lzg68j-conan-2.33.0/bin/conan
✅ git ✅ git
git version 2.54.0 git version 2.55.0
/nix/store/a14yxcqvv9x2l9mllgpirzhvz93pgprg-git-2.54.0/bin/git /nix/store/gw7c7m0dwca5lg4152x9lpmxpj171bzw-git-2.55.0/bin/git
✅ python3 ✅ python3
Python 3.13.13 Python 3.14.7
/nix/store/ygxqin6ydzjfawywqpp5pal8wv6sf5bh-python3-3.13.13/bin/python3.13 /nix/store/0kcws5blwbdyxqxjd1w8hjipz61xny3k-python3-3.14.7/bin/python3.14
Development tooling: Development tooling:
✅ ccache ✅ ccache
ccache version 4.13.6 ccache version 4.13.6
/nix/store/57davyvs6p6dkrl3svzwg1ph18wsy4cz-ccache-4.13.6/bin/ccache /nix/store/ydr5nlzxp1djb5256y0zzqa87vz55gsk-ccache-4.13.6/bin/ccache
✅ clang ✅ clang
clang version 22.1.7 clang version 23.1.0
/nix/store/192glrb2cldvziyf3378mzjqbzx3ih4g-clang-wrapper-22.1.7/bin/clang /nix/store/2c16z6akvv65znb8330sl5qpklaf3194-clang-wrapper-23.1.0/bin/clang
✅ clang-22 ✅ clang-23
clang version 22.1.7 clang version 23.1.0
/nix/store/rbap7zqq7mw00fyqa02p5rj7gqjp4w5i-clang-22/bin/clang-22 /nix/store/vfd0q2395vyn0bsjsh1b4068icy1x9ph-clang-23/bin/clang-23
✅ clang++ ✅ clang++
clang version 22.1.7 clang version 23.1.0
/nix/store/192glrb2cldvziyf3378mzjqbzx3ih4g-clang-wrapper-22.1.7/bin/clang++ /nix/store/2c16z6akvv65znb8330sl5qpklaf3194-clang-wrapper-23.1.0/bin/clang++
✅ clang++-22 ✅ clang++-23
clang version 22.1.7 clang version 23.1.0
/nix/store/v9haf787f7bcz0mq1sad4bpyx21pj6li-clang++-22/bin/clang++-22 /nix/store/0i6kfnif2v4sqyv5fzfg8a9n09rw9lkp-clang++-23/bin/clang++-23
✅ ClangBuildAnalyzer ✅ ClangBuildAnalyzer
ClangBuildAnalyzer 1.6.0 ClangBuildAnalyzer 1.6.0
/nix/store/4l50ds9fa2mkvh7wg8qzrlbmjs12sb8l-clangbuildanalyzer-1.6.0/bin/ClangBuildAnalyzer /nix/store/c7jjnw29ra78jdlzjww2m374izhy05n8-clangbuildanalyzer-1.6.0/bin/ClangBuildAnalyzer
✅ curl ✅ curl
curl 8.20.0 (aarch64-apple-darwin25.3.0) libcurl/8.20.0 OpenSSL/3.6.2 zlib/1.3.2 libssh2/1.11.1 nghttp2/1.69.0 mit-krb5/1.22.1 curl 8.22.0 (aarch64-apple-darwin25.6.0) libcurl/8.22.0 OpenSSL/3.5.8 zlib/1.3.2 libssh2/1.11.1 nghttp2/1.70.0 mit-krb5/1.22.2
/nix/store/kclq0czaxvsgh4ym9ld7b6iwy50l1snk-curl-8.20.0-bin/bin/curl /nix/store/pq1h17abqy6q5y6k5dn9qj0fwb89flba-curl-8.22.0-bin/bin/curl
✅ file ✅ file
file-5.47 file-5.48
/nix/store/dax63li7wwcbqxxkkgzc4g2rx7d4w86x-file-5.47/bin/file /nix/store/y44vpziwbzfm8020dzlqqbybyyy7lb6g-file-5.48/bin/file
✅ jq
jq-1.8.2
/nix/store/wm7v59a2lhj1w2k8jz53spcs1iizm9lv-jq-1.8.2-bin/bin/jq
✅ less ✅ less
less 692 (PCRE2 regular expressions) less 710 (PCRE2 regular expressions)
/nix/store/lvr16y75r1pdxpdv0aph5ak2yd0hkvqm-less-692/bin/less /nix/store/3yn3dx5fwg5i0inqqzwnxq7f6lwhpjqa-less-710/bin/less
✅ make ✅ make
GNU Make 4.4.1 GNU Make 4.4.1
/nix/store/8wwiw8pwyhrkzyq28hqzxfl4z84lks81-gnumake-4.4.1/bin/make /nix/store/8l4wgxmhdxfvc9g18y76bnxl1ghgcp7n-gnumake-4.4.1/bin/make
✅ netstat ✅ netstat
present present
/nix/store/qsd1kzqb0ahrk433vmyl245gp623j19s-network_cmds-730.80.3/bin/netstat /nix/store/57fqvgdav8lrmzndkwm7qrgksl01yj23-network_cmds-741.100.2/bin/netstat
✅ ninja ✅ ninja
1.13.2 1.13.2
/nix/store/bqykhrblarkj4fl0hz2mf8ngwfv6x6bz-ninja-1.13.2/bin/ninja /nix/store/infm4vlx71q83bqz0k559w1gn4b0rq4i-ninja-1.13.2/bin/ninja
✅ perl ✅ perl
v5.42.0 v5.42.3
/nix/store/js13ri9fvm0ajk1fpd3acigys2a9whdv-perl-5.42.0/bin/perl /nix/store/7rvr6qjfzk2ybzn1imjw6c6qq1n1a9cr-perl-5.42.3/bin/perl
✅ pkg-config ✅ pkg-config
0.29.2 0.29.2
/nix/store/lzrwr375jqhhbca116kja96xf1md83l8-pkg-config-wrapper-0.29.2/bin/pkg-config /nix/store/nhgylvj98klqggy54h7gbc3b2ia4a00y-pkg-config-wrapper-0.29.2/bin/pkg-config
✅ vim ✅ vim
VIM - Vi IMproved 9.2 (2026 Feb 14, compiled Jan 01 1980 00:00:00) VIM - Vi IMproved 9.2 (2026 Feb 14, compiled Jan 01 1980 00:00:00)
/nix/store/6vbkykg92w603c0sw3mkk7p7mfaawbns-vim-9.2.0389/bin/vim /nix/store/akaa9kqm3b8rlkv61kvsqr2l2j70rvxb-vim-9.2.1001/bin/vim
✅ zip ✅ zip
Zip 3.0 Zip 3.0
/nix/store/z6ph729vcakbvz3wh8ln1wk6mi06w487-zip-3.0/bin/zip /nix/store/dvawr36npnad4xa6dxi2ss0fw44aa82r-zip-3.0/bin/zip
✅ clang-apply-replacements ✅ clang-apply-replacements
clang-apply-replacements version 22.1.7 clang-apply-replacements version 23.1.0
/nix/store/vzyyjf3cm1hbj9wcr2qcb66x6j98zpy7-clang-tools-22.1.7/bin/clang-apply-replacements /nix/store/mva6ngy45m9in3m2lsfccj1y0z6n1f5s-clang-tools-23.1.0/bin/clang-apply-replacements
✅ clang-apply-replacements-22 ✅ clang-apply-replacements-23
clang-apply-replacements version 22.1.7 clang-apply-replacements version 23.1.0
/nix/store/m3ii69rca4077lf4wlk7m3jcag1fs577-clang-apply-replacements-22/bin/clang-apply-replacements-22 /nix/store/872k02mqr21hxwcpfwaqkxljfj60aak0-clang-apply-replacements-23/bin/clang-apply-replacements-23
✅ clang-format ✅ clang-format
clang-format version 22.1.7 clang-format version 23.1.0
/nix/store/vzyyjf3cm1hbj9wcr2qcb66x6j98zpy7-clang-tools-22.1.7/bin/clang-format /nix/store/mva6ngy45m9in3m2lsfccj1y0z6n1f5s-clang-tools-23.1.0/bin/clang-format
✅ clang-format-22 ✅ clang-format-23
clang-format version 22.1.7 clang-format version 23.1.0
/nix/store/4fawqy6ngqcsqd2ygyyzm93q0xy3f5gs-clang-format-22/bin/clang-format-22 /nix/store/wf30x6lcya44n2y1fagd6q7x7p4gyl6f-clang-format-23/bin/clang-format-23
✅ clang-tidy ✅ clang-tidy
LLVM version 22.1.7 LLVM version 23.1.0
/nix/store/vzyyjf3cm1hbj9wcr2qcb66x6j98zpy7-clang-tools-22.1.7/bin/clang-tidy /nix/store/mva6ngy45m9in3m2lsfccj1y0z6n1f5s-clang-tools-23.1.0/bin/clang-tidy
✅ clang-tidy-22 ✅ clang-tidy-23
LLVM version 22.1.7 LLVM version 23.1.0
/nix/store/jqw4280saixaxxihwdba9ldm2fsm6dr3-clang-tidy-22/bin/clang-tidy-22 /nix/store/kgx00aass66g02p1s4gqqf65kq39m4ci-clang-tidy-23/bin/clang-tidy-23
✅ dot ✅ dot
dot - graphviz version 12.2.1 (0) dot - graphviz version 15.1.1 (0)
/nix/store/ijb4fbnqa6wzlpqnhb6q9knqpf7qqn5z-graphviz-12.2.1/bin/dot /nix/store/mc99a6bpbk2waym2cnw6ifmxli4ndb4x-graphviz-15.1.1/bin/dot
✅ doxygen ✅ doxygen
1.16.1 1.17.0
/nix/store/kbryjdpq9jizjb0ws0nzbf2h2ymbdiwm-doxygen-1.16.1/bin/doxygen /nix/store/kz43yaj0wg6fx6cbrcmi2442z1ramy0c-doxygen-1.17.0/bin/doxygen
✅ gcovr ✅ gcovr
gcovr 8.4 gcovr 8.4
/nix/store/wn8jiyh9p0bybs96s4163qp3k8vfmczx-python3.13-gcovr-8.4/bin/gcovr /nix/store/czj1vxsizrbba280gg22cys40qxkqjgr-python3.14-gcovr-8.4/bin/gcovr
✅ gh ✅ gh
gh version 2.94.0 (nixpkgs) gh version 2.102.0 (2026-09-30)
/nix/store/fhnpw0hs0gjms1ha6ap02jq7rx13gkbp-gh-2.94.0/bin/gh /nix/store/s8bahl6zssvry93ihivfmk1l6c58byrr-gh-2.102.0/bin/gh
✅ git-cliff ✅ git-cliff
git-cliff 2.13.1 git-cliff 2.14.2
/nix/store/cy0wwhgxa7yvrz97zydbq6sqmixc90fq-git-cliff-2.13.1/bin/git-cliff /nix/store/k4m5yk0qb7hfslwsq1zjajz1d94j12bj-git-cliff-2.14.2/bin/git-cliff
✅ git-lfs ✅ git-lfs
git-lfs/3.7.1 (3.7.1; darwin arm64; go 1.26.3) git-lfs/3.8.0 (3.8.0; darwin arm64; go 1.26.8)
/nix/store/k9r7zjfjplqa4d5s71cqvf2iv73jd9mc-git-lfs-3.7.1/bin/git-lfs /nix/store/wzixjr3yb40a13m2q654hm3bdjn6sal3-git-lfs-3.8.0/bin/git-lfs
✅ gpg ✅ gpg
gpg (GnuPG) 2.4.9 gpg (GnuPG) 2.4.9
/nix/store/cgh6iwzz5jgx9z5whka4vgj210i6npc6-gnupg-2.4.9/bin/gpg /nix/store/0ldfwnwx385i5kh7cyvxx4mkvgjhs5rh-gnupg-2.4.9/bin/gpg
✅ pre-commit ✅ pre-commit
pre-commit 4.5.1 pre-commit 4.6.2
/nix/store/z3cca68620w0w10f090szgzdnmh1waf2-pre-commit-4.5.1/bin/pre-commit /nix/store/ivh54xypg9qvd3ha9lis0i8p4nkf8n7a-pre-commit-4.6.2/bin/pre-commit
✅ run-clang-tidy ✅ run-clang-tidy
usage: run-clang-tidy [-h] [-allow-enabling-alpha-checkers] usage: run-clang-tidy [-h] [-allow-enabling-alpha-checkers]
/nix/store/4x28x911z2f9y7adqlh3qspp4a16dig7-run-clang-tidy/bin/run-clang-tidy /nix/store/zjbzr154xan5xg9pmjiv0zkwklyb94wv-run-clang-tidy/bin/run-clang-tidy
✅ run-clang-tidy-22 ✅ run-clang-tidy-23
usage: run-clang-tidy [-h] [-allow-enabling-alpha-checkers] usage: run-clang-tidy [-h] [-allow-enabling-alpha-checkers]
/nix/store/x8iymrh76sk5q91ryg5pa7i32s6gfh34-run-clang-tidy-22/bin/run-clang-tidy-22 /nix/store/svhfrpgx2j581brsqmkpav9b286v22yy-run-clang-tidy-23/bin/run-clang-tidy-23
Rust toolchain: Rust toolchain:
✅ cargo ✅ cargo
cargo 1.97.1 (c980f4866 2026-06-30) cargo 1.97.1 (c980f4866 2026-06-30)
/nix/store/bnfk1sl4s9angb0vj1cj9a5y5zvqinwy-rust-minimal-1.97.1/bin/cargo /nix/store/gklji8yq8yrx1k039c10kwz60vqf2dxj-rust-minimal-1.97.1/bin/cargo
✅ cargo-audit ✅ cargo-audit
cargo-audit-audit 0.22.1 cargo-audit-audit 0.22.2
/nix/store/snwkga2f5gyf404h7mmp9wriwxb8v65f-cargo-audit-0.22.1/bin/cargo-audit /nix/store/7jgrwj557l91940aj0ag4i924ima1cqn-cargo-audit-0.22.2/bin/cargo-audit
✅ cargo-llvm-cov ✅ cargo-llvm-cov
cargo-llvm-cov 0.8.5 cargo-llvm-cov 0.9.0
/nix/store/fpiqdh91gwyxalqp409ynm0s0g086w7w-cargo-llvm-cov-0.8.5/bin/cargo-llvm-cov /nix/store/5q1h285z8zzkw2qxig9a0b1avcsk1cf0-cargo-llvm-cov-0.9.0/bin/cargo-llvm-cov
✅ cargo-nextest ✅ cargo-nextest
cargo-nextest 0.9.137 cargo-nextest 0.9.146
/nix/store/ylz7m947mhkgsp6i7611id3s3gcd58nq-cargo-nextest-0.9.137/bin/cargo-nextest /nix/store/69v3hx3k597hcxd2zy7yad7fg0aw5yxd-cargo-nextest-0.9.146/bin/cargo-nextest
✅ clippy-driver ✅ clippy-driver
clippy 0.1.97 (8bab26f4f6 2026-07-14) clippy 0.1.97 (8bab26f4f6 2026-07-14)
/nix/store/bnfk1sl4s9angb0vj1cj9a5y5zvqinwy-rust-minimal-1.97.1/bin/clippy-driver /nix/store/gklji8yq8yrx1k039c10kwz60vqf2dxj-rust-minimal-1.97.1/bin/clippy-driver
✅ rust-analyzer ✅ rust-analyzer
rust-analyzer 1.97.1 (8bab26f4 2026-07-14) rust-analyzer 1.97.1 (8bab26f4 2026-07-14)
/nix/store/j6apc5pmd0giy15da9p650r8zklslmvi-rust-analyzer-preview-1.97.1-aarch64-apple-darwin/bin/rust-analyzer /nix/store/30rbyk8gx7v53fxqhs4pp0fvxfjycspr-rust-analyzer-preview-1.97.1-aarch64-apple-darwin/bin/rust-analyzer
✅ rust-nightly ✅ rust-nightly
rustc 1.99.0-nightly (87e5904f5 2026-07-20) rustc 1.101.0-nightly (282215592 2026-10-04)
/nix/store/fqpjz4l0nsnji8b2pz57mnj0akbp6hcl-rust-nightly/bin/rust-nightly /nix/store/a9552rf3pylcnkijc1z0hf1lcnv50djq-rust-nightly/bin/rust-nightly
✅ rustc ✅ rustc
rustc 1.97.1 (8bab26f4f 2026-07-14) rustc 1.97.1 (8bab26f4f 2026-07-14)
/nix/store/bnfk1sl4s9angb0vj1cj9a5y5zvqinwy-rust-minimal-1.97.1/bin/rustc /nix/store/gklji8yq8yrx1k039c10kwz60vqf2dxj-rust-minimal-1.97.1/bin/rustc
✅ rustfmt ✅ rustfmt
rustfmt 1.9.0-stable (8bab26f4f6 2026-07-14) rustfmt 1.9.0-stable (8bab26f4f6 2026-07-14)
/nix/store/5ymwgr9jqjz7zzbmj0j5vqbwcd3kp0vm-rustfmt-preview-1.97.1-aarch64-apple-darwin/bin/rustfmt /nix/store/0jmdipyn8266j9kqx2xxm2qkxlrlrjfc-rustfmt-preview-1.97.1-aarch64-apple-darwin/bin/rustfmt
Skipping git-over-HTTPS check (CHECK_TOOLS_SKIP_CLONE is set). Skipping git-over-HTTPS check (CHECK_TOOLS_SKIP_CLONE is set).
✅ All 45 checked tools are present and runnable. ✅ All 46 checked tools are present and runnable.
+99 -96
View File
@@ -2,173 +2,176 @@ Detected OS: linux (Linux x86_64)
Core build tools: Core build tools:
✅ cmake ✅ cmake
cmake version 4.1.2 cmake version 4.4.3
/nix/store/r9941n32g4wyvggz2703dlplbdq8a6rd-cmake-4.1.2/bin/cmake /nix/store/jcvvpih1046akxcwh9hdiak5q24jqcf0-cmake-4.4.3/bin/cmake
✅ conan ✅ conan
Conan version 2.28.1 Conan version 2.33.0
/nix/store/lxny9y4jvjdws7hgz1mygvb7hjrpmna5-conan-2.28.1/bin/conan /nix/store/b4lnzrqc60glhl9al1nakfc0vd20kdna-conan-2.33.0/bin/conan
✅ git ✅ git
git version 2.54.0 git version 2.55.0
/nix/store/bcnisk3ydfgv26v2gw3zlky24g00yww2-git-2.54.0/bin/git /nix/store/lg46w7hrjx7kylsh6645c9l975i8h43b-git-2.55.0/bin/git
✅ python3 ✅ python3
Python 3.13.13 Python 3.14.7
/nix/store/60m4rxhg2fldqaak400c0lry96ijrzqn-python3-3.13.13/bin/python3.13 /nix/store/lb41b0anx1f98y9y5s9mdv97gjgsq740-python3-3.14.7/bin/python3.14
Development tooling: Development tooling:
✅ ccache ✅ ccache
ccache version 4.13.6 ccache version 4.13.6
/nix/store/c9wwl7s5i6rsfwvf4v0xbbmzx5m6jgfr-ccache-4.13.6/bin/ccache /nix/store/p1a1s700dqsw1b3b8d2ba64nqw68zgpy-ccache-4.13.6/bin/ccache
✅ clang ✅ clang
clang version 22.1.7 clang version 23.1.0
/nix/store/ff0hrp9r9i3pa5arkdw0sgmzp8d576qi-clang-wrapper-22.1.7/bin/clang /nix/store/mlqh1xrp0zi3i5g9b0zjcz6zlbbzdgb8-clang-wrapper-23.1.0/bin/clang
✅ clang-22 ✅ clang-23
clang version 22.1.7 clang version 23.1.0
/nix/store/dagc2rq44gfbr7w7yvvqca3yqpc9gqbq-clang-22/bin/clang-22 /nix/store/xgi7q1bady9dk89zvjmiicjzzp1gvm7x-clang-23/bin/clang-23
✅ clang++ ✅ clang++
clang version 22.1.7 clang version 23.1.0
/nix/store/ff0hrp9r9i3pa5arkdw0sgmzp8d576qi-clang-wrapper-22.1.7/bin/clang++ /nix/store/mlqh1xrp0zi3i5g9b0zjcz6zlbbzdgb8-clang-wrapper-23.1.0/bin/clang++
✅ clang++-22 ✅ clang++-23
clang version 22.1.7 clang version 23.1.0
/nix/store/l5m8clin1npl605wdkd8mr18ggxww3z4-clang++-22/bin/clang++-22 /nix/store/4slsaz29v72xgc4g36cp94f0p41a81pv-clang++-23/bin/clang++-23
✅ ClangBuildAnalyzer ✅ ClangBuildAnalyzer
ClangBuildAnalyzer 1.6.0 ClangBuildAnalyzer 1.6.0
/nix/store/bshlmn8fqw55nsnm581xqlfbahfkykxx-clangbuildanalyzer-1.6.0/bin/ClangBuildAnalyzer /nix/store/gvx8im1c89vspwb8ixa91lr1dagbi241-clangbuildanalyzer-1.6.0/bin/ClangBuildAnalyzer
✅ curl ✅ curl
curl 8.20.0 (x86_64-pc-linux-gnu) libcurl/8.20.0 OpenSSL/3.6.2 zlib/1.3.2 libssh2/1.11.1 nghttp2/1.69.0 mit-krb5/1.22.1 curl 8.22.0 (x86_64-pc-linux-gnu) libcurl/8.22.0 OpenSSL/3.5.8 zlib/1.3.2 libssh2/1.11.1 nghttp2/1.70.0 mit-krb5/1.22.2
/nix/store/zbwymrp4lcfjc4kkk0n4779v0kjjz58z-curl-8.20.0-bin/bin/curl /nix/store/305w9ipyg497mz9dq31abdf61qk58k29-curl-8.22.0-bin/bin/curl
✅ file ✅ file
file-5.47 file-5.48
/nix/store/bizyfqdw0h67wzqmp10knmf9s2pqahdb-file-5.47/bin/file /nix/store/g0fbnccaan8q0rxlw43xnbyb90i94vlc-file-5.48/bin/file
✅ jq
jq-1.8.2
/nix/store/m3y7hqmy20nd1ps6qy8410a326255bf0-jq-1.8.2-bin/bin/jq
✅ less ✅ less
less 692 (PCRE2 regular expressions) less 710 (PCRE2 regular expressions)
/nix/store/c6bacbn93qg4a7g9n4czww8rg24dvysr-less-692/bin/less /nix/store/zi4d0awnc6crz18s177bv9y2yz9al3lq-less-710/bin/less
✅ make ✅ make
GNU Make 4.4.1 GNU Make 4.4.1
/nix/store/d3bwqm6bymhy3pdgbvf7vxjqfp31m3j1-gnumake-4.4.1/bin/make /nix/store/z565rgmn9vccv2h0g87z725pw610jmm8-gnumake-4.4.1/bin/make
✅ netstat ✅ netstat
net-tools 2.10 net-tools 2.10
/nix/store/jmyzqvgflnswmws7rnxx6g3zbj680xvd-net-tools-2.10/bin/netstat /nix/store/9i6j9lrsliyz1ww2f8xx18z36wc9n38a-net-tools-2.10/bin/netstat
✅ ninja ✅ ninja
1.13.2 1.13.2
/nix/store/7a235m7crqbb4h49sak20fqxpw3n7hr0-ninja-1.13.2/bin/ninja /nix/store/4nsdla28c4177ssp0hlyv5l2yzj8wcba-ninja-1.13.2/bin/ninja
✅ perl ✅ perl
v5.42.0 v5.42.3
/nix/store/6plwsm6pkq79yjv4xvy8csk2pd4hzr67-perl-5.42.0/bin/perl /nix/store/8g4dmf7l8q1mf9w4wfmlcl8gvdgmhb8v-perl-5.42.3/bin/perl
✅ pkg-config ✅ pkg-config
0.29.2 0.29.2
/nix/store/1m05k7xgfnw6jc21xxk5681ni3ar97wf-pkg-config-wrapper-0.29.2/bin/pkg-config /nix/store/b9izmrfjp0qnnyahdwwrzdwi87s1h179-pkg-config-wrapper-0.29.2/bin/pkg-config
✅ vim ✅ vim
VIM - Vi IMproved 9.2 (2026 Feb 14, compiled Jan 01 1980 00:00:00) VIM - Vi IMproved 9.2 (2026 Feb 14, compiled Jan 01 1980 00:00:00)
/nix/store/hvyqx52g4g2fxhgpans3fksjj6lmlyaw-vim-9.2.0389/bin/vim /nix/store/9swnd5pf8p8w1gwcbhdpm2yx705kbp38-vim-9.2.1001/bin/vim
✅ zip ✅ zip
Zip 3.0 Zip 3.0
/nix/store/qnd2ag67hrjj0b6vbmisdshf50r6s72n-zip-3.0/bin/zip /nix/store/5ypvkry3qra47dylc9kfk36r1q9vha80-zip-3.0/bin/zip
✅ clang-apply-replacements ✅ clang-apply-replacements
clang-apply-replacements version 22.1.7 clang-apply-replacements version 23.1.0
/nix/store/4zp1rjpj2xijrv4kqpwsy3ixwb2r6nlk-clang-tools-22.1.7/bin/clang-apply-replacements /nix/store/ipnj8b3s6f00ngi26fi7p5h9lxv6a3s3-clang-tools-23.1.0/bin/clang-apply-replacements
✅ clang-apply-replacements-22 ✅ clang-apply-replacements-23
clang-apply-replacements version 22.1.7 clang-apply-replacements version 23.1.0
/nix/store/py2wihg0a96qcppv4hjmww547xabr0fb-clang-apply-replacements-22/bin/clang-apply-replacements-22 /nix/store/lbyc9hrkkymybah7b6n8c7sijlgldfz0-clang-apply-replacements-23/bin/clang-apply-replacements-23
✅ clang-format ✅ clang-format
clang-format version 22.1.7 clang-format version 23.1.0
/nix/store/4zp1rjpj2xijrv4kqpwsy3ixwb2r6nlk-clang-tools-22.1.7/bin/clang-format /nix/store/ipnj8b3s6f00ngi26fi7p5h9lxv6a3s3-clang-tools-23.1.0/bin/clang-format
✅ clang-format-22 ✅ clang-format-23
clang-format version 22.1.7 clang-format version 23.1.0
/nix/store/kz820ccifjlwqnwqjsx7kbiajrgsmbrh-clang-format-22/bin/clang-format-22 /nix/store/40w351b7i7aqhpl5wmicfnp2ij8k12g9-clang-format-23/bin/clang-format-23
✅ clang-tidy ✅ clang-tidy
LLVM version 22.1.7 LLVM version 23.1.0
/nix/store/4zp1rjpj2xijrv4kqpwsy3ixwb2r6nlk-clang-tools-22.1.7/bin/clang-tidy /nix/store/ipnj8b3s6f00ngi26fi7p5h9lxv6a3s3-clang-tools-23.1.0/bin/clang-tidy
✅ clang-tidy-22 ✅ clang-tidy-23
LLVM version 22.1.7 LLVM version 23.1.0
/nix/store/gdrkvpw846lkyzh8y9p3zx50g6ml2v84-clang-tidy-22/bin/clang-tidy-22 /nix/store/40rj38k5ygq7sawkiv0cdaljclbspwz9-clang-tidy-23/bin/clang-tidy-23
✅ dot ✅ dot
dot - graphviz version 12.2.1 (0) dot - graphviz version 15.1.1 (0)
/nix/store/12rgns2296s4qcja778gvcbx61z77rc4-graphviz-12.2.1/bin/dot /nix/store/f7r47nc0d13xa4c2xaaxa6dp3pzm9sp1-graphviz-15.1.1/bin/dot
✅ doxygen ✅ doxygen
1.16.1 1.17.0
/nix/store/k0vzr5lvgq1byraknzwvk51wcgpnsrkh-doxygen-1.16.1/bin/doxygen /nix/store/q6yx2nsimj9xmckmgw4br2cnapbgnqpk-doxygen-1.17.0/bin/doxygen
✅ gcovr ✅ gcovr
gcovr 8.4 gcovr 8.4
/nix/store/iyzi7fpyclqrha054adnizvif02lg49x-python3.13-gcovr-8.4/bin/gcovr /nix/store/shx7mfl8n4kx11icvwyj5x7cmf6z5ahq-python3.14-gcovr-8.4/bin/gcovr
✅ gh ✅ gh
gh version 2.94.0 (nixpkgs) gh version 2.102.0 (2026-09-30)
/nix/store/pidh15szlsb1vc41xdsa3xbdghdazvby-gh-2.94.0/bin/gh /nix/store/66h5dr9v94x04myh2kabx06rq9763jfc-gh-2.102.0/bin/gh
✅ git-cliff ✅ git-cliff
git-cliff 2.13.1 git-cliff 2.14.2
/nix/store/1q851fs62shgjhc03fxxdkpzxdjg7k11-git-cliff-2.13.1/bin/git-cliff /nix/store/sl19b42d69b3w2vb9pxp6jbqk841z8vj-git-cliff-2.14.2/bin/git-cliff
✅ git-lfs ✅ git-lfs
git-lfs/3.7.1 (3.7.1; linux amd64; go 1.26.3) git-lfs/3.8.0 (3.8.0; linux amd64; go 1.26.8)
/nix/store/6ljwpal7b1756708m33vj0crpral7mvl-git-lfs-3.7.1/bin/git-lfs /nix/store/rp9ld1f6h83xmf2rb5fpib5wmr46fy9f-git-lfs-3.8.0/bin/git-lfs
✅ gpg ✅ gpg
gpg (GnuPG) 2.4.9 gpg (GnuPG) 2.4.9
/nix/store/wx7vk8babxkgy813r70yc67vcwnmagbx-gnupg-2.4.9/bin/gpg /nix/store/8gm9aq3sspqmvvh7c0x7djcivj2x7yvn-gnupg-2.4.9/bin/gpg
✅ pre-commit ✅ pre-commit
pre-commit 4.5.1 pre-commit 4.6.2
/nix/store/bj6i9vl34cij5h0r165y40hrjqak0bmz-pre-commit-4.5.1/bin/pre-commit /nix/store/6blf72f7sdmlrqjggxvk5ij4cxb7fk4c-pre-commit-4.6.2/bin/pre-commit
✅ run-clang-tidy ✅ run-clang-tidy
usage: run-clang-tidy [-h] [-allow-enabling-alpha-checkers] usage: run-clang-tidy [-h] [-allow-enabling-alpha-checkers]
/nix/store/sbg911hs9dbclrzlp04br3iyfpgnaj6r-run-clang-tidy/bin/run-clang-tidy /nix/store/y7isn3dr8bildnp78vk5nhcav63g80dz-run-clang-tidy/bin/run-clang-tidy
✅ run-clang-tidy-22 ✅ run-clang-tidy-23
usage: run-clang-tidy [-h] [-allow-enabling-alpha-checkers] usage: run-clang-tidy [-h] [-allow-enabling-alpha-checkers]
/nix/store/n8yak1ap308gvi7gmrniw0ybsx80fjws-run-clang-tidy-22/bin/run-clang-tidy-22 /nix/store/pm5a8465hs9zb5i116b39i0y3xfpw6n3-run-clang-tidy-23/bin/run-clang-tidy-23
Rust toolchain: Rust toolchain:
✅ cargo ✅ cargo
cargo 1.97.1 (c980f4866 2026-06-30) cargo 1.97.1 (c980f4866 2026-06-30)
/nix/store/88abzp43ywyzql1rhf8jh5aj5n5j7xzr-cargo-1.97.1-x86_64-unknown-linux-gnu/bin/cargo /nix/store/60b0cz400q34wj2gzav5a41i7y6jzlw3-cargo-1.97.1-x86_64-unknown-linux-gnu/bin/cargo
✅ cargo-audit ✅ cargo-audit
cargo-audit-audit 0.22.1 cargo-audit-audit 0.22.2
/nix/store/2w9if868piw98xz057sz97jnjvf7hnvf-cargo-audit-0.22.1/bin/cargo-audit /nix/store/kksgynfwir3pfii9qkbj3gcc61an0d4s-cargo-audit-0.22.2/bin/cargo-audit
✅ cargo-llvm-cov ✅ cargo-llvm-cov
cargo-llvm-cov 0.8.5 cargo-llvm-cov 0.9.0
/nix/store/jjpdf1l6izz6607a346ykra9sndzaw7h-cargo-llvm-cov-0.8.5/bin/cargo-llvm-cov /nix/store/4y8qxx0mlm22hnxlw2cmbcwpxispw02h-cargo-llvm-cov-0.9.0/bin/cargo-llvm-cov
✅ cargo-nextest ✅ cargo-nextest
cargo-nextest 0.9.137 cargo-nextest 0.9.146
/nix/store/jhkr7gwyrchkml33gyns9cy0yn7b57qc-cargo-nextest-0.9.137/bin/cargo-nextest /nix/store/q0anzqrazmdr8n1049ca28098q6lv2y8-cargo-nextest-0.9.146/bin/cargo-nextest
✅ clippy-driver ✅ clippy-driver
clippy 0.1.97 (8bab26f4f6 2026-07-14) clippy 0.1.97 (8bab26f4f6 2026-07-14)
/nix/store/40d3mzka7r1ps71l0yv2fs6616nbw85m-rust-minimal-1.97.1/bin/clippy-driver /nix/store/kk0kqdc4f7am21yp30rr8jcrnib5xqzy-rust-minimal-1.97.1/bin/clippy-driver
✅ rust-analyzer ✅ rust-analyzer
rust-analyzer 1.97.1 (8bab26f 2026-07-14) rust-analyzer 1.97.1 (8bab26f 2026-07-14)
/nix/store/lr3m97p3hx1k22a7c44pb0wa7rbayhfi-rust-analyzer-preview-1.97.1-x86_64-unknown-linux-gnu/bin/rust-analyzer /nix/store/4mglk7qw9jqbv5nwlx9ahdnpcn5sz70r-rust-analyzer-preview-1.97.1-x86_64-unknown-linux-gnu/bin/rust-analyzer
✅ rust-nightly ✅ rust-nightly
rustc 1.99.0-nightly (87e5904f5 2026-07-20) rustc 1.101.0-nightly (282215592 2026-10-04)
/nix/store/j7kf7a5h4xypzp6x1skg4dsdx2k4fwb3-rust-nightly/bin/rust-nightly /nix/store/qwyzkvba3f9569wjj45b4iyb7nz7qbnr-rust-nightly/bin/rust-nightly
✅ rustc ✅ rustc
rustc 1.97.1 (8bab26f4f 2026-07-14) rustc 1.97.1 (8bab26f4f 2026-07-14)
/nix/store/40d3mzka7r1ps71l0yv2fs6616nbw85m-rust-minimal-1.97.1/bin/rustc /nix/store/kk0kqdc4f7am21yp30rr8jcrnib5xqzy-rust-minimal-1.97.1/bin/rustc
✅ rustfmt ✅ rustfmt
rustfmt 1.9.0-stable (8bab26f4f6 2026-07-14) rustfmt 1.9.0-stable (8bab26f4f6 2026-07-14)
/nix/store/6f1icmb2za20kxn30pgmbv5jq9fnbf4z-rustfmt-preview-1.97.1-x86_64-unknown-linux-gnu/bin/rustfmt /nix/store/y5gf8a3hix7pnwzdwcfpf3acqhzv3xy6-rustfmt-preview-1.97.1-x86_64-unknown-linux-gnu/bin/rustfmt
GCC toolchain: GCC toolchain:
✅ gcc ✅ gcc
gcc (GCC) 15.2.0 gcc (GCC) 15.3.0
/nix/store/3dd6y3pq00i3r85l45jvz63wjya403nl-gcc-wrapper-15.2.0/bin/gcc /nix/store/bslmkbaiymxxdc6lwcdb1qyw745nds5j-gcc-wrapper-15.3.0/bin/gcc
✅ gcc-15 ✅ gcc-15
gcc (GCC) 15.2.0 gcc (GCC) 15.3.0
/nix/store/d6iri2s6bzqq5ac3fg25j6hgnn1lz44f-gcc-15/bin/gcc-15 /nix/store/h6f2qc8kgwf7r81gwb10csvpjqfc2404-gcc-15/bin/gcc-15
✅ g++ ✅ g++
g++ (GCC) 15.2.0 g++ (GCC) 15.3.0
/nix/store/3dd6y3pq00i3r85l45jvz63wjya403nl-gcc-wrapper-15.2.0/bin/g++ /nix/store/bslmkbaiymxxdc6lwcdb1qyw745nds5j-gcc-wrapper-15.3.0/bin/g++
✅ g++-15 ✅ g++-15
g++ (GCC) 15.2.0 g++ (GCC) 15.3.0
/nix/store/gm3msmmxq055lm9gprkfjj9d2gdz1mpg-g++-15/bin/g++-15 /nix/store/jwncv76v61ld9l99v0b1dkmf810if65s-g++-15/bin/g++-15
✅ cpp ✅ cpp
cpp (GCC) 15.2.0 cpp (GCC) 15.3.0
/nix/store/3dd6y3pq00i3r85l45jvz63wjya403nl-gcc-wrapper-15.2.0/bin/cpp /nix/store/bslmkbaiymxxdc6lwcdb1qyw745nds5j-gcc-wrapper-15.3.0/bin/cpp
✅ cpp-15 ✅ cpp-15
cpp (GCC) 15.2.0 cpp (GCC) 15.3.0
/nix/store/bn3gmn0m7g4gn2i0yml46fljc7mghiq5-cpp-15/bin/cpp-15 /nix/store/jmi558xj8v7lz2fm6wrradh40dp48zx9-cpp-15/bin/cpp-15
✅ gcov ✅ gcov
gcov (GCC) 15.2.0 gcov (GCC) 15.3.0
/nix/store/xvv5sm5i8x0ks6ypfkzl7c4j9srnxz7k-gcc-15.2.0/bin/gcov /nix/store/n2ab7kf7mm84hna35x463mizcy52pf1h-gcc-15.3.0/bin/gcov
Mold: Mold:
✅ mold ✅ mold
mold 2.41.0 (compatible with GNU ld) mold 2.42.1 (compatible with GNU ld)
/nix/store/2w6fpgxjzzyqmd25wzplm23dfa49a0p2-mold-unwrapped-wrapper-2.41.0/bin/mold /nix/store/9dcddrfxlfl9n3wfibi5jkmp22bjkvkh-mold-unwrapped-wrapper-2.42.1/bin/mold
Skipping git-over-HTTPS check (CHECK_TOOLS_SKIP_CLONE is set). Skipping git-over-HTTPS check (CHECK_TOOLS_SKIP_CLONE is set).
✅ All 53 checked tools are present and runnable. ✅ All 54 checked tools are present and runnable.
+99 -96
View File
@@ -2,173 +2,176 @@ Detected OS: linux (Linux aarch64)
Core build tools: Core build tools:
✅ cmake ✅ cmake
cmake version 4.1.2 cmake version 4.4.3
/nix/store/nkcpxjifkambzlrwh27a8igvhnbchibg-cmake-4.1.2/bin/cmake /nix/store/39cq2g3d3flq2lmb6hc09grxs4xaax8p-cmake-4.4.3/bin/cmake
✅ conan ✅ conan
Conan version 2.28.1 Conan version 2.33.0
/nix/store/8i2gyqgc00xvxg9xm6y7n0ilncdv8imw-conan-2.28.1/bin/conan /nix/store/grz6a77mllqzzmg198qagx1r9zhvfijw-conan-2.33.0/bin/conan
✅ git ✅ git
git version 2.54.0 git version 2.55.0
/nix/store/ixp98f9avf8ikpdrmp40cj33g0dazyp9-git-2.54.0/bin/git /nix/store/kj6aff4gmz3snpp35rl3gysbl9srd81a-git-2.55.0/bin/git
✅ python3 ✅ python3
Python 3.13.13 Python 3.14.7
/nix/store/lqn6mbgzzdrqq2qkwddcmxj9z6amdd86-python3-3.13.13/bin/python3.13 /nix/store/81ag9nxz1flw3xjkv1vvqg8y2ipx2ins-python3-3.14.7/bin/python3.14
Development tooling: Development tooling:
✅ ccache ✅ ccache
ccache version 4.13.6 ccache version 4.13.6
/nix/store/2q39xi2kbi04ibga7635f2sl148d1mzv-ccache-4.13.6/bin/ccache /nix/store/nzb1lir9sw06fn4635kfx055myqanaz8-ccache-4.13.6/bin/ccache
✅ clang ✅ clang
clang version 22.1.7 clang version 23.1.0
/nix/store/xjqffrq9i7la058s9865ig71l9sp1ys5-clang-wrapper-22.1.7/bin/clang /nix/store/g8sc13kz6jarzip643hk01832x40v8ms-clang-wrapper-23.1.0/bin/clang
✅ clang-22 ✅ clang-23
clang version 22.1.7 clang version 23.1.0
/nix/store/vcf6ilfwn57828hwzyp6zlyr24j9j6yw-clang-22/bin/clang-22 /nix/store/j8qvcg9150s5n09qg8p62q5z3ci02hd9-clang-23/bin/clang-23
✅ clang++ ✅ clang++
clang version 22.1.7 clang version 23.1.0
/nix/store/xjqffrq9i7la058s9865ig71l9sp1ys5-clang-wrapper-22.1.7/bin/clang++ /nix/store/g8sc13kz6jarzip643hk01832x40v8ms-clang-wrapper-23.1.0/bin/clang++
✅ clang++-22 ✅ clang++-23
clang version 22.1.7 clang version 23.1.0
/nix/store/xby0f6gamr7m27zp5cndsvghbp9lgb3c-clang++-22/bin/clang++-22 /nix/store/n62cn5w7fgbslamy3dgm8zhl5yly7zq0-clang++-23/bin/clang++-23
✅ ClangBuildAnalyzer ✅ ClangBuildAnalyzer
ClangBuildAnalyzer 1.6.0 ClangBuildAnalyzer 1.6.0
/nix/store/h893hd4q1bb6ily2lby5dzyfrrzd2nvj-clangbuildanalyzer-1.6.0/bin/ClangBuildAnalyzer /nix/store/ml2991pbdhh0qcxqj9331lhpsg449vky-clangbuildanalyzer-1.6.0/bin/ClangBuildAnalyzer
✅ curl ✅ curl
curl 8.20.0 (aarch64-unknown-linux-gnu) libcurl/8.20.0 OpenSSL/3.6.2 zlib/1.3.2 libssh2/1.11.1 nghttp2/1.69.0 mit-krb5/1.22.1 curl 8.22.0 (aarch64-unknown-linux-gnu) libcurl/8.22.0 OpenSSL/3.5.8 zlib/1.3.2 libssh2/1.11.1 nghttp2/1.70.0 mit-krb5/1.22.2
/nix/store/i1s0lqwlrmjd2dxzgy2p84cxqqsb0bmk-curl-8.20.0-bin/bin/curl /nix/store/94c2x2bl3xb7mx43sg1bs1hd7pnw83ac-curl-8.22.0-bin/bin/curl
✅ file ✅ file
file-5.47 file-5.48
/nix/store/dx973zg9km2w9albsib2vw9wyvacfrlw-file-5.47/bin/file /nix/store/66sd1x1hls0yijibn00iz08jh4fnas9z-file-5.48/bin/file
✅ jq
jq-1.8.2
/nix/store/kr5py0dcqc9f3l9148qd1axh0z77lld3-jq-1.8.2-bin/bin/jq
✅ less ✅ less
less 692 (PCRE2 regular expressions) less 710 (PCRE2 regular expressions)
/nix/store/1blb3s7hhsr77wqi598m6k1qkfp3ms0w-less-692/bin/less /nix/store/n6z9dv3yjlgvfx1nmrx6qzyv8vzim1l2-less-710/bin/less
✅ make ✅ make
GNU Make 4.4.1 GNU Make 4.4.1
/nix/store/9ngw1ippk25jjj5fjxv36xbp6iq7rxdx-gnumake-4.4.1/bin/make /nix/store/q07jxvck60qgrg4p1ywypddh5zz6i9s2-gnumake-4.4.1/bin/make
✅ netstat ✅ netstat
net-tools 2.10 net-tools 2.10
/nix/store/7vdsz21f0s499s5yyqzp5s4676q4yxdd-net-tools-2.10/bin/netstat /nix/store/rfmhd3f8drg3wqyr2mhyrlkd7vyp2pxv-net-tools-2.10/bin/netstat
✅ ninja ✅ ninja
1.13.2 1.13.2
/nix/store/8ksx98gsbn5lmlizcmw57yd4sg0k2p58-ninja-1.13.2/bin/ninja /nix/store/lfkdyggn1ffslfd830l35jrvapr5lzri-ninja-1.13.2/bin/ninja
✅ perl ✅ perl
v5.42.0 v5.42.3
/nix/store/5wnly69vv1i3y97al4v3xrqymf9hlzgq-perl-5.42.0/bin/perl /nix/store/nyp5q4d2cb0pghi4i7nscb97bqkb6kp3-perl-5.42.3/bin/perl
✅ pkg-config ✅ pkg-config
0.29.2 0.29.2
/nix/store/c7vwy0gl1q0agl2h22gi0m9dg7xxad2l-pkg-config-wrapper-0.29.2/bin/pkg-config /nix/store/h82n3d0wdrgskdc3yvmz5l3c50h2snvp-pkg-config-wrapper-0.29.2/bin/pkg-config
✅ vim ✅ vim
VIM - Vi IMproved 9.2 (2026 Feb 14, compiled Jan 01 1980 00:00:00) VIM - Vi IMproved 9.2 (2026 Feb 14, compiled Jan 01 1980 00:00:00)
/nix/store/v8c7pvx26irvy9k5sbwd183cyvckzzb3-vim-9.2.0389/bin/vim /nix/store/h39h0qq4i80sp3yd7sxjn2wf497v5rln-vim-9.2.1001/bin/vim
✅ zip ✅ zip
Zip 3.0 Zip 3.0
/nix/store/5mh19mvbv9ym2sm9vymyyaac5l2cj2jq-zip-3.0/bin/zip /nix/store/lfwhq17wfcmjy823fldhlhxj1hjchdzc-zip-3.0/bin/zip
✅ clang-apply-replacements ✅ clang-apply-replacements
clang-apply-replacements version 22.1.7 clang-apply-replacements version 23.1.0
/nix/store/s53p2m776iqaz7acgr5csgpsd18w15h7-clang-tools-22.1.7/bin/clang-apply-replacements /nix/store/jh9xhz6gwxyz3rfx7vy5g4j5d71w940r-clang-tools-23.1.0/bin/clang-apply-replacements
✅ clang-apply-replacements-22 ✅ clang-apply-replacements-23
clang-apply-replacements version 22.1.7 clang-apply-replacements version 23.1.0
/nix/store/bg4kn8z81hk7b9284rjqvr51wpfjqc24-clang-apply-replacements-22/bin/clang-apply-replacements-22 /nix/store/1ajzrfr62m3cianfh9i97r30a7vp1xmb-clang-apply-replacements-23/bin/clang-apply-replacements-23
✅ clang-format ✅ clang-format
clang-format version 22.1.7 clang-format version 23.1.0
/nix/store/s53p2m776iqaz7acgr5csgpsd18w15h7-clang-tools-22.1.7/bin/clang-format /nix/store/jh9xhz6gwxyz3rfx7vy5g4j5d71w940r-clang-tools-23.1.0/bin/clang-format
✅ clang-format-22 ✅ clang-format-23
clang-format version 22.1.7 clang-format version 23.1.0
/nix/store/79v57mzcw8ng8kl7p961ck08ymhp31v7-clang-format-22/bin/clang-format-22 /nix/store/5nfddq7xgbp4zmj8jn7xk1pxyyn5wiwl-clang-format-23/bin/clang-format-23
✅ clang-tidy ✅ clang-tidy
LLVM version 22.1.7 LLVM version 23.1.0
/nix/store/s53p2m776iqaz7acgr5csgpsd18w15h7-clang-tools-22.1.7/bin/clang-tidy /nix/store/jh9xhz6gwxyz3rfx7vy5g4j5d71w940r-clang-tools-23.1.0/bin/clang-tidy
✅ clang-tidy-22 ✅ clang-tidy-23
LLVM version 22.1.7 LLVM version 23.1.0
/nix/store/wdyd6cb9z1lyi37lbzvwldgcc7yv1n5c-clang-tidy-22/bin/clang-tidy-22 /nix/store/cawfgsx0vsslc1f007cavmy8md9drb1r-clang-tidy-23/bin/clang-tidy-23
✅ dot ✅ dot
dot - graphviz version 12.2.1 (0) dot - graphviz version 15.1.1 (0)
/nix/store/58rrk4yzwpmyxvl8cqm18h3dhv24zf00-graphviz-12.2.1/bin/dot /nix/store/vz4zb8d1rfigzzdn3i0hd4kff28vk02l-graphviz-15.1.1/bin/dot
✅ doxygen ✅ doxygen
1.16.1 1.17.0
/nix/store/hq32kzwpl89wgr49iq0gmqn9r5n072zq-doxygen-1.16.1/bin/doxygen /nix/store/6q4z332wc9jnvad71wjj87lgjxidhgzl-doxygen-1.17.0/bin/doxygen
✅ gcovr ✅ gcovr
gcovr 8.4 gcovr 8.4
/nix/store/sml3xbbfhhlhk6h7jnlg19pdbx9b764b-python3.13-gcovr-8.4/bin/gcovr /nix/store/v548fjz51k2nmr257vjnd0zp3bxpc2r1-python3.14-gcovr-8.4/bin/gcovr
✅ gh ✅ gh
gh version 2.94.0 (nixpkgs) gh version 2.102.0 (2026-09-30)
/nix/store/7hh2qi0gj2ifbxbl56cjzbiyfc379bji-gh-2.94.0/bin/gh /nix/store/vgg6gnq74h76b4r2ac2q9366f2s5qxwx-gh-2.102.0/bin/gh
✅ git-cliff ✅ git-cliff
git-cliff 2.13.1 git-cliff 2.14.2
/nix/store/bidn3pz53yd6qlg711917xx0q10hqmqv-git-cliff-2.13.1/bin/git-cliff /nix/store/hrlgliq7l3fl2qrdlc197mvscs4n03rd-git-cliff-2.14.2/bin/git-cliff
✅ git-lfs ✅ git-lfs
git-lfs/3.7.1 (3.7.1; linux arm64; go 1.26.3) git-lfs/3.8.0 (3.8.0; linux arm64; go 1.26.8)
/nix/store/4rsklvkbac5bayy0zv12kxyvspi4sshd-git-lfs-3.7.1/bin/git-lfs /nix/store/pa2g4xdvr4a73m6mv4cqs0pik1ka1xp5-git-lfs-3.8.0/bin/git-lfs
✅ gpg ✅ gpg
gpg (GnuPG) 2.4.9 gpg (GnuPG) 2.4.9
/nix/store/ka4i8zz5ni3rzqnzcxbfvwr95fk8pn6q-gnupg-2.4.9/bin/gpg /nix/store/3qc90b7qkxz7na3xnpd2qb8yvcq8zdp6-gnupg-2.4.9/bin/gpg
✅ pre-commit ✅ pre-commit
pre-commit 4.5.1 pre-commit 4.6.2
/nix/store/n981w6hjfar2l81kxbxs2wxl64vwa5kj-pre-commit-4.5.1/bin/pre-commit /nix/store/5f3av75nc7n7xbf2hlvlagzpp2g8g562-pre-commit-4.6.2/bin/pre-commit
✅ run-clang-tidy ✅ run-clang-tidy
usage: run-clang-tidy [-h] [-allow-enabling-alpha-checkers] usage: run-clang-tidy [-h] [-allow-enabling-alpha-checkers]
/nix/store/4z2fyklg78klallr7x9j02kz92hnxp4m-run-clang-tidy/bin/run-clang-tidy /nix/store/nlg35d9ccslsq5qny7raxyyyrxgk7vsq-run-clang-tidy/bin/run-clang-tidy
✅ run-clang-tidy-22 ✅ run-clang-tidy-23
usage: run-clang-tidy [-h] [-allow-enabling-alpha-checkers] usage: run-clang-tidy [-h] [-allow-enabling-alpha-checkers]
/nix/store/f8m0p9ad40brp9ahy4i0h27kqjkya1j9-run-clang-tidy-22/bin/run-clang-tidy-22 /nix/store/a50nf8hp8p8l8pgcf9fs0j25hij5acw3-run-clang-tidy-23/bin/run-clang-tidy-23
Rust toolchain: Rust toolchain:
✅ cargo ✅ cargo
cargo 1.97.1 (c980f4866 2026-06-30) cargo 1.97.1 (c980f4866 2026-06-30)
/nix/store/6hch2qrr86n2sa2m90lrpxrfxxwbkayl-cargo-1.97.1-aarch64-unknown-linux-gnu/bin/cargo /nix/store/nci0zxxj2fiq0dlkpqzbnqfh27wz4sq4-cargo-1.97.1-aarch64-unknown-linux-gnu/bin/cargo
✅ cargo-audit ✅ cargo-audit
cargo-audit-audit 0.22.1 cargo-audit-audit 0.22.2
/nix/store/9rxbrn9aa2r1z96186s69pc7vzizyfch-cargo-audit-0.22.1/bin/cargo-audit /nix/store/zldaj03mfz9f21yiby5yymq7v8vqygd7-cargo-audit-0.22.2/bin/cargo-audit
✅ cargo-llvm-cov ✅ cargo-llvm-cov
cargo-llvm-cov 0.8.5 cargo-llvm-cov 0.9.0
/nix/store/vwjsi159n89szrx4yh5pc3jlf2gp4fld-cargo-llvm-cov-0.8.5/bin/cargo-llvm-cov /nix/store/iwpcfjah31fgn99ph32ajzz7i22j6al5-cargo-llvm-cov-0.9.0/bin/cargo-llvm-cov
✅ cargo-nextest ✅ cargo-nextest
cargo-nextest 0.9.137 cargo-nextest 0.9.146
/nix/store/qb6bcg2fjvm3r9s9j98nmffmf9xwh45s-cargo-nextest-0.9.137/bin/cargo-nextest /nix/store/p5svqr8x1rr7b1i8595pr8qafsr7s6fm-cargo-nextest-0.9.146/bin/cargo-nextest
✅ clippy-driver ✅ clippy-driver
clippy 0.1.97 (8bab26f4f6 2026-07-14) clippy 0.1.97 (8bab26f4f6 2026-07-14)
/nix/store/a6p27cg6b8szfixfyvkssx6l0c345zw8-rust-minimal-1.97.1/bin/clippy-driver /nix/store/ny64zks16ms5d70jk1qsiwsk0fr33ipp-rust-minimal-1.97.1/bin/clippy-driver
✅ rust-analyzer ✅ rust-analyzer
rust-analyzer 1.97.1 (8bab26f 2026-07-14) rust-analyzer 1.97.1 (8bab26f 2026-07-14)
/nix/store/262830dlw2517lnagfx7i7agqgl4fmsd-rust-analyzer-preview-1.97.1-aarch64-unknown-linux-gnu/bin/rust-analyzer /nix/store/d9s5skhvi1qxj940mylwym2rjicnc2kq-rust-analyzer-preview-1.97.1-aarch64-unknown-linux-gnu/bin/rust-analyzer
✅ rust-nightly ✅ rust-nightly
rustc 1.99.0-nightly (87e5904f5 2026-07-20) rustc 1.101.0-nightly (282215592 2026-10-04)
/nix/store/c59pxk1yikdlf129qwyg4fplmxcrha0k-rust-nightly/bin/rust-nightly /nix/store/rbsf1gr6f9ikv2izlyh8im117w6hs7h5-rust-nightly/bin/rust-nightly
✅ rustc ✅ rustc
rustc 1.97.1 (8bab26f4f 2026-07-14) rustc 1.97.1 (8bab26f4f 2026-07-14)
/nix/store/a6p27cg6b8szfixfyvkssx6l0c345zw8-rust-minimal-1.97.1/bin/rustc /nix/store/ny64zks16ms5d70jk1qsiwsk0fr33ipp-rust-minimal-1.97.1/bin/rustc
✅ rustfmt ✅ rustfmt
rustfmt 1.9.0-stable (8bab26f4f6 2026-07-14) rustfmt 1.9.0-stable (8bab26f4f6 2026-07-14)
/nix/store/nd8g81wv1smnvdpy4whpcyv2siwjmaan-rustfmt-preview-1.97.1-aarch64-unknown-linux-gnu/bin/rustfmt /nix/store/dplvgjikmv8909rk0dkqr90ryjg7xn0j-rustfmt-preview-1.97.1-aarch64-unknown-linux-gnu/bin/rustfmt
GCC toolchain: GCC toolchain:
✅ gcc ✅ gcc
gcc (GCC) 15.2.0 gcc (GCC) 15.3.0
/nix/store/rn6svg593xsmn8qcjzk8x9pa1i62c4kb-gcc-wrapper-15.2.0/bin/gcc /nix/store/g7z555pl99vnwif4jxa05nk1qdc33i1n-gcc-wrapper-15.3.0/bin/gcc
✅ gcc-15 ✅ gcc-15
gcc (GCC) 15.2.0 gcc (GCC) 15.3.0
/nix/store/h489d1rmjisfbxh5kmsb0a7c35j8qsdf-gcc-15/bin/gcc-15 /nix/store/vbdsfjk3j1xy5z329sl2d8vp6mq6x09i-gcc-15/bin/gcc-15
✅ g++ ✅ g++
g++ (GCC) 15.2.0 g++ (GCC) 15.3.0
/nix/store/rn6svg593xsmn8qcjzk8x9pa1i62c4kb-gcc-wrapper-15.2.0/bin/g++ /nix/store/g7z555pl99vnwif4jxa05nk1qdc33i1n-gcc-wrapper-15.3.0/bin/g++
✅ g++-15 ✅ g++-15
g++ (GCC) 15.2.0 g++ (GCC) 15.3.0
/nix/store/9ywmhz8bmzknrn3pn84g46z8hj3vrmw5-g++-15/bin/g++-15 /nix/store/9ghl998ry4cxlsg6hnq5rn2iipnlkccm-g++-15/bin/g++-15
✅ cpp ✅ cpp
cpp (GCC) 15.2.0 cpp (GCC) 15.3.0
/nix/store/rn6svg593xsmn8qcjzk8x9pa1i62c4kb-gcc-wrapper-15.2.0/bin/cpp /nix/store/g7z555pl99vnwif4jxa05nk1qdc33i1n-gcc-wrapper-15.3.0/bin/cpp
✅ cpp-15 ✅ cpp-15
cpp (GCC) 15.2.0 cpp (GCC) 15.3.0
/nix/store/vmjilh1b830qz9yh0a1jj5ads0jxizdk-cpp-15/bin/cpp-15 /nix/store/wj0mv2fv2lhglvpjzhscqpbigkvik6br-cpp-15/bin/cpp-15
✅ gcov ✅ gcov
gcov (GCC) 15.2.0 gcov (GCC) 15.3.0
/nix/store/rmwf5hpi1y2m1wpnfvlxmrhksm4djk2j-gcc-15.2.0/bin/gcov /nix/store/mszfsj00qnv9ygqcqz3w02qzxxskhvlb-gcc-15.3.0/bin/gcov
Mold: Mold:
✅ mold ✅ mold
mold 2.41.0 (compatible with GNU ld) mold 2.42.1 (compatible with GNU ld)
/nix/store/f5qh5a0bx1dslmnf5n5gx0s6aljbswq3-mold-unwrapped-wrapper-2.41.0/bin/mold /nix/store/gbq334xbibaz4gn184j7gs58m2spgwi7-mold-unwrapped-wrapper-2.42.1/bin/mold
Skipping git-over-HTTPS check (CHECK_TOOLS_SKIP_CLONE is set). Skipping git-over-HTTPS check (CHECK_TOOLS_SKIP_CLONE is set).
✅ All 53 checked tools are present and runnable. ✅ All 54 checked tools are present and runnable.
+3 -2
View File
@@ -7,7 +7,7 @@
... ...
}: }:
let let
inherit (import ./packages.nix { inherit pkgs; }) commonPackages; inherit (import ./packages.nix { inherit pkgs customGlibc; }) commonPackages;
# Each forces something absent on the other platform, so both stay lazy. # Each forces something absent on the other platform, so both stay lazy.
linux = import ./linux.nix { inherit pkgs customGlibc; }; linux = import ./linux.nix { inherit pkgs customGlibc; };
@@ -21,7 +21,8 @@ let
) )
); );
toolchain = if pkgs.stdenv.isLinux then linux.toolchain else (darwin.toolchain ++ [ darwinEnv ]); toolchain =
if pkgs.stdenv.hostPlatform.isLinux then linux.toolchain else (darwin.toolchain ++ [ darwinEnv ]);
in in
{ {
default = pkgs.buildEnv { default = pkgs.buildEnv {
+21 -18
View File
@@ -20,15 +20,19 @@ let
# Custom-glibc stdenvs, matching the CI environment. darwin has no custom # Custom-glibc stdenvs, matching the CI environment. darwin has no custom
# glibc, so there they fall back to the plain nixpkgs stdenvs. # glibc, so there they fall back to the plain nixpkgs stdenvs.
customGccStdenv = if pkgs.stdenv.isLinux then linux.gccStdenv else plainGccStdenv; customGccStdenv = if pkgs.stdenv.hostPlatform.isLinux then linux.gccStdenv else plainGccStdenv;
customClangStdenv = if pkgs.stdenv.isLinux then linux.clangStdenv else plainClangStdenv; customClangStdenv =
if pkgs.stdenv.hostPlatform.isLinux then linux.clangStdenv else plainClangStdenv;
# gcov matching each gcc shell, so `-Dcoverage=ON` builds work in the shell. # gcov matching each gcc shell, so `-Dcoverage=ON` builds work in the shell.
plainGcov = mkGcov { plainGcov = mkGcov {
name = "plain"; name = "plain";
cc = gccPackage.cc; cc = gccPackage.cc;
}; };
customGccGcov = if pkgs.stdenv.isLinux then linux.gcov else plainGcov; customGccGcov = if pkgs.stdenv.hostPlatform.isLinux then linux.gcov else plainGcov;
# commonPackages whose clang tools parse with the custom toolchain's headers.
customCommonPackages = (import ./packages.nix { inherit pkgs customGlibc; }).commonPackages;
# Whole directory: init.sh locates the profiles relative to itself. # Whole directory: init.sh locates the profiles relative to itself.
conanDir = ../conan; conanDir = ../conan;
@@ -51,7 +55,7 @@ let
# Not sdkEnv: a shell's stdenv already sets that up. Prepended so the stub # Not sdkEnv: a shell's stdenv already sets that up. Prepended so the stub
# beats the nixpkgs libresolv this shell's tooling drags in. # beats the nixpkgs libresolv this shell's tooling drags in.
darwinLibresolvHook = pkgs.lib.optionalString pkgs.stdenv.isDarwin ( darwinLibresolvHook = pkgs.lib.optionalString pkgs.stdenv.hostPlatform.isDarwin (
pkgs.lib.concatLines ( pkgs.lib.concatLines (
pkgs.lib.mapAttrsToList ( pkgs.lib.mapAttrsToList (
name: value: ''export ${name}="${value} ''${${name}:-}"'' name: value: ''export ${name}="${value} ''${${name}:-}"''
@@ -85,11 +89,11 @@ let
version ? null, version ? null,
versionedTools ? [ ], versionedTools ? [ ],
extraPackages ? [ ], extraPackages ? [ ],
warningHook ? "", # The stock nixpkgs toolchain: warn that it doesn't match CI, keep the
# Opt out of PatchNixBinary.cmake retargeting binaries to the system # clang tools off the custom toolchain, and opt out of PatchNixBinary.cmake
# loader. The plain toolchain links a newer glibc, so it must not be # retargeting binaries to the system loader (the plain toolchain links a
# patched; the custom toolchain patches by default. # newer glibc, so it must not be patched).
noPatchNixBinary ? false, plain ? false,
}: }:
let let
compilerVersionHook = compilerVersionHook =
@@ -109,7 +113,8 @@ let
in in
(pkgs.mkShell.override { inherit stdenv; }) ( (pkgs.mkShell.override { inherit stdenv; }) (
{ {
packages = commonPackages ++ versionedLinks ++ extraPackages; packages =
(if plain then commonPackages else customCommonPackages) ++ versionedLinks ++ extraPackages;
# Marks a managed dev shell, so the build (XrplSanity.cmake) can tell an # Marks a managed dev shell, so the build (XrplSanity.cmake) can tell an
# intentional Nix toolchain from one leaked into a bare shell. # intentional Nix toolchain from one leaked into a bare shell.
XRPL_DEVSHELL = shellName; XRPL_DEVSHELL = shellName;
@@ -118,15 +123,15 @@ let
${compilerVersionHook} ${compilerVersionHook}
${darwinLibresolvHook} ${darwinLibresolvHook}
${conanHook} ${conanHook}
${warningHook} ${pkgs.lib.optionalString plain plainWarningHook}
''; '';
} }
// pkgs.lib.optionalAttrs noPatchNixBinary { XRPLD_NO_PATCH_NIX_BINARY = "1"; } // pkgs.lib.optionalAttrs plain { XRPLD_NO_PATCH_NIX_BINARY = "1"; }
); );
in in
rec { rec {
# macOS: Nix Clang. Linux: Nix GCC. # macOS: Nix Clang. Linux: Nix GCC.
default = if pkgs.stdenv.isDarwin then clang else gcc; default = if pkgs.stdenv.hostPlatform.isDarwin then clang else gcc;
# gcc/clang use the custom-glibc toolchain, matching CI. On darwin there is no # gcc/clang use the custom-glibc toolchain, matching CI. On darwin there is no
# custom glibc, so they fall back to the plain nixpkgs toolchain. # custom glibc, so they fall back to the plain nixpkgs toolchain.
@@ -171,7 +176,7 @@ rec {
# The *-plain shells (stock nixpkgs toolchain) exist only on Linux: on darwin # The *-plain shells (stock nixpkgs toolchain) exist only on Linux: on darwin
# gcc/clang are already plain, so these would be redundant and are omitted, which # gcc/clang are already plain, so these would be redundant and are omitted, which
# makes `nix develop .#gcc-plain` fail there rather than silently aliasing gcc. # makes `nix develop .#gcc-plain` fail there rather than silently aliasing gcc.
// pkgs.lib.optionalAttrs pkgs.stdenv.isLinux { // pkgs.lib.optionalAttrs pkgs.stdenv.hostPlatform.isLinux {
gcc-plain = makeShell { gcc-plain = makeShell {
shellName = "gcc-plain"; shellName = "gcc-plain";
stdenv = plainGccStdenv; stdenv = plainGccStdenv;
@@ -179,8 +184,7 @@ rec {
version = gccVersion; version = gccVersion;
versionedTools = gccVersionedTools; versionedTools = gccVersionedTools;
extraPackages = [ plainGcov ]; extraPackages = [ plainGcov ];
warningHook = plainWarningHook; plain = true;
noPatchNixBinary = true;
}; };
clang-plain = makeShell { clang-plain = makeShell {
@@ -189,7 +193,6 @@ rec {
compilerName = "clang"; compilerName = "clang";
version = llvmVersion; version = llvmVersion;
versionedTools = clangVersionedTools; versionedTools = clangVersionedTools;
warningHook = plainWarningHook; plain = true;
noPatchNixBinary = true;
}; };
} }
+3 -3
View File
@@ -60,10 +60,10 @@ ENV GIT_SSL_CAINFO="/nix/ci-env/etc/ssl/certs/ca-bundle.crt"
# Externally-built dynamically-linked ELF binaries hard-code the loader path # Externally-built dynamically-linked ELF binaries hard-code the loader path
# (e.g. /lib64/ld-linux-x86-64.so.2) in their PT_INTERP header. Install it # (e.g. /lib64/ld-linux-x86-64.so.2) in their PT_INTERP header. Install it
# from the Nix store when the base image doesn't already provide one. # from the Nix store when the base image doesn't already provide one.
COPY bin/default-loader-path.sh /tmp/loader-path.sh COPY bin/nix/default-loader-path.sh /usr/local/bin/default-loader-path.sh
RUN <<EOF RUN <<EOF
target="$(/tmp/loader-path.sh)" target="$(/usr/local/bin/default-loader-path.sh)"
if [ ! -e "${target}" ]; then if [ ! -e "${target}" ]; then
# Use the loader from the same glibc that gcc links libc against, so # Use the loader from the same glibc that gcc links libc against, so
@@ -101,7 +101,7 @@ RUN if echo "${BASE_IMAGE}" | grep -qiE 'nixos'; then \
SHELL ["/bin/bash", "-e", "-o", "pipefail", "-c"] SHELL ["/bin/bash", "-e", "-o", "pipefail", "-c"]
# Sanity-check that the built binaries run correctly in the vanilla base image, with the necessary sanitizer runtime libraries installed. # Sanity-check that the built binaries run correctly in the vanilla base image, with the necessary sanitizer runtime libraries installed.
COPY bin/install-sanitizer-libs.sh /tmp/install-sanitizer-libs.sh COPY bin/install/sanitizer-libs.sh /tmp/install-sanitizer-libs.sh
COPY nix/docker/test_files/cpp/run-binaries.sh /tmp/test_files/cpp/run-binaries.sh COPY nix/docker/test_files/cpp/run-binaries.sh /tmp/test_files/cpp/run-binaries.sh
COPY nix/docker/test_files/rust/run-binaries.sh /tmp/test_files/rust/run-binaries.sh COPY nix/docker/test_files/rust/run-binaries.sh /tmp/test_files/rust/run-binaries.sh
COPY --from=final /tmp/cpp-bins /tmp/cpp-bins COPY --from=final /tmp/cpp-bins /tmp/cpp-bins
+15 -14
View File
@@ -52,10 +52,10 @@ work without `ca-certificates` being installed in the base image.
workspace with `cargo` to exercise proc-macro dylib loading. workspace with `cargo` to exercise proc-macro dylib loading.
3. **`tester`** — Start again from a clean `BASE_IMAGE` (no Nix toolchain), 3. **`tester`** — Start again from a clean `BASE_IMAGE` (no Nix toolchain),
install only the sanitizer runtime libraries install only the sanitizer runtime libraries
([`install-sanitizer-libs.sh`](./install-sanitizer-libs.sh)), and run the ([`bin/install/sanitizer-libs.sh`](../../bin/install/sanitizer-libs.sh)),
binaries compiled in `final`. This proves the binaries built with the Nix and run the binaries compiled in `final`. This proves the binaries built with
toolchain actually run on a vanilla base image. On `nixos/nix` this step is the Nix toolchain actually run on a vanilla base image. On `nixos/nix` this
skipped (the binaries are patched for a conventional FHS loader). step is skipped (the binaries are patched for a conventional FHS loader).
4. **Output** — The final image is gated on the tester succeeding: it copies a 4. **Output** — The final image is gated on the tester succeeding: it copies a
sentinel file out of `tester`, so a failed test run fails the whole build. sentinel file out of `tester`, so a failed test run fails the whole build.
@@ -75,9 +75,10 @@ toolchain being present at runtime. Two pieces make that work:
- **An expected dynamic linker in the image.** - **An expected dynamic linker in the image.**
Binaries built in Nix environments reference a dynamic linker from Nix store paths, which won't be present in the base image. However, Binaries built in Nix environments reference a dynamic linker from Nix store paths, which won't be present in the base image. However,
[`bin/default-loader-path.sh`](../../bin/default-loader-path.sh) reports the [`bin/nix/default-loader-path.sh`](../../bin/nix/default-loader-path.sh) reports the
expected loader path for the current architecture, so we can patch the binaries expected loader path for the current architecture, so we can patch the binaries
to use the correct loader. to use the correct loader. The image ships it as
`/usr/local/bin/default-loader-path.sh`.
The build then verifies all of this end to end, and the C++ and Rust programs The build then verifies all of this end to end, and the C++ and Rust programs
go through the same pipeline: each is compiled in `final`, has its `PT_INTERP` go through the same pipeline: each is compiled in `final`, has its `PT_INTERP`
@@ -91,11 +92,11 @@ whose resulting binary is patched and run like the others.
## Files ## Files
| File | Purpose | | File | Purpose |
| ----------------------------------------------------------------------- | ------------------------------------------------------------------------------------ | | ------------------------------------------------------------------------- | ------------------------------------------------------------------------------------ |
| [`./Dockerfile`](./Dockerfile) | Multi-stage build described above. | | [`./Dockerfile`](./Dockerfile) | Multi-stage build described above. |
| [`./test_files/cpp/`](./test_files/cpp) | C++ sanitizer smoke test: sources + compile/run scripts. | | [`./test_files/cpp/`](./test_files/cpp) | C++ sanitizer smoke test: sources + compile/run scripts. |
| [`./test_files/rust/`](./test_files/rust) | Rust smoke test: rustc sources + a cargo proc-macro workspace + compile/run scripts. | | [`./test_files/rust/`](./test_files/rust) | Rust smoke test: rustc sources + a cargo proc-macro workspace + compile/run scripts. |
| [`/bin/check-tools.sh`](../../bin/check-tools.sh) | Verify every expected tools are present and runnable. | | [`/bin/check-tools.sh`](../../bin/check-tools.sh) | Verify every expected tools are present and runnable. |
| [`/bin/default-loader-path.sh`](../../bin/default-loader-path.sh) | Print the dynamic-linker (`PT_INTERP`) path for the current architecture. | | [`/bin/nix/default-loader-path.sh`](../../bin/nix/default-loader-path.sh) | Print the dynamic-linker (`PT_INTERP`) path for the current architecture. |
| [`/bin/install-sanitizer-libs.sh`](../../bin/install-sanitizer-libs.sh) | Install `libasan`/`libtsan`/`libubsan` runtimes on the supported base images. | | [`/bin/install/sanitizer-libs.sh`](../../bin/install/sanitizer-libs.sh) | Install `libasan`/`libtsan`/`libubsan` runtimes on the supported base images. |
+1 -1
View File
@@ -8,7 +8,7 @@ set -eo pipefail
src_dir="${1:?usage: $0 <src_dir> <dst_dir>}" src_dir="${1:?usage: $0 <src_dir> <dst_dir>}"
dst_dir="${2:?usage: $0 <src_dir> <dst_dir>}" dst_dir="${2:?usage: $0 <src_dir> <dst_dir>}"
loader="$(/tmp/loader-path.sh)" loader="$(/usr/local/bin/default-loader-path.sh)"
mkdir -p "${dst_dir}" mkdir -p "${dst_dir}"
Loaded 100 of 419 files, more files were not shown because too many files have changed in this diff. Show more