Skip to content

Commit c1a12a6

Browse files
committed
Merge remote-tracking branch 'origin/main' into rust_libc_api_support
2 parents 5d4347e + 80bdcd9 commit c1a12a6

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

80 files changed

+3014
-3041
lines changed

Diff for: .github/workflows/main.yml

+82-26
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,11 @@
11
name: snmalloc CI
22

3+
# The following should ensure that the workflow only runs a single set of actions
4+
# for each PR. But it will not apply this to pushes to the main branch.
5+
concurrency:
6+
group: ${{ github.ref }}
7+
cancel-in-progress: ${{ github.ref != 'refs/heads/main' }}
8+
39
# Controls when the workflow will run
410
on:
511
# Triggers the workflow on push or pull request events but only for the master branch
@@ -16,7 +22,7 @@ jobs:
1622
strategy:
1723
matrix:
1824
# Build each combination of OS and release/debug variants
19-
os: [ "ubuntu-latest", "ubuntu-20.04" ]
25+
os: [ "ubuntu-24.04", "ubuntu-22.04", "ubuntu-20.04", "ubuntu-24.04-arm" ]
2026
build-type: [ "Release", "Debug" ]
2127
# Extra cmake flags. GitHub Actions matrix overloads `include` to mean
2228
# 'add extra things to a job' and 'add jobs'. You can add extra things
@@ -33,30 +39,34 @@ jobs:
3339
extra-cmake-flags: [ "" ]
3440
# Modify the complete matrix
3541
include:
42+
- os: "ubuntu-22.04"
43+
variant: "C++17"
44+
build-type: "Debug"
45+
extra-cmake-flags: "-DSNMALLOC_USE_CXX17=ON"
3646
- os: "ubuntu-20.04"
3747
variant: "C++17"
3848
build-type: "Debug"
3949
extra-cmake-flags: "-DSNMALLOC_USE_CXX17=ON"
4050
# Add the self-host build, using the bounds-checked memcpy in
4151
# maximally paranoid mode (checking loads and stores)
42-
- os: "ubuntu-latest"
52+
- os: "ubuntu-24.04"
4353
build-type: Debug
4454
self-host: true
4555
extra-cmake-flags: "-DSNMALLOC_MEMCPY_BOUNDS=ON -DSNMALLOC_CHECK_LOADS=ON"
4656
# Extra build to check using pthread library for destructing local state.
47-
- os: "ubuntu-latest"
57+
- os: "ubuntu-24.04"
4858
variant: "with pthread destructors"
4959
build-type: Debug
5060
self-host: true
5161
extra-cmake-flags: "-DSNMALLOC_USE_PTHREAD_DESTRUCTORS=On"
5262
# Extra build to check using individual mitigations works.
53-
- os: "ubuntu-latest"
63+
- os: "ubuntu-24.04"
5464
variant: "individual mitigations"
5565
build-type: Release
5666
self-host: true
5767
extra-cmake-flags: "-DSNMALLOC_BENCHMARK_INDIVIDUAL_MITIGATIONS=On -DSNMALLOC_BUILD_TESTING=Off"
5868
# Check that we can build specifically with libstdc++
59-
- os: "ubuntu-latest"
69+
- os: "ubuntu-24.04"
6070
variant: "libstdc++ (Build only)"
6171
build-type: Release
6272
extra-cmake-flags: "-DCMAKE_CXX_COMPILER=clang++ -DCMAKE_CXX_FLAGS=-stdlib=libstdc++"
@@ -80,7 +90,7 @@ jobs:
8090
# Don't abort runners if a single one fails
8191
fail-fast: false
8292
runs-on: ${{ matrix.os }}
83-
name: ${{ matrix.os }} ${{ matrix.build-type }} ${{ matrix.variant }}
93+
name: Ubuntu - ${{ matrix.os }} ${{ matrix.build-type }} ${{ matrix.variant }}
8494
steps:
8595
- uses: actions/checkout@v4
8696
- name: Install build dependencies
@@ -116,7 +126,7 @@ jobs:
116126
extra-cmake-flags: [ "", "-DSNMALLOC_USE_CXX17=ON" ]
117127
fail-fast: false
118128
runs-on: ${{ matrix.os }}
119-
name: ${{ matrix.os }} ${{ matrix.build-type }} ${{ matrix.extra-cmake-flags }}
129+
name: Mac OS ${{ matrix.os }} ${{ matrix.build-type }} ${{ matrix.extra-cmake-flags }}
120130
steps:
121131
- uses: actions/checkout@v4
122132
- name: Install build dependencies
@@ -255,21 +265,20 @@ jobs:
255265
matrix:
256266
# Build just release variant as Debug is too slow.
257267
build-type: [ Release ]
258-
os: ["ubuntu-latest", "ubuntu-20.04"]
268+
os: ["ubuntu-24.04", "ubuntu-22.04"]
259269
include:
260-
- os: "ubuntu-latest"
270+
- os: "ubuntu-22.04"
261271
variant: "libc++ (TSan + UBSan)"
262272
dependencies: "sudo apt install ninja-build libc++-dev"
263273
extra-cmake-flags: "-DCMAKE_CXX_COMPILER=clang++ -DCMAKE_CXX_FLAGS=-stdlib=\"libc++ -g\" -DSNMALLOC_SANITIZER=undefined,thread"
264-
# Also test specifically with clang-10 (on ubuntu-20.04)
265-
- os: "ubuntu-20.04"
266-
variant: "clang-10 libc++ (TSan + UBSan)"
274+
- os: "ubuntu-24.04"
275+
variant: "libc++ (TSan + UBSan)"
267276
dependencies: "sudo apt install ninja-build libc++-dev"
268-
extra-cmake-flags: "-DCMAKE_CXX_COMPILER=clang++-10 -DCMAKE_CXX_FLAGS=-stdlib=\"libc++ -g\" -DSNMALLOC_SANITIZER=undefined,thread"
277+
extra-cmake-flags: "-DCMAKE_CXX_COMPILER=clang++ -DCMAKE_CXX_FLAGS=-stdlib=\"libc++ -g\" -DSNMALLOC_SANITIZER=undefined,thread"
269278
# Don't abort runners if a single one fails
270279
fail-fast: false
271280
runs-on: ${{ matrix.os }}
272-
name: ${{ matrix.os }} ${{ matrix.build-type }} ${{ matrix.variant }}
281+
name: Sanitizer - ${{ matrix.os }} ${{ matrix.build-type }} ${{ matrix.variant }}
273282
steps:
274283
- uses: actions/checkout@v4
275284
- name: Install build dependencies
@@ -294,13 +303,13 @@ jobs:
294303
triple: arm-linux-gnueabihf
295304
rtld: ld-linux-armhf.so.3
296305
ld-flavour: lld
297-
host-os: ubuntu-latest
306+
host-os: ubuntu-24.04
298307
- name: arm64
299308
system-processor: aarch64
300309
triple: aarch64-linux-gnu
301310
rtld: ld-linux-aarch64.so.1
302311
ld-flavour: lld
303-
host-os: ubuntu-latest
312+
host-os: ubuntu-24.04
304313
- name: ppc64el
305314
system-processor: powerpc64le
306315
triple: powerpc64le-linux-gnu
@@ -315,11 +324,11 @@ jobs:
315324
extra-packages: binutils-riscv64-linux-gnu
316325
ld-flavour: bfd
317326
ld: /usr/bin/riscv64-linux-gnu-ld.bfd
318-
host-os: ubuntu-latest
327+
host-os: ubuntu-24.04
319328
# Don't abort runners if a single one fails
320329
fail-fast: false
321330
runs-on: ${{matrix.arch.host-os}}
322-
name: ${{matrix.build-type}} cross-build for ${{ matrix.arch.triple }}
331+
name: Crossbuild - ${{matrix.build-type}} cross-build for ${{ matrix.arch.triple }}
323332
steps:
324333
- uses: actions/checkout@v4
325334
- name: "Install cross-compile toolchain and QEMU (ubuntu-20.04)"
@@ -332,8 +341,8 @@ jobs:
332341
sudo apt update
333342
sudo apt install libstdc++-9-dev-${{ matrix.arch.name }}-cross qemu-user ninja-build clang-13 lld-13
334343
sudo apt install ${{matrix.arch.extra-packages}}
335-
- name: "Install cross-compile toolchain and QEMU (ubuntu-latest)"
336-
if: matrix.arch.host-os == 'ubuntu-latest'
344+
- name: "Install cross-compile toolchain and QEMU (ubuntu-24.04)"
345+
if: matrix.arch.host-os == 'ubuntu-24.04'
337346
run: |
338347
sudo apt update
339348
sudo apt install libstdc++-12-dev-${{ matrix.arch.name }}-cross qemu-user ninja-build
@@ -350,7 +359,7 @@ jobs:
350359
chmod +x ppc64.sh
351360
- name: Configure
352361
env:
353-
SNMALLOC_CI_CLANG_VERSION: ${{ (matrix.arch.host-os == 'ubuntu-latest') && 16 || 13 }}
362+
SNMALLOC_CI_CLANG_VERSION: ${{ (matrix.arch.host-os == 'ubuntu-24.04') && 16 || 13 }}
354363
RTLD_NAME: ${{ matrix.arch.rtld }}
355364
ARCH: ${{ matrix.arch.system-processor }}
356365
TRIPLE: ${{ matrix.arch.triple}}
@@ -384,7 +393,7 @@ jobs:
384393
strategy:
385394
matrix:
386395
# Build each combination of OS and release/debug variants
387-
os: [ windows-2019 ]
396+
os: [ windows-2019, windows-2022, windows-2025 ]
388397
build-type: [ Release, Debug ]
389398
arch: [ Win32, x64 ]
390399
toolchain: [ "", "-T ClangCL" ]
@@ -439,7 +448,7 @@ jobs:
439448
# Don't abort runners if a single one fails
440449
fail-fast: false
441450
runs-on: ${{ matrix.os }}
442-
name: ${{ matrix.os }} ${{ matrix.arch }} ${{ matrix.build-type }} ${{ matrix.toolchain }} ${{ matrix.variant }}
451+
name: Windows - ${{ matrix.os }} ${{ matrix.arch }} ${{ matrix.build-type }} ${{ matrix.toolchain }} ${{ matrix.variant }}
443452
steps:
444453
- uses: actions/checkout@v4
445454
- name: Configure CMake
@@ -459,6 +468,7 @@ jobs:
459468
# Job to run clang-format and report errors
460469
format:
461470
runs-on: ubuntu-22.04
471+
name: Format check
462472
# We don't need to do the build for this job, but we need to configure it to get the clang-format target
463473
steps:
464474
- uses: actions/checkout@v4
@@ -484,6 +494,7 @@ jobs:
484494
fi
485495
486496
fuzzing:
497+
name: Fuzzing
487498
runs-on: ubuntu-24.04
488499
steps:
489500
- uses: actions/checkout@v4
@@ -495,7 +506,6 @@ jobs:
495506
run: ${{github.workspace}}/build/fuzzing/snmalloc-fuzzer
496507

497508
self-vendored:
498-
name: Self Vendored STL Functionality
499509
strategy:
500510
fail-fast: false
501511
matrix:
@@ -513,6 +523,7 @@ jobs:
513523
cxx: clang++
514524
cc: clang
515525
runs-on: ${{ matrix.os }}
526+
name: Self Vendored STL - ${{ matrix.os }} ${{ matrix.cxx }}
516527
steps:
517528
- uses: actions/checkout@v4
518529
- name: Prepare Windows
@@ -542,12 +553,57 @@ jobs:
542553
run: |
543554
cd ${{github.workspace}}/build
544555
ctest --parallel
545-
556+
557+
gwp-asan:
558+
strategy:
559+
fail-fast: false
560+
matrix:
561+
os: [ubuntu-24.04, ubuntu-24.04-arm]
562+
profile: [RelWithDebInfo, Debug]
563+
runs-on: ${{ matrix.os }}
564+
steps:
565+
- uses: actions/checkout@v4
566+
- name: Install Ninja
567+
run: |
568+
sudo apt-get install -y ninja-build
569+
- name: Install Compiler-RT
570+
shell: bash
571+
run: |
572+
cd ..
573+
git clone https://github.com/llvm/llvm-project --depth=1 -b llvmorg-19.1.7
574+
mkdir compiler-rt
575+
cmake -G Ninja \
576+
-S llvm-project/runtimes \
577+
-B llvm-project/build \
578+
-DCMAKE_BUILD_TYPE=${{ matrix.profile }}\
579+
-DLLVM_ENABLE_RUNTIMES=compiler-rt \
580+
-DCMAKE_CXX_COMPILER=clang++-18 \
581+
-DCMAKE_C_COMPILER=clang-18 \
582+
-DCMAKE_INSTALL_PREFIX=$(realpath compiler-rt)
583+
cmake --build llvm-project/build --parallel
584+
cmake --build llvm-project/build --target=install
585+
- name: Configure SnMalloc
586+
run: >
587+
cmake -GNinja
588+
-B${{github.workspace}}/build
589+
-DCMAKE_BUILD_TYPE=${{ matrix.profile }}
590+
-DCMAKE_CXX_COMPILER=clang++-18
591+
-DCMAKE_C_COMPILER=clang-18
592+
-DSNMALLOC_ENABLE_GWP_ASAN_INTEGRATION=On
593+
-DSNMALLOC_GWP_ASAN_INCLUDE_PATH=${{github.workspace}}/../llvm-project/compiler-rt/lib
594+
-DSNMALLOC_GWP_ASAN_LIBRARY_PATH=${{github.workspace}}/../compiler-rt/lib/linux
595+
- name: Build
596+
run: cmake --build ${{github.workspace}}/build --parallel
597+
- name: Test
598+
run: |
599+
cd ${{github.workspace}}/build
600+
ctest --parallel --output-on-failure
601+
546602
all-checks:
547603
# Currently FreeBSD and NetBSD CI are not working, so we do not require them to pass.
548604
# Add fuzzing back when the memove issue is fixed.
549605
needs: [ubuntu, macos, freebsd, netbsd, sanitizer, qemu-crossbuild, windows, format]
550-
runs-on: ubuntu-latest
606+
runs-on: ubuntu-24.04
551607
steps:
552608
- name: Dummy step
553609
run: true

Diff for: CMakeLists.txt

+35-14
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,12 @@ cmake_dependent_option(SNMALLOC_STATIC_LIBRARY "Build static libraries" ON "NOT
3737
cmake_dependent_option(SNMALLOC_CHECK_LOADS "Perform bounds checks on the source argument to memcpy with heap objects" OFF "NOT SNMALLOC_HEADER_ONLY_LIBRARY" OFF)
3838
cmake_dependent_option(SNMALLOC_OPTIMISE_FOR_CURRENT_MACHINE "Compile for current machine architecture" Off "NOT SNMALLOC_HEADER_ONLY_LIBRARY" OFF)
3939
cmake_dependent_option(SNMALLOC_PAGEID "Set an id to memory regions" OFF "NOT SNMALLOC_PAGEID" OFF)
40+
41+
# GwpAsan secondary allocator
42+
option(SNMALLOC_ENABLE_GWP_ASAN_INTEGRATION "Enable GwpAsan as a secondary allocator" OFF)
43+
set(SNMALLOC_GWP_ASAN_INCLUDE_PATH "" CACHE PATH "GwpAsan header directory")
44+
set(SNMALLOC_GWP_ASAN_LIBRARY_PATH "" CACHE PATH "GwpAsan library directory")
45+
4046
if (NOT SNMALLOC_HEADER_ONLY_LIBRARY)
4147
# Pick a sensible default for the thread cleanup mechanism
4248
if (${CMAKE_SYSTEM_NAME} STREQUAL FreeBSD)
@@ -115,6 +121,19 @@ int main()
115121
SNMALLOC_LINKER_SUPPORT_NOSTDLIBXX)
116122
set(CMAKE_REQUIRED_LINK_OPTIONS "")
117123

124+
# Detect if pthread_atfork works
125+
CHECK_CXX_SOURCE_COMPILES("
126+
#include <pthread.h>
127+
void prepare() {}
128+
void parent() {}
129+
void child() {}
130+
int main() {
131+
pthread_atfork(prepare, parent, child);
132+
return 0;
133+
}
134+
" SNMALLOC_PTHREAD_ATFORK_WORKS)
135+
136+
118137
if (NOT MSVC AND NOT (SNMALLOC_CLEANUP STREQUAL CXX11_DESTRUCTORS))
119138
# If the target compiler doesn't support -nostdlib++ then we must enable C at
120139
# the global scope for the fallbacks to work.
@@ -242,6 +261,20 @@ if(SNMALLOC_USE_SELF_VENDORED_STL)
242261
target_compile_definitions(snmalloc INTERFACE SNMALLOC_USE_SELF_VENDORED_STL)
243262
endif()
244263

264+
if (SNMALLOC_ENABLE_GWP_ASAN_INTEGRATION)
265+
if (NOT EXISTS ${SNMALLOC_GWP_ASAN_INCLUDE_PATH})
266+
message(FATAL_ERROR "GwpAsan cannot be enabled without setting SNMALLOC_GWP_ASAN_INCLUDE_PATH")
267+
endif()
268+
if (NOT EXISTS ${SNMALLOC_GWP_ASAN_LIBRARY_PATH})
269+
message(FATAL_ERROR "GwpAsan cannot be enabled without setting SNMALLOC_GWP_ASAN_LIBRARY_PATH")
270+
endif()
271+
message(STATUS "GwpAsan is enabled: ${SNMALLOC_GWP_ASAN_LIBRARY_PATH}/libclang_rt.gwp_asan-${CMAKE_SYSTEM_PROCESSOR}.a")
272+
target_include_directories(snmalloc INTERFACE ${SNMALLOC_GWP_ASAN_INCLUDE_PATH})
273+
target_link_directories(snmalloc INTERFACE ${SNMALLOC_GWP_ASAN_LIBRARY_PATH})
274+
target_compile_definitions(snmalloc INTERFACE -DSNMALLOC_ENABLE_GWP_ASAN_INTEGRATION)
275+
target_link_libraries(snmalloc INTERFACE clang_rt.gwp_asan-${CMAKE_SYSTEM_PROCESSOR})
276+
endif()
277+
245278
# https://learn.microsoft.com/en-us/cpp/build/reference/zc-cplusplus
246279
if(MSVC)
247280
target_compile_options(snmalloc INTERFACE "/Zc:__cplusplus")
@@ -301,6 +334,7 @@ add_as_define(SNMALLOC_QEMU_WORKAROUND)
301334
add_as_define(SNMALLOC_TRACING)
302335
add_as_define(SNMALLOC_CI_BUILD)
303336
add_as_define(SNMALLOC_PLATFORM_HAS_GETENTROPY)
337+
add_as_define(SNMALLOC_PTHREAD_ATFORK_WORKS)
304338
add_as_define(SNMALLOC_HAS_LINUX_RANDOM_H)
305339
add_as_define(SNMALLOC_HAS_LINUX_FUTEX_H)
306340
if (SNMALLOC_NO_REALLOCARRAY)
@@ -559,22 +593,9 @@ endif()
559593
endif()
560594

561595
if (SNMALLOC_BUILD_TESTING)
562-
if (WIN32
563-
OR (CMAKE_SYSTEM_NAME STREQUAL NetBSD)
564-
OR (CMAKE_SYSTEM_NAME STREQUAL OpenBSD)
565-
OR (CMAKE_SYSTEM_NAME STREQUAL SunOS))
566-
# Windows does not support aligned allocation well enough
567-
# for pass through.
568-
# NetBSD, OpenBSD and DragonFlyBSD do not support malloc*size calls.
569-
set(FLAVOURS fast;check)
570-
else()
571-
set(FLAVOURS fast;check;malloc)
572-
endif()
596+
set(FLAVOURS fast;check)
573597

574598
foreach(FLAVOUR ${FLAVOURS})
575-
if (${FLAVOUR} STREQUAL "malloc")
576-
set(DEFINES SNMALLOC_PASS_THROUGH)
577-
endif()
578599
if (${FLAVOUR} STREQUAL "check")
579600
set(DEFINES SNMALLOC_CHECK_CLIENT)
580601
endif()

Diff for: docs/AddressSpace.md

+3-3
Original file line numberDiff line numberDiff line change
@@ -16,10 +16,10 @@ For simplicity, we assume that
1616
Since this is the first allocation, all the internal caches will be empty, and so we will hit all the slow paths.
1717
For simplicity, we gloss over much of the "lazy initialization" that would actually be implied by a first allocation.
1818

19-
1. The `LocalAlloc::small_alloc` finds that it cannot satisfy the request because its `LocalCache` lacks a free list for this size class.
20-
The request is delegated, unchanged, to `CoreAllocator::small_alloc`.
19+
1. The `Allocator::small_alloc` finds that it cannot satisfy the request because its lacks a fast free list for this size class.
20+
The request is delegated, unchanged, to `Allocator::small_refill`.
2121

22-
2. The `CoreAllocator` has no active slab for this sizeclass, so `CoreAllocator::small_alloc_slow` delegates to `BackendAllocator::alloc_chunk`.
22+
2. The `Allocator` has no active slab for this sizeclass, so `Allocator::small_refill_slow` delegates to `BackendAllocator::alloc_chunk`.
2323
At this point, the allocation request is enlarged to one or a few chunks (a small counting number multiple of `MIN_CHUNK_SIZE`, which is typically 16KiB); see `sizeclass_to_slab_size`.
2424

2525
3. `BackendAllocator::alloc_chunk` at this point splits the allocation request in two, allocating both the chunk's metadata structure (of size `PAGEMAP_METADATA_STRUCT_SIZE`) and the chunk itself (a multiple of `MIN_CHUNK_SIZE`).

Diff for: docs/release/0.7/README.md

+3-3
Original file line numberDiff line numberDiff line change
@@ -109,10 +109,10 @@ The additional meta-data size in snmalloc 0.6 was fixed and under a cache line i
109109
In snmalloc 0.7, we have made this meta-data size configurable.
110110
This allows developers to build new security features on top of snmalloc.
111111

112-
For instance, building snmalloc with the following definition of `Alloc` will allow you to store a 64-bit counter for each allocation:
112+
For instance, building snmalloc with the following definition of `Config` will allow you to store a 64-bit counter for each allocation:
113113
```cpp
114-
using Alloc = snmalloc::LocalAllocator<snmalloc::StandardConfigClientMeta<
115-
ArrayClientMetaDataProvider<std::atomic<size_t>>>>;
114+
using Config = snmalloc::StandardConfigClientMeta<
115+
ArrayClientMetaDataProvider<std::atomic<size_t>>>;
116116
```
117117

118118
This does not affect the underlying alignment of the allocations.

Diff for: fuzzing/snmalloc-fuzzer.cpp

+1-1
Original file line numberDiff line numberDiff line change
@@ -148,7 +148,7 @@ struct Result
148148
{
149149
auto alloc = snmalloc::get_scoped_allocator();
150150
if (ptr)
151-
alloc->dealloc(ptr, size);
151+
alloc->dealloc(ptr);
152152
ptr = nullptr;
153153
}
154154
};

Diff for: src/snmalloc/README.md

+1-1
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ These are arranged in a hierarchy such that each of the directories may include
2020
This includes data structures such as pagemap implementations (efficient maps from a chunk address to associated metadata) and buddy allocators for managing address-space ranges.
2121
- `backend/` provides some example implementations for snmalloc embeddings that provide a global memory allocator for an address space.
2222
Users may ignore this entirely and use the types in `mem/` with a custom back end to expose an snmalloc instance with specific behaviour.
23-
Layers above this can be used with a custom configuration by defining `SNMALLOC_PROVIDE_OWN_CONFIG` and exporting a type as `snmalloc::Alloc` that defines the type of an `snmalloc::LocalAllocator` template specialisation.
23+
Layers above this can be used with a custom configuration by defining `SNMALLOC_PROVIDE_OWN_CONFIG` and exporting a type as `snmalloc::Config` that defines the configuration.
2424
- `global/` provides some front-end components that assume that snmalloc is available in a global configuration.
2525
- `override/` builds on top of `global/` to provide specific implementations with compatibility with external specifications (for example C `malloc`, C++ `operator new`, jemalloc's `*allocx`, or Rust's `std::alloc`).
2626

0 commit comments

Comments
 (0)