Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
58 commits
Select commit Hold shift + click to select a range
2ffa22d
feat: Implement the GPU Info gathering within the Native SDK
mujacica Aug 11, 2025
792c1af
Fix file format
mujacica Aug 11, 2025
ae6c5f6
Add changelog entry
mujacica Aug 11, 2025
a1fa547
Extend README with new SENTRY_WITH_GPU_INFO option
mujacica Aug 11, 2025
1d7de99
Skip apple silicon tests on non darwin platforms
mujacica Aug 11, 2025
2c2bd6d
Enable GPU Info per default to test cmake on github runners
mujacica Aug 11, 2025
e98bfb3
Resolve compiler issues on Linux
mujacica Aug 11, 2025
52d8c44
Fix Windows builds
mujacica Aug 11, 2025
1aeb0f2
Fix failing tests
mujacica Aug 11, 2025
bf248f3
Fix IOS builds
mujacica Aug 11, 2025
5620eac
Fix remaining failing tests
mujacica Aug 11, 2025
63d8620
Fix format
mujacica Aug 11, 2025
0bfff8a
Keep GPU Info disabled by default
mujacica Aug 11, 2025
3df5f64
Fix CMake for all platforms
mujacica Aug 11, 2025
42e6b81
Fix comments, and findings from testing
mujacica Aug 12, 2025
f22b5cb
Further testing fixes
mujacica Aug 12, 2025
3b8e940
Fix failing test
mujacica Aug 12, 2025
0771c62
Use Sentry wstr function instead of custom implementation
mujacica Aug 12, 2025
958f720
Simplify Unix implementation and CMakeLists
mujacica Aug 14, 2025
ed42e48
Add nvml support, add multi-gpu support
mujacica Aug 14, 2025
3eecedf
Fix linux complier warnings
mujacica Aug 14, 2025
eab9dbb
Fix file formats
mujacica Aug 14, 2025
ce7deb1
Fix build issues after refactoring
mujacica Aug 14, 2025
635b3d5
Fix file formats
mujacica Aug 14, 2025
abcf048
Use Vulkan for GPU info with multi-platform support
mujacica Aug 17, 2025
19a588c
Fix file format
mujacica Aug 17, 2025
19da153
Fix None implementation
mujacica Aug 17, 2025
7da6373
Don't use singleton
mujacica Aug 17, 2025
9713125
Fix format
mujacica Aug 17, 2025
ca4f058
Simplify driver version, remove test script
mujacica Aug 20, 2025
7b4eceb
Use Vulkan headers, dynamically load
mujacica Aug 20, 2025
57d11e5
Fix format
mujacica Aug 20, 2025
553cd55
Fix CMake to include headers only
mujacica Aug 20, 2025
a5f5d88
Fix 32-bit builds
mujacica Aug 20, 2025
d3e5fd9
Fix GPU test pritnf formats
mujacica Aug 20, 2025
408b3c7
Fix format
mujacica Aug 20, 2025
072b03a
One more test fix
mujacica Aug 20, 2025
8b81b22
Fix format
mujacica Aug 20, 2025
1ded02e
Fix cursor comment
mujacica Oct 2, 2025
61d288a
Update src/gpu/sentry_gpu_vulkan.c
mujacica Oct 9, 2025
2a1efb9
Update src/gpu/sentry_gpu_vulkan.c
mujacica Oct 9, 2025
2452945
Update tests/unit/test_gpu.c
mujacica Oct 9, 2025
f05f610
Update README.md
mujacica Oct 9, 2025
2aef893
Fix PR Comments
mujacica Oct 9, 2025
fb3a571
Update tests/unit/test_gpu.c
mujacica Oct 9, 2025
239aa5b
Further fixes
mujacica Oct 9, 2025
0f26974
Fix memory units
mujacica Oct 9, 2025
427ee77
Fix docs
mujacica Oct 9, 2025
25adf1d
Fix more comments
mujacica Oct 9, 2025
64fcd67
Fix Mac compatibility
mujacica Oct 9, 2025
9bc68f3
Fix Vendor ID's
mujacica Oct 13, 2025
9053706
Fix memory size to MB
mujacica Oct 13, 2025
f86dae5
Fix CHANGELOG
mujacica Feb 11, 2026
3e996d9
Fix review findings: harden GPU info, disable by default
mujacica Mar 19, 2026
1a0dc3a
Move GPU changelog entry to Unreleased section
mujacica Mar 19, 2026
1021456
Fix VK_INCOMPLETE handling, GPU context key gaps, and formatting
mujacica Mar 19, 2026
1b64cf0
fix(gpu): reset function pointers on partial Vulkan load failure
mujacica Mar 19, 2026
5d328bc
fix(gpu): add forward declaration for unload_vulkan_library
mujacica Mar 19, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -251,7 +251,7 @@ jobs:
run: |
sudo apt update
# Install common dependencies
sudo apt install cmake llvm valgrind zlib1g-dev libcurl4-openssl-dev
sudo apt install cmake llvm valgrind zlib1g-dev libcurl4-openssl-dev libvulkan-dev
# For GCC, install both gcc-X and g++-X. For Clang, only install clang-X (includes C++ compiler)
if [[ "$CC" == gcc-* ]]; then
sudo apt install "${CC}" "${CXX}"
Expand Down
3 changes: 3 additions & 0 deletions .gitmodules
Original file line number Diff line number Diff line change
Expand Up @@ -14,3 +14,6 @@
[submodule "external/benchmark"]
path = external/benchmark
url = https://github.com/google/benchmark.git
[submodule "external/vulkan-headers"]
path = external/vulkan-headers
url = https://github.com/KhronosGroup/Vulkan-Headers.git
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,10 @@

## Unreleased:

**Features**:

- Implement GPU info context gathering for the Native SDK. Supported on Windows, macOS, and Linux via Vulkan. Disabled by default — enable with `-DSENTRY_WITH_GPU_INFO=ON`. ([#1336](https://github.com/getsentry/sentry-native/pull/1336))

**Fixes**:

- inproc: only the handling thread cleans up after the crash. ([#1579](https://github.com/getsentry/sentry-native/pull/1579))
Expand Down
13 changes: 13 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,13 @@ option(SENTRY_PIC "Build sentry (and dependent) libraries as position independen

option(SENTRY_TRANSPORT_COMPRESSION "Enable transport gzip compression" OFF)

option(SENTRY_WITH_GPU_INFO "Build with GPU information gathering support (supported on Windows, macOS, Linux)" OFF)

# GPU info enabled - no longer requires Vulkan SDK (uses headers submodule + dynamic linking)
if(SENTRY_WITH_GPU_INFO)
message(STATUS "GPU information gathering enabled (using vulkan-headers submodule)")
endif()

option(SENTRY_BUILD_TESTS "Build sentry-native tests" "${SENTRY_MAIN_PROJECT}")
option(SENTRY_BUILD_EXAMPLES "Build sentry-native example(s)" "${SENTRY_MAIN_PROJECT}")
option(SENTRY_BUILD_BENCHMARKS "Build sentry-native benchmarks" OFF)
Expand Down Expand Up @@ -605,6 +612,12 @@ if(NOT XBOX)
endif()
endif()

# handle Vulkan headers for GPU info
if(SENTRY_WITH_GPU_INFO)
target_include_directories(sentry PRIVATE
"$<BUILD_INTERFACE:${PROJECT_SOURCE_DIR}/external/vulkan-headers/include>")
endif()

# apply platform libraries to sentry library
target_link_libraries(sentry PRIVATE ${_SENTRY_PLATFORM_LIBS})

Expand Down
13 changes: 9 additions & 4 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -184,7 +184,7 @@ The example currently supports the following commands:
- `discarding-before-transaction`: Installs a `before_transaction()` callback that discards the transaction.
- `traces-sampler`: Installs a traces sampler callback function when used alongside `capture-transaction`.
- `attach-view-hierarchy`: Adds a `view-hierarchy.json` attachment file, giving it the proper `attachment_type` and `content_type`.
This file can be found in `./tests/fixtures/view-hierachy.json`.
This file can be found in `./tests/fixtures/view-hierachy.json`.
- `set-trace`: Sets the scope `propagation_context`'s trace data to the given `trace_id="aaaabbbbccccddddeeeeffff00001111"` and `parent_span_id=""f0f0f0f0f0f0f0f0"`.
- `capture-with-scope`: Captures an event with a local scope.
- `attach-to-scope`: Same as `attachment` but attaches the file to the local scope.
Expand All @@ -196,6 +196,7 @@ The example currently supports the following commands:
- `test-logger-before-crash`: Outputs marker directly using printf for test parsing before crash.

Only on Linux using crashpad:

- `crashpad-wait-for-upload`: Couples application shutdown to complete the upload in the `crashpad_handler`.

Only on Windows using crashpad with its WER handler module:
Expand All @@ -218,15 +219,15 @@ invoked directly.

## Handling locks

There are a couple of rules based on the current usage of mutexes in the Native SDK that should always be
There are a couple of rules based on the current usage of mutexes in the Native SDK that should always be
applied in order not to have to fight boring concurrency bugs:

* we use recursive mutexes throughout the code-base
* these primarily allow us to call public interfaces from internal code instead of having a layer in-between
* but they come at the risk of less clarity whether a lock release still leaves a live lock
* but they come at the risk of less clarity whether a lock release still leaves a live lock
* they should not be considered as convenience:
* reduce the amount of recursive locking to an absolute minimum
* instead of retrieval via global locks, pass shared state like `options` or `scope` around in internal helpers
* instead of retrieval via global locks, pass shared state like `options` or `scope` around in internal helpers
* or better yet: extract what you need into locals, then release the lock early
* we provide lexical scope macros `SENTRY_WITH_OPTIONS` and `SENTRY_WITH_SCOPE` (and variants) as convenience wrappers
* if you use them be aware of the following:
Expand All @@ -236,3 +237,7 @@ applied in order not to have to fight boring concurrency bugs:
* never early-return or jump (via `goto` or `return`) from within a `SENTRY_WITH_*` block: doing so skips the corresponding release or cleanup
* in particular, since `options` are readonly after `sentry_init()` the lock is only acquired to increment the refcount for the duration of `SENTRY_WITH_OPTIONS`
* however, `SENTRY_WITH_SCOPE` (and variants) always hold the lock for the entirety of their lexical scope

## Runtime Library Requirements

**Vulkan** (optional): When GPU info gathering is enabled (`-DSENTRY_WITH_GPU_INFO=ON`), a Vulkan runtime library (e.g. `libvulkan.so`, `vulkan-1.dll`, or `libvulkan.dylib` via MoltenVK) must be available at runtime. The SDK dynamically loads the library — no Vulkan SDK is needed at build time (headers are vendored). If the library is not found at runtime, GPU info is silently skipped.
11 changes: 9 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
[![Conan Center](https://shields.io/conan/v/sentry-native)](https://conan.io/center/recipes/sentry-native) [![homebrew](https://img.shields.io/homebrew/v/sentry-native)](https://formulae.brew.sh/formula/sentry-native) [![nixpkgs unstable](https://repology.org/badge/version-for-repo/nix_unstable/sentry-native.svg)](https://github.com/NixOS/nixpkgs/blob/nixos-unstable/pkgs/by-name/se/sentry-native/package.nix) [![vcpkg](https://shields.io/vcpkg/v/sentry-native)](https://vcpkg.link/ports/sentry-native)

<p align="center">
<a href="https://sentry.io/?utm_source=github&utm_medium=logo" target="_blank">
<picture>
Expand All @@ -10,6 +11,7 @@
</p>

# Official Sentry SDK for C/C++ <!-- omit in toc -->

[![GH Workflow](https://img.shields.io/github/actions/workflow/status/getsentry/sentry-native/ci.yml?branch=master)](https://github.com/getsentry/sentry-native/actions)
[![codecov](https://codecov.io/gh/getsentry/sentry-native/branch/master/graph/badge.svg)](https://codecov.io/gh/getsentry/sentry-native)

Expand Down Expand Up @@ -184,8 +186,8 @@ specifying the `SDKROOT`:
$ export SDKROOT=$(xcrun --sdk macosx --show-sdk-path)
```

If you build on macOS using _CMake 4_, then you _must_ specify the `SDKROOT`, because
[CMake 4 defaults to an empty `CMAKE_OSX_SYSROOT`](https://cmake.org/cmake/help/latest/variable/CMAKE_OSX_SYSROOT.html),
If you build on macOS using _CMake 4_, then you _must_ specify the `SDKROOT`, because
[CMake 4 defaults to an empty `CMAKE_OSX_SYSROOT`](https://cmake.org/cmake/help/latest/variable/CMAKE_OSX_SYSROOT.html),
which could lead to inconsistent include paths when CMake tries to gather the `sysroot` later in the build.

### Compile-Time Options
Expand Down Expand Up @@ -301,6 +303,11 @@ using `cmake -D BUILD_SHARED_LIBS=OFF ..`.
tuning the thread stack guarantee parameters. Warnings and errors in the process of setting thread stack guarantees
will always be logged.

- `SENTRY_WITH_GPU_INFO` (Default: `OFF`):
Enables GPU information collection and reporting. Supported on Windows, macOS, and Linux. When enabled, the SDK
will attempt to gather GPU details such as GPU name, vendor, memory size, and driver version, which are included
in event contexts. The implementation uses the Vulkan API with dynamic loading for cross-platform GPU detection.

### Support Matrix

| Feature | Windows | macOS | Linux | Android | iOS |
Expand Down
1 change: 1 addition & 0 deletions external/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -197,3 +197,4 @@ target_include_directories(breakpad_client
PUBLIC
"$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}>"
)

1 change: 1 addition & 0 deletions external/vulkan-headers
Submodule vulkan-headers added at 2efaa5
27 changes: 27 additions & 0 deletions src/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -272,3 +272,30 @@ else()
screenshot/sentry_screenshot_none.c
)
endif()

# gpu
if(SENTRY_WITH_GPU_INFO)
target_compile_definitions(sentry PRIVATE SENTRY_WITH_GPU_INFO)
sentry_target_sources_cwd(sentry
sentry_gpu.h
gpu/sentry_gpu_common.c
)

if(WIN32 OR (APPLE AND NOT IOS) OR LINUX)
sentry_target_sources_cwd(sentry
gpu/sentry_gpu_vulkan.h
gpu/sentry_gpu_vulkan.c
)
else()
# For platforms that do not support GPU info gathering, we provide a no-op implementation
sentry_target_sources_cwd(sentry
gpu/sentry_gpu_none.c
)
endif()
else()
sentry_target_sources_cwd(sentry
sentry_gpu.h
gpu/sentry_gpu_common.c
gpu/sentry_gpu_none.c
)
endif()
169 changes: 169 additions & 0 deletions src/gpu/sentry_gpu_common.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,169 @@
#include "sentry_gpu.h"
#include "sentry_logger.h"
#include "sentry_string.h"

char *
sentry__gpu_vendor_id_to_name(unsigned int vendor_id)
{
switch (vendor_id) {
case 0x10DE:
return sentry__string_clone("NVIDIA Corporation");
case 0x1002:
case 0x1022:
return sentry__string_clone("Advanced Micro Devices, Inc. [AMD/ATI]");
case 0x8086:
return sentry__string_clone("Intel Corporation");
case 0x106B:
return sentry__string_clone("Apple Inc.");
case 0x1414:
return sentry__string_clone("Microsoft Corporation");
case 0x5143:
case 0x17CB:
return sentry__string_clone("Qualcomm");
case 0x13B5:
return sentry__string_clone("ARM");
case 0x144D:
return sentry__string_clone("Samsung Electronics");
case 0x1AE0:
return sentry__string_clone("Google");
case 0x1010:
return sentry__string_clone("VideoLogic");
case 0x1023:
return sentry__string_clone("Trident Microsystems");
case 0x102B:
return sentry__string_clone("Matrox Graphics");
case 0x121A:
return sentry__string_clone("3dfx Interactive");
case 0x18CA:
return sentry__string_clone("XGI Technology");
case 0x1039:
return sentry__string_clone("Silicon Integrated Systems [SiS]");
case 0x126F:
return sentry__string_clone("Silicon Motion");
default: {
char unknown_vendor[64];
snprintf(unknown_vendor, sizeof(unknown_vendor), "Unknown (0x%04X)",
vendor_id);
return sentry__string_clone(unknown_vendor);
}
}
}

static sentry_value_t
create_gpu_context_from_info(sentry_gpu_info_t *gpu_info)
{
if (!gpu_info) {
SENTRY_WARN("No GPU info provided. Skipping GPU context creation.");
return sentry_value_new_null();
}

sentry_value_t gpu_context = sentry_value_new_object();
if (sentry_value_is_null(gpu_context)) {
return gpu_context;
}

// Add type field for frontend recognition
sentry_value_set_by_key(
gpu_context, "type", sentry_value_new_string("gpu"));

// Add GPU name
if (gpu_info->name) {
sentry_value_set_by_key(
gpu_context, "name", sentry_value_new_string(gpu_info->name));
}

// Add vendor information
if (gpu_info->vendor_name) {
sentry_value_set_by_key(gpu_context, "vendor_name",
sentry_value_new_string(gpu_info->vendor_name));
}

if (gpu_info->vendor_id != 0) {
char vendor_id_str[32];
snprintf(
vendor_id_str, sizeof(vendor_id_str), "%u", gpu_info->vendor_id);
sentry_value_set_by_key(
gpu_context, "vendor_id", sentry_value_new_string(vendor_id_str));
}

// Add device ID
if (gpu_info->device_id != 0) {
char device_id_str[32];
snprintf(
device_id_str, sizeof(device_id_str), "%u", gpu_info->device_id);
sentry_value_set_by_key(
gpu_context, "device_id", sentry_value_new_string(device_id_str));
}

// Add memory size
if (gpu_info->memory_size > 0) {
sentry_value_set_by_key(gpu_context, "memory_size",
sentry_value_new_uint64(gpu_info->memory_size));
}

// Add driver version
if (gpu_info->driver_version) {
sentry_value_set_by_key(gpu_context, "driver_version",
sentry_value_new_string(gpu_info->driver_version));
}

sentry_value_freeze(gpu_context);
return gpu_context;
}

void
sentry__free_gpu_info(sentry_gpu_info_t *gpu_info)
{
if (!gpu_info) {
return;
}

sentry_free(gpu_info->name);
sentry_free(gpu_info->vendor_name);
sentry_free(gpu_info->driver_version);
sentry_free(gpu_info);
}

void
sentry__free_gpu_list(sentry_gpu_list_t *gpu_list)
{
if (!gpu_list) {
return;
}

for (unsigned int i = 0; i < gpu_list->count; i++) {
sentry__free_gpu_info(gpu_list->gpus[i]);
}

sentry_free(gpu_list->gpus);
sentry_free(gpu_list);
}

void
sentry__add_gpu_contexts(sentry_value_t contexts)
{
sentry_gpu_list_t *gpu_list = sentry__get_gpu_info();
if (!gpu_list) {
return;
}

unsigned int context_index = 0;
for (unsigned int i = 0; i < gpu_list->count; i++) {
sentry_value_t gpu_context
= create_gpu_context_from_info(gpu_list->gpus[i]);
if (!sentry_value_is_null(gpu_context)) {
// Use context_index (not i) so keys are contiguous: gpu, gpu2, gpu3
char context_key[32];
if (context_index == 0) {
snprintf(context_key, sizeof(context_key), "gpu");
} else {
snprintf(context_key, sizeof(context_key), "gpu%u",
context_index + 1);
}
sentry_value_set_by_key(contexts, context_key, gpu_context);
context_index++;
}
}

sentry__free_gpu_list(gpu_list);
}
7 changes: 7 additions & 0 deletions src/gpu/sentry_gpu_none.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
#include "sentry_gpu.h"

sentry_gpu_list_t *
sentry__get_gpu_info(void)
{
return NULL;
}
Loading
Loading