diff --git a/CHANGELOG.md b/CHANGELOG.md index 6a52435cd..416b0b988 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,12 @@ # Changelog +## Unreleased (1.0.0) + +**Breaking / Important behavior changes**: + +- macOS/Linux: shared libraries now use ABI-versioned filenames, such as `libsentry.1.dylib` or `libsentry.so.1` for 1.x. Windows, Android, and static libraries remain unchanged. ([#2103](https://github.com/getsentry/sentry-native/pull/2103)) + - NOTE: Applications must package the real versioned library and its symlinks, including `libsentry.1.dylib` or `libsentry.so.1`, because they link to and load the ABI-versioned name. + ## Unreleased **Breaking / Important behavior changes**: diff --git a/CMakeLists.txt b/CMakeLists.txt index 3d3c63e05..11984db39 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -384,6 +384,27 @@ add_library(sentry ${SENTRY_LIBRARY_TYPE} "${PROJECT_SOURCE_DIR}/src/sentry_mpac if (XBOX) set_target_properties(sentry PROPERTIES VS_USER_PROPS gdk_build.props) endif() + +set_target_properties(sentry PROPERTIES + VERSION "${SENTRY_VERSION_BASE}" + SOVERSION "${SENTRY_VERSION_MAJOR}") + +if(WIN32 AND SENTRY_BUILD_SHARED_LIBS) + set(_SENTRY_IMAGE_VERSION "${SENTRY_VERSION_MAJOR}.${SENTRY_VERSION_MINOR}") + if(CMAKE_GENERATOR MATCHES "^Visual Studio " AND CMAKE_VERSION VERSION_LESS 4.1) + # VS generators before CMake 4.1 ignore VERSION for the PE image header. + target_link_options(sentry PRIVATE "/VERSION:${_SENTRY_IMAGE_VERSION}") + elseif(MINGW) + include(CheckLinkerFlag) + check_linker_flag(C "LINKER:/version:0.0" _SENTRY_LINKER_SUPPORTS_PE_VERSION) + if(_SENTRY_LINKER_SUPPORTS_PE_VERSION) + # lld silently ignores CMake's GNU image-version flags. + target_link_options(sentry PRIVATE "LINKER:/version:${_SENTRY_IMAGE_VERSION}") + endif() + endif() + unset(_SENTRY_IMAGE_VERSION) +endif() + target_sources(sentry PRIVATE "${PROJECT_SOURCE_DIR}/include/sentry.h") add_library(sentry::sentry ALIAS sentry) diff --git a/README.md b/README.md index d9c63cc17..833991479 100644 --- a/README.md +++ b/README.md @@ -119,12 +119,17 @@ install └── lib ├── cmake │ └── sentry - ├── libsentry.dylib - └── libsentry.dylib.dSYM + ├── libsentry.1.0.0.dylib + ├── libsentry.1.dylib -> libsentry.1.0.0.dylib + ├── libsentry.dylib -> libsentry.1.dylib + └── libsentry.1.0.0.dylib.dSYM ``` Please refer to the CMake Manual for more details. +Starting with 1.0.0, shared libraries on macOS and Linux use ABI-versioned +runtime names such as `libsentry.1.dylib` or `libsentry.so.1`. + **Android**: The CMake project can also be configured to correctly work with the Android NDK, diff --git a/tests/test_build_static.py b/tests/test_build.py similarity index 70% rename from tests/test_build_static.py rename to tests/test_build.py index 950ed334f..c31a66a80 100644 --- a/tests/test_build_static.py +++ b/tests/test_build.py @@ -1,17 +1,71 @@ import subprocess import sys import os +import struct + import pytest + +from . import SENTRY_VERSION, lib_name from .conditions import ( has_breakpad, has_crashpad, has_native, + is_aix, is_android, is_qemu, is_wine, ) +def _assert_symlink(path, target): + assert path.is_symlink() + assert os.readlink(path) == target + + +def _assert_shared_version(directory): + major, minor, _ = SENTRY_VERSION.split(".") + + if sys.platform == "darwin": + real_name = f"libsentry.{SENTRY_VERSION}.dylib" + abi_name = f"libsentry.{major}.dylib" + _assert_symlink(directory / "libsentry.dylib", abi_name) + _assert_symlink(directory / abi_name, real_name) + output = subprocess.check_output( + ["otool", "-L", directory / real_name], text=True + ) + assert abi_name in output + assert f"compatibility version {major}.0.0" in output + assert f"current version {SENTRY_VERSION}" in output + elif sys.platform == "win32": + dll = directory / lib_name("sentry") + with dll.open("rb") as binary: + binary.seek(0x3C) + pe_offset = struct.unpack("