Compare commits

...

47 Commits

Author SHA1 Message Date
3f72edd065 Fix compile time string search in CTTI (#42)
Fixes https://github.com/boostorg/type_index/issues/41
2025-03-19 10:22:58 +03:00
a418e8414b Update copyright years 2025-01-07 20:41:54 +03:00
795773e0e0 Add support for modular build structure. (#40)
This is part of the effort to make the Boost libraries "modular" for build and consumption. See https://lists.boost.org/Archives/boost/2024/01/255704.php and https://github.com/grafikrobot/boost-b2-modular/blob/b2-modular/README.adoc for more information.

This PR depends on the following other PRs being merged to both develop and master branches of the respective repos:

- https://github.com/boostorg/boost/pull/854
2024-08-24 12:38:13 +03:00
e37bc99e85 Modernize the alignment test 2024-01-07 14:49:28 +03:00
43dd1e135a Update copyright years 2024-01-07 12:59:10 +03:00
29ab3258a7 do not run tests on old MSVC in appveyor 2023-08-25 14:06:21 +03:00
4a04bb5f46 update meta 2023-08-25 12:49:14 +03:00
34e6c165da run tests on more compilers 2023-08-25 11:59:54 +03:00
034d105a48 Remove hard error about C++11 requirement (fixes #38) 2023-08-25 11:41:48 +03:00
62a3c9e89f Use relative URL for redirect in index.html (#37) 2023-08-12 11:03:19 +03:00
b9815d397b Drop C++03 support and Boost.Preprocessor usage (#13) 2023-08-11 21:34:25 +03:00
7bde4f36af Update CI (3) 2023-05-27 17:30:17 +03:00
b66e6cf881 update CI setup (2) 2023-05-21 12:21:05 +03:00
ad7e8f7e4b update CI setup (1) 2023-05-21 11:19:51 +03:00
6fcb86f6cc update CI setup 2023-05-21 10:59:55 +03:00
b8e658c5bd add C++03 deprecation warnings 2023-05-14 20:08:00 +03:00
9507b06b68 Update copyright years 2023-01-19 10:22:50 +03:00
9f35fab4cf Update ci.yml 2022-12-24 17:51:43 +02:00
d4fe92e302 Regenerate CMakeLists.txt 2022-12-23 03:05:52 +02:00
cca370a918 update copyright years 2022-01-30 15:01:13 +03:00
97fc5b9838 do not use depth 1 for checkouts in CI 2021-09-20 21:56:00 +03:00
0cc169ecd6 modernize CI setup 2021-09-11 18:18:54 +03:00
a3c6a957ee Update CMakeLists.txt 2021-06-10 00:48:35 +03:00
04cc1734ef use HTTPS links in Readme 2021-04-27 11:22:44 +03:00
f395836779 gather coverage in CI from more platforms 2021-04-24 21:53:20 +03:00
4f51b1f4eb update Readme with new CI links and new doc links, do not gather coverage twice, remove drone 2021-04-24 18:53:27 +03:00
a2ef72c907 CI updates: proper setup of clang-7 and restore sanitizers for gcc-10 2021-04-24 14:28:28 +03:00
331c26760e Use clang-7 in CI instead of clang-3.8; do not sanitize with GCC-10 2021-04-24 14:20:46 +03:00
d6d07a8ce8 add missing include and do not tests on clang-3.7 2021-04-24 13:49:52 +03:00
4468903f8f modernize CI 2021-04-24 12:47:19 +03:00
88c5d9a998 fix broken link 2021-04-24 12:46:59 +03:00
f0b87ea7d3 Merge pull request #35 from sdarwin/githubactions
GitHub Actions config
2021-04-18 14:10:35 +03:00
03794d6144 Add GitHub Actions config [ci skip] 2021-03-04 18:22:58 +00:00
62154d3b19 Merge pull request #33 from sdarwin/drone
Drone config
2021-01-27 10:29:41 +03:00
b4014f385d Merge pull request #32 from eldiener/develop
[skip ci] Add "cxxstd" json field
2021-01-27 10:25:31 +03:00
0dc42bab8f add drone config [ci skip] 2021-01-26 15:29:49 +00:00
a4726d239f [skip ci] Add "cxxstd" json field. The "cxxstd" json field is being added to each Boost library's meta json information for libraries in order to specify the minumum C++ standard compilation level. The value of this field matches one of the values for 'cxxstd' in Boost.Build. The purpose of doing this is to provide information for the Boost website documentation for each library which will specify the minimum C++ standard compilation that an end-user must employ in order to use the particular library. This will aid end-users who want to know if they can successfully use a Boost library based on their C++ compiler's compilation level, without having to search the library's documentation to find this out. 2021-01-21 16:26:02 -05:00
f40f4731e1 Merge github.com:apolukhin/type_index into develop 2021-01-04 18:29:36 +03:00
754fb0f348 CI fix attempt (1) 2021-01-04 13:32:09 +03:00
6fa4f57e7d CI fix attempt 2021-01-04 13:23:42 +03:00
c79f1c8d5d Specify address model for MSVC
Relates boostorg/build#659
2021-01-04 11:04:54 +03:00
843ee6848b update copyright years 2021-01-03 20:01:31 +03:00
6fc5b35b00 Merge pull request #31 from sdarwin/lcov
update .travis.yml to correct lcov error messages
2021-01-03 12:49:28 +03:00
84d68f32e2 update lcov in .travis.yml 2020-12-31 00:51:49 +00:00
1dacdb561e Merge pull request #29 from Kojoley/cease-dependence-on-smart_ptr
Cease dependence on SmartPtr
2020-08-27 12:03:36 +03:00
9862011b6b CI fixes 2020-07-06 11:36:48 +03:00
321749796e Cease dependence on SmartPtr
by forward declaring `boost::shared_ptr`
2020-05-26 02:56:12 +03:00
49 changed files with 576 additions and 541 deletions

192
.github/workflows/ci.yml vendored Normal file
View File

@ -0,0 +1,192 @@
name: CI
on:
pull_request:
push:
branches:
- master
- develop
- feature/**
env:
UBSAN_OPTIONS: print_stacktrace=1
jobs:
posix:
strategy:
fail-fast: false
matrix:
include:
- toolset: gcc-12
cxxstd: "03,11,14,17,2a"
os: ubuntu-22.04
cxxflags: "cxxflags=--coverage -fsanitize=address,leak,undefined -fno-sanitize-recover=undefined"
linkflags: "linkflags=--coverage -lasan -lubsan"
gcov_tool: "gcov-12"
launcher: "testing.launcher=LD_PRELOAD=/usr/lib/x86_64-linux-gnu/libasan.so.8"
- toolset: gcc-11
cxxstd: "03,11,14,17,2a"
os: ubuntu-22.04
cxxflags: "cxxflags=--coverage -fsanitize=address,leak,undefined -fno-sanitize-recover=undefined"
linkflags: "linkflags=--coverage -lasan -lubsan"
gcov_tool: "gcov-11"
launcher: "testing.launcher=LD_PRELOAD=/usr/lib/x86_64-linux-gnu/libasan.so.6"
- toolset: gcc-10
cxxstd: "03,11,14,17,2a"
os: ubuntu-22.04
cxxflags: "cxxflags=--coverage -fsanitize=address,leak,undefined -fno-sanitize-recover=undefined"
linkflags: "linkflags=--coverage -lasan -lubsan"
gcov_tool: "gcov-10"
launcher: "testing.launcher=LD_PRELOAD=/usr/lib/x86_64-linux-gnu/libasan.so.6"
- toolset: gcc-9
cxxstd: "03,11,14,17,2a"
os: ubuntu-22.04
cxxflags: "cxxflags=--coverage -fsanitize=address,leak,undefined -fno-sanitize-recover=undefined"
linkflags: "linkflags=--coverage -lasan -lubsan"
gcov_tool: "gcov-9"
launcher: "testing.launcher=LD_PRELOAD=/usr/lib/x86_64-linux-gnu/libasan.so.5"
- toolset: clang
compiler: clang++-14
cxxstd: "03,11,14,17,2a"
os: ubuntu-22.04
- toolset: clang
compiler: clang++-10
cxxstd: "03,11,14,17,2a"
os: ubuntu-20.04
runs-on: ${{matrix.os}}
steps:
- uses: actions/checkout@v3
- name: Install packages
if: matrix.install
run: sudo apt install ${{matrix.install}}
- name: Setup Boost
run: |
echo GITHUB_REPOSITORY: $GITHUB_REPOSITORY
LIBRARY=${GITHUB_REPOSITORY#*/}
echo LIBRARY: $LIBRARY
echo "LIBRARY=$LIBRARY" >> $GITHUB_ENV
echo GITHUB_BASE_REF: $GITHUB_BASE_REF
echo GITHUB_REF: $GITHUB_REF
REF=${GITHUB_BASE_REF:-$GITHUB_REF}
REF=${REF#refs/heads/}
echo REF: $REF
BOOST_BRANCH=develop && [ "$REF" == "master" ] && BOOST_BRANCH=master || true
echo BOOST_BRANCH: $BOOST_BRANCH
cd ..
git clone -b $BOOST_BRANCH --depth 10 https://github.com/boostorg/boost.git boost-root
cd boost-root
git submodule update --init --depth 10 --jobs 2 tools/boostdep tools/inspect libs/filesystem
python tools/boostdep/depinst/depinst.py --git_args "--depth 10 --jobs 3" filesystem
rm -rf libs/$LIBRARY/*
cp -r $GITHUB_WORKSPACE/* libs/$LIBRARY
python tools/boostdep/depinst/depinst.py --include benchmark --include example --include examples --include tools --git_args "--depth 10 --jobs 3" $LIBRARY
./bootstrap.sh
./b2 -d0 headers
./b2 -j4 variant=debug tools/inspect/build
- name: Run tests
run: |
cd ../boost-root
./b2 -j3 libs/$LIBRARY/test toolset=${{matrix.toolset}} cxxstd=${{matrix.cxxstd}} variant=debug,release "${{matrix.cxxflags}}" "${{matrix.linkflags}}" "${{matrix.launcher}}"
dist/bin/inspect libs/$LIBRARY
- name: Prepare coverage data
if: matrix.gcov_tool
run: |
mkdir -p $GITHUB_WORKSPACE/coveralls
echo -e "#!/bin/bash\nexec ${{matrix.gcov_tool}} \"\$@\"" > $GITHUB_WORKSPACE/coveralls/gcov_wrapper.sh
chmod +x $GITHUB_WORKSPACE/coveralls/gcov_wrapper.sh
wget https://github.com/linux-test-project/lcov/archive/v1.15.zip
unzip v1.15.zip
LCOV="`pwd`/lcov-1.15/bin/lcov --gcov-tool $GITHUB_WORKSPACE/coveralls/gcov_wrapper.sh"
echo "$LCOV --directory ../boost-root/bin.v2/libs/$LIBRARY/ --base-directory `pwd`/libs/$LIBRARY/test --capture --output-file $GITHUB_WORKSPACE/coveralls/coverage.info"
$LCOV --directory ../boost-root/bin.v2/libs/$LIBRARY/ --base-directory ../boost-root/ --capture --output-file $GITHUB_WORKSPACE/coveralls/coverage.info
$LCOV --remove $GITHUB_WORKSPACE/coveralls/coverage.info "/usr*" "*/$LIBRARY/test/*" ${{matrix.ignore_coverage}} "*/$LIBRARY/tests/*" "*/$LIBRARY/examples/*" "*/$LIBRARY/example/*" -o $GITHUB_WORKSPACE/coveralls/coverage.info
cd ../boost-root
OTHER_LIBS=`grep "submodule .*" .gitmodules | sed 's/\[submodule\ "\(.*\)"\]/"\*\/boost\/\1\.hpp" "\*\/boost\/\1\/\*"/g'| sed "/\"\*\/boost\/$LIBRARY\/\*\"/d" | sed ':a;N;$!ba;s/\n/ /g'`
echo $OTHER_LIBS
eval "$LCOV --remove $GITHUB_WORKSPACE/coveralls/coverage.info $OTHER_LIBS -o $GITHUB_WORKSPACE/coveralls/coverage.info"
- name: Coveralls
uses: coverallsapp/github-action@master
if: matrix.gcov_tool
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
path-to-lcov: ./coveralls/coverage.info
parallel: true
windows:
strategy:
fail-fast: false
matrix:
include:
- toolset: msvc-14.0
cxxstd: "14,latest"
addrmd: 32,64
os: windows-2019
- toolset: msvc-14.2
cxxstd: "14,17,20,latest"
addrmd: 32,64
os: windows-2019
- toolset: msvc-14.3
cxxstd: "14,17,20,latest"
addrmd: 32,64
os: windows-2022
- toolset: clang-win
cxxstd: "14,17,latest"
addrmd: 32,64
os: windows-2022
- toolset: gcc
cxxstd: "03,11,14,17,2a"
addrmd: 64
os: windows-2019
runs-on: ${{matrix.os}}
steps:
- uses: actions/checkout@v3
- name: Setup Boost
shell: cmd
run: |
echo GITHUB_REPOSITORY: %GITHUB_REPOSITORY%
for /f %%i in ("%GITHUB_REPOSITORY%") do set LIBRARY=%%~nxi
echo LIBRARY: %LIBRARY%
echo LIBRARY=%LIBRARY%>>%GITHUB_ENV%
echo GITHUB_BASE_REF: %GITHUB_BASE_REF%
echo GITHUB_REF: %GITHUB_REF%
if "%GITHUB_BASE_REF%" == "" set GITHUB_BASE_REF=%GITHUB_REF%
set BOOST_BRANCH=develop
for /f %%i in ("%GITHUB_BASE_REF%") do if "%%~nxi" == "master" set BOOST_BRANCH=master
echo BOOST_BRANCH: %BOOST_BRANCH%
cd ..
git clone -b %BOOST_BRANCH% --depth 10 https://github.com/boostorg/boost.git boost-root
cd boost-root
xcopy /s /e /q %GITHUB_WORKSPACE% libs\%LIBRARY%\
git submodule update --init tools/boostdep
python tools/boostdep/depinst/depinst.py --include benchmark --include example --include examples --include tools --git_args "--jobs 3" %LIBRARY%
cmd /c bootstrap
b2 -d0 headers
- name: Run tests
shell: cmd
run: |
cd ../boost-root
b2 -j3 libs/%LIBRARY%/test toolset=${{matrix.toolset}} cxxstd=${{matrix.cxxstd}} address-model=${{matrix.addrmd}} variant=debug,release embed-manifest-via=linker
finish:
needs: posix
runs-on: ubuntu-latest
steps:
- name: Coveralls Finished
uses: coverallsapp/github-action@master
with:
github-token: ${{ secrets.github_token }}
parallel-finished: true

View File

@ -1,146 +0,0 @@
# Use, modification, and distribution are
# subject to the Boost Software License, Version 1.0. (See accompanying
# file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
#
# Copyright Antony Polukhin 2014-2019.
#
# See https://svn.boost.org/trac/boost/wiki/TravisCoverals for description of this file
# and how it can be used with Boost libraries.
#
# File revision #10
sudo: false
language: cpp
os: linux
env:
global:
# Autodetect Boost branch by using the following code: - BOOST_BRANCH=$TRAVIS_BRANCH
# or just directly specify it
- BOOST_BRANCH=develop && [ "$TRAVIS_BRANCH" == "master" ] && BOOST_BRANCH=master || true
# Files, which coverage results must be ignored (files from other projects).
# Example: - IGNORE_COVERAGE='*/boost/progress.hpp */filesystem/src/*'
- IGNORE_COVERAGE=''
# boost-local/libs/ folder to put this library into. This may be useful, if you're for example running Travis
# from `Boost.DLL` repo while Boost already has `dll` and with to replace `dll` with content of`Boost.DLL`.
#
# Otherwise just leave the default value - BOOST_LIBS_FOLDER=$(basename $TRAVIS_BUILD_DIR)
- BOOST_LIBS_FOLDER=$(basename $TRAVIS_BUILD_DIR)
# Global options for sanitizers
- UBSAN_OPTIONS=print_stacktrace=1
- LSAN_OPTIONS=verbosity=1:log_threads=1
# `--coverage` flags required to generate coverage info for Coveralls
matrix:
include:
- env: B2_ARGS='cxxstd=98,03,11,14,1z toolset=gcc-8 cxxflags="--coverage -fsanitize=address,leak,undefined -fno-sanitize-recover=undefined -DBOOST_TRAVISCI_BUILD" linkflags="--coverage -lasan -lubsan" "testing.launcher=LD_PRELOAD=/usr/lib/x86_64-linux-gnu/libasan.so.5"'
name: "GCC-8"
sudo: required # Required by leak sanitizer
addons:
apt:
sources: ubuntu-toolchain-r-test
packages: g++-8
- env: B2_ARGS='cxxstd=98,0x toolset=gcc-4.6 cxxflags="--coverage -DBOOST_TRAVISCI_BUILD" linkflags="--coverage"'
name: "GCC-4.6"
addons:
apt:
sources: ubuntu-toolchain-r-test
packages: g++-4.6
- env: B2_ARGS='cxxstd=98,03,11,14,1z toolset=clang-8 cxxflags="--coverage -fsanitize=address,leak,undefined -fno-sanitize-recover=undefined -DBOOST_TRAVISCI_BUILD" linkflags="--coverage -fsanitize=address,leak,undefined"'
name: "Clang-8"
sudo: required # Required by leak sanitizer
addons:
apt:
sources: llvm-toolchain-trusty-8
packages: clang-8
# Sanitizers disabled for this toolset as they started causing link troubles:
# hidden symbol `_ZNSt3__112basic_stringIcNS_11char_traitsIcEENS_9allocatorIcEEE11__recommendEm' isn't defined
- env: B2_ARGS='cxxstd=03,11,14 toolset=clang-libc++ cxxflags="--coverage -DBOOST_TRAVISCI_BUILD" linkflags="--coverage"'
name: "Clang-3.8, libc++"
addons:
apt:
packages: libc++-dev
###############################################################################################################
# From this point and below code is same for all the Boost libs
###############################################################################################################
# Installing additional tools
addons:
apt:
sources: git-core
packages:
- git
- python-yaml
before_install:
# Cloning minimal set of Boost libraries
- BOOST=$HOME/boost-local
- git clone -b $BOOST_BRANCH --depth 10 https://github.com/boostorg/boost.git $BOOST
- cd $BOOST
- git submodule update --init --depth 10 --jobs 2 tools/build tools/boostdep tools/inspect libs/filesystem
- python tools/boostdep/depinst/depinst.py --git_args "--depth 10 --jobs 2" $BOOST/libs/filesystem
# Replacing Boost module with this project and installing Boost dependencies
- echo "Testing $BOOST/libs/$BOOST_LIBS_FOLDER moved from $TRAVIS_BUILD_DIR, branch $BOOST_BRANCH"
- rm -rf $BOOST/libs/$BOOST_LIBS_FOLDER || true
- mv $TRAVIS_BUILD_DIR $BOOST/libs/$BOOST_LIBS_FOLDER
- python tools/boostdep/depinst/depinst.py --git_args "--depth 10 --jobs 2" $BOOST_LIBS_FOLDER
- git status
# Adding missing toolsets and preparing Boost headers
- ./bootstrap.sh
- ./b2 headers
- ./b2 -j4 variant=debug tools/inspect/build
- |-
echo "using gcc ;" >> ~/user-config.jam
echo "using clang ;" >> ~/user-config.jam
echo "using clang : 3.8 : clang++-3.8 ;" >> ~/user-config.jam
echo "using clang : 4 : clang++-4.0 ;" >> ~/user-config.jam
echo "using clang : 5 : clang++-5.0 ;" >> ~/user-config.jam
echo "using clang : 6 : clang++-6.0 ;" >> ~/user-config.jam
echo "using clang : 7 : clang++-7.0 ;" >> ~/user-config.jam
echo "using clang : 8 : clang++-8 ;" >> ~/user-config.jam
echo "using clang : libc++ : clang++-libc++ ;" >> ~/user-config.jam
- cd $BOOST/libs/$BOOST_LIBS_FOLDER/test/
script:
- sh -c "../../../b2 -j2 $B2_ARGS"
# inspect tool run without -link and -assert_macro checks
- ../../../dist/bin/inspect .. -license -copyright -crlf -end -path_name -tab -ascii -apple_macro -deprecated_macro -minmax -unnamed
after_success:
# Copying Coveralls data to a separate folder
- mkdir -p $TRAVIS_BUILD_DIR/coverals
- find ../../../bin.v2/ -name "*.gcda" -exec cp "{}" $TRAVIS_BUILD_DIR/coverals/ \;
- find ../../../bin.v2/ -name "*.gcno" -exec cp "{}" $TRAVIS_BUILD_DIR/coverals/ \;
- find ../../../bin.v2/ -name "*.da" -exec cp "{}" $TRAVIS_BUILD_DIR/coverals/ \;
- find ../../../bin.v2/ -name "*.no" -exec cp "{}" $TRAVIS_BUILD_DIR/coverals/ \;
- wget https://github.com/linux-test-project/lcov/archive/v1.12.zip
- unzip v1.12.zip
- LCOV="`pwd`/lcov-1.12/bin/lcov --gcov-tool gcov-6"
# Preparing Coveralls data by changind data format to a readable one
- echo "$LCOV --directory $TRAVIS_BUILD_DIR/coverals --base-directory `pwd` --capture --output-file $TRAVIS_BUILD_DIR/coverals/coverage.info"
- $LCOV --directory $TRAVIS_BUILD_DIR/coverals --base-directory `pwd` --capture --output-file $TRAVIS_BUILD_DIR/coverals/coverage.info
# ... erasing /test/ /example/ folder data
- cd $BOOST
- $LCOV --remove $TRAVIS_BUILD_DIR/coverals/coverage.info "/usr*" "*/$BOOST_LIBS_FOLDER/test/*" $IGNORE_COVERAGE "*/$BOOST_LIBS_FOLDER/tests/*" "*/$BOOST_LIBS_FOLDER/examples/*" "*/$BOOST_LIBS_FOLDER/example/*" -o $TRAVIS_BUILD_DIR/coverals/coverage.info
# ... erasing data that is not related to this project directly
- OTHER_LIBS=`grep "submodule .*" .gitmodules | sed 's/\[submodule\ "\(.*\)"\]/"\*\/boost\/\1\.hpp" "\*\/boost\/\1\/\*"/g'| sed "/\"\*\/boost\/$BOOST_LIBS_FOLDER\/\*\"/d" | sed ':a;N;$!ba;s/\n/ /g'`
- echo $OTHER_LIBS
- eval "$LCOV --remove $TRAVIS_BUILD_DIR/coverals/coverage.info $OTHER_LIBS -o $TRAVIS_BUILD_DIR/coverals/coverage.info"
# Sending data to Coveralls
- cd $TRAVIS_BUILD_DIR
- gem install coveralls-lcov
- coveralls-lcov coverals/coverage.info

View File

@ -1,12 +1,11 @@
# Copyright 2019 Mike Dev
# Generated by `boostdep --cmake type_index`
# Copyright 2020, 2021 Peter Dimov
# Distributed under the Boost Software License, Version 1.0.
# See accompanying file LICENSE_1_0.txt or copy at https://www.boost.org/LICENSE_1_0.txt
#
# NOTE: CMake support for Boost.TypeIndex is currently experimental at best
# and the interface is likely to change in the future
# https://www.boost.org/LICENSE_1_0.txt
cmake_minimum_required(VERSION 3.5)
project(Boost.TypeIndex)
cmake_minimum_required(VERSION 3.5...3.20)
project(boost_type_index VERSION "${BOOST_SUPERPROJECT_VERSION}" LANGUAGES CXX)
add_library(boost_type_index INTERFACE)
add_library(Boost::type_index ALIAS boost_type_index)
@ -14,13 +13,15 @@ add_library(Boost::type_index ALIAS boost_type_index)
target_include_directories(boost_type_index INTERFACE include)
target_link_libraries(boost_type_index
INTERFACE
Boost::config
Boost::container_hash
Boost::core
Boost::preprocessor
Boost::smart_ptr
Boost::static_assert
Boost::throw_exception
Boost::type_traits
INTERFACE
Boost::config
Boost::container_hash
Boost::core
Boost::throw_exception
)
if(BUILD_TESTING AND EXISTS "${CMAKE_CURRENT_SOURCE_DIR}/test/CMakeLists.txt")
add_subdirectory(test)
endif()

View File

@ -1,18 +1,16 @@
# [Boost.TypeIndex](http://boost.org/libs/type_index)
Boost.TypeIndex is a part of the [Boost C++ Libraries](http://github.com/boostorg). It is a runtime/compile time copyable type info.
# [Boost.TypeIndex](https://boost.org/libs/type_index)
Boost.TypeIndex is a part of the [Boost C++ Libraries](https://github.com/boostorg). It is a runtime/compile time copyable type info.
### Test results
@ | Build | Tests coverage | More info
----------------|-------------- | -------------- |-----------
Develop branch: | [![Build Status](https://travis-ci.org/apolukhin/type_index.svg?branch=develop)](https://travis-ci.org/apolukhin/type_index) [![Build status](https://ci.appveyor.com/api/projects/status/197a5imq10dqx6r8/branch/develop?svg=true)](https://ci.appveyor.com/project/apolukhin/type-index/branch/develop) | [![Coverage Status](https://coveralls.io/repos/apolukhin/type_index/badge.png?branch=develop)](https://coveralls.io/r/apolukhin/type_index?branch=develop) | [details...](http://www.boost.org/development/tests/develop/developer/type_index.html)
Master branch: | [![Build Status](https://travis-ci.org/apolukhin/type_index.svg?branch=master)](https://travis-ci.org/apolukhin/type_index) [![Build status](https://ci.appveyor.com/api/projects/status/197a5imq10dqx6r8/branch/master?svg=true)](https://ci.appveyor.com/project/apolukhin/type-index/branch/master) | [![Coverage Status](https://coveralls.io/repos/apolukhin/type_index/badge.png?branch=master)](https://coveralls.io/r/apolukhin/type_index?branch=master) | [details...](http://www.boost.org/development/tests/master/developer/type_index.html)
Develop branch: | [![CI](https://github.com/boostorg/type_index/actions/workflows/ci.yml/badge.svg?branch=develop)](https://github.com/boostorg/type_index/actions/workflows/ci.yml) [![Build status](https://ci.appveyor.com/api/projects/status/197a5imq10dqx6r8/branch/develop?svg=true)](https://ci.appveyor.com/project/apolukhin/type-index/branch/develop) | [![Coverage Status](https://coveralls.io/repos/apolukhin/type_index/badge.png?branch=develop)](https://coveralls.io/r/apolukhin/type_index?branch=develop) | [details...](https://www.boost.org/development/tests/develop/developer/type_index.html)
Master branch: | [![CI](https://github.com/boostorg/type_index/actions/workflows/ci.yml/badge.svg?branch=master)](https://github.com/boostorg/type_index/actions/workflows/ci.yml) [![Build status](https://ci.appveyor.com/api/projects/status/197a5imq10dqx6r8/branch/master?svg=true)](https://ci.appveyor.com/project/apolukhin/type-index/branch/master) | [![Coverage Status](https://coveralls.io/repos/apolukhin/type_index/badge.png?branch=master)](https://coveralls.io/r/apolukhin/type_index?branch=master) | [details...](https://www.boost.org/development/tests/master/developer/type_index.html)
[Open Issues](https://svn.boost.org/trac/boost/query?status=!closed&component=type_index)
[Latest developer documentation](http://boostorg.github.com/type_index/index.html)
[Latest developer documentation](https://www.boost.org/doc/libs/develop/doc/html/boost_typeindex.html)
### License
Distributed under the [Boost Software License, Version 1.0](http://boost.org/LICENSE_1_0.txt).
Distributed under the [Boost Software License, Version 1.0](https://boost.org/LICENSE_1_0.txt).

26
build.jam Normal file
View File

@ -0,0 +1,26 @@
# Copyright René Ferdinand Rivera Morell 2023-2024
# Distributed under the Boost Software License, Version 1.0.
# (See accompanying file LICENSE_1_0.txt or copy at
# http://www.boost.org/LICENSE_1_0.txt)
require-b2 5.2 ;
constant boost_dependencies :
/boost/config//boost_config
/boost/container_hash//boost_container_hash
/boost/core//boost_core
/boost/throw_exception//boost_throw_exception ;
project /boost/type_index
: common-requirements
<include>include
;
explicit
[ alias boost_type_index : : : : <library>$(boost_dependencies) ]
[ alias all : boost_type_index test ]
;
call-if : boost-library type_index
;

View File

@ -1,4 +1,4 @@
# Copyright 2011-2020 Antony Polukhin.
# Copyright 2011-2025 Antony Polukhin.
# Use, modification, and distribution are
# subject to the Boost Software License, Version 1.0. (See accompanying
# file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
@ -9,9 +9,9 @@ import doxygen ;
doxygen autodoc
:
[ glob ../../../boost/type_index.hpp ]
[ glob ../../../boost/type_index/*.hpp ]
[ glob ../../../boost/type_index/runtime_cast/*.hpp ]
[ glob ../include/boost/type_index.hpp ]
[ glob ../include/boost/type_index/*.hpp ]
[ glob ../include/boost/type_index/runtime_cast/*.hpp ]
:
<doxygen:param>EXTRACT_ALL=NO
<doxygen:param>HIDE_UNDOC_MEMBERS=YES

View File

@ -1,7 +1,7 @@
[library Boost.TypeIndex
[quickbook 1.6]
[version 4.1]
[copyright 2012-2020 Antony Polukhin]
[copyright 2012-2025 Antony Polukhin]
[category Language Features Emulation]
[license
Distributed under the Boost Software License, Version 1.0.

View File

@ -1,4 +1,4 @@
// Copyright 2013-2020 Antony Polukhin
// Copyright 2013-2025 Antony Polukhin
// Distributed under the Boost Software License, Version 1.0.
// (See the accompanying file LICENSE_1_0.txt
@ -6,6 +6,8 @@
#include <boost/config.hpp>
#include <cstddef>
template <class T>
void do_something(const T&) {}

View File

@ -1,4 +1,4 @@
// Copyright 2013-2020 Antony Polukhin
// Copyright 2013-2025 Antony Polukhin
// Distributed under the Boost Software License, Version 1.0.
// (See the accompanying file LICENSE_1_0.txt

View File

@ -1,4 +1,4 @@
// Copyright 2013-2020 Antony Polukhin
// Copyright 2013-2025 Antony Polukhin
// Distributed under the Boost Software License, Version 1.0.
// (See the accompanying file LICENSE_1_0.txt

View File

@ -1,4 +1,4 @@
// Copyright 2013-2020 Antony Polukhin
// Copyright 2013-2025 Antony Polukhin
// Distributed under the Boost Software License, Version 1.0.
// (See the accompanying file LICENSE_1_0.txt
@ -23,6 +23,8 @@
// Making `#include <cassert>` visible in docs, while actually using hand-made check
// instead of `assert`. This is required to verify correct behavior even if NDEBUG
// is defined and to avoid `unused local variable` warnings with defined NDEBUG.
//
// boost-no-inspect
#ifdef assert
# undef assert
#endif

View File

@ -1,4 +1,4 @@
// Copyright 2013-2020 Antony Polukhin
// Copyright 2013-2025 Antony Polukhin
// Distributed under the Boost Software License, Version 1.0.
// (See the accompanying file LICENSE_1_0.txt
@ -22,7 +22,7 @@ struct A {
};
struct B: public A { BOOST_TYPE_INDEX_REGISTER_CLASS };
struct C: public B { BOOST_TYPE_INDEX_REGISTER_CLASS };
struct D: public C { BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(BOOST_TYPE_INDEX_NO_BASE_CLASS) };
struct D: public C { BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS() };
void print_real_type(const A& a) {
std::cout << boost::typeindex::type_id_runtime(a).pretty_name() << '\n';

View File

@ -1,4 +1,4 @@
// Copyright 2013-2020 Antony Polukhin
// Copyright 2013-2025 Antony Polukhin
// Distributed under the Boost Software License, Version 1.0.
// (See the accompanying file LICENSE_1_0.txt
@ -16,6 +16,8 @@
// Making `#include <cassert>` visible in docs, while actually using `BOOST_TEST`
// instead of `assert`. This is required to verify correct behavior even if NDEBUG
// is defined and to avoid `unused local variable` warnings with defined NDEBUG.
//
// boost-no-inspect
#include <boost/core/lightweight_test.hpp>
#ifdef assert
# undef assert

View File

@ -18,27 +18,27 @@
#include <iostream>
struct A {
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(BOOST_TYPE_INDEX_NO_BASE_CLASS)
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS()
virtual ~A()
{}
};
struct B {
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(BOOST_TYPE_INDEX_NO_BASE_CLASS)
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS()
virtual ~B()
{}
};
struct C : A {
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS((A))
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(A)
};
struct D : B {
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS((B))
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(B)
};
struct E : C, D {
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS((C)(D))
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(C, D)
};
int main() {

View File

@ -1,4 +1,4 @@
// Copyright 2013-2020 Antony Polukhin
// Copyright 2013-2025 Antony Polukhin
// Distributed under the Boost Software License, Version 1.0.
// (See the accompanying file LICENSE_1_0.txt

View File

@ -1,4 +1,4 @@
// Copyright 2013-2020 Antony Polukhin
// Copyright 2013-2025 Antony Polukhin
// Distributed under the Boost Software License, Version 1.0.
// (See the accompanying file LICENSE_1_0.txt
@ -14,10 +14,11 @@
*/
// BOOST_TYPE_INDEX_USER_TYPEINDEX must be defined *BEFORE* first inclusion of <boost/type_index.hpp>
#define BOOST_TYPE_INDEX_USER_TYPEINDEX <boost/../libs/type_index/examples/user_defined_typeinfo.hpp>
#define BOOST_TYPE_INDEX_USER_TYPEINDEX <user_defined_typeinfo.hpp>
#include <boost/type_index.hpp>
//] [/type_index_my_type_index_worldwide_macro]
// boost-no-inspect
#include <boost/core/lightweight_test.hpp>
#ifdef assert
# undef assert

View File

@ -1,4 +1,4 @@
// Copyright 2013-2020 Antony Polukhin
// Copyright 2013-2025 Antony Polukhin
// Distributed under the Boost Software License, Version 1.0.
// (See the accompanying file LICENSE_1_0.txt

View File

@ -1,5 +1,5 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
@ -208,7 +208,7 @@ typedef type_index::type_info_t type_info;
/// \throw Nothing.
/// \return boost::typeindex::type_index with information about the specified type T.
template <class T>
inline type_index type_id() BOOST_NOEXCEPT {
inline type_index type_id() noexcept {
return type_index::type_id<T>();
}
@ -228,7 +228,7 @@ inline type_index type_id() BOOST_NOEXCEPT {
/// \throw Nothing.
/// \return boost::typeindex::type_index with information about the specified type T.
template <class T>
inline type_index type_id_with_cvr() BOOST_NOEXCEPT {
inline type_index type_id_with_cvr() noexcept {
return type_index::type_id_with_cvr<T>();
}
@ -253,7 +253,7 @@ inline type_index type_id_with_cvr() BOOST_NOEXCEPT {
/// \throw Nothing.
/// \return boost::typeindex::type_index with information about the specified variable.
template <class T>
inline type_index type_id_runtime(const T& runtime_val) BOOST_NOEXCEPT {
inline type_index type_id_runtime(const T& runtime_val) noexcept {
return type_index::type_id_runtime(runtime_val);
}

View File

@ -1,5 +1,5 @@
//
// Copyright 2013-2020 Antony Polukhin.
// Copyright 2013-2025 Antony Polukhin.
//
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
@ -22,10 +22,8 @@
#include <boost/type_index/detail/compile_time_type_info.hpp>
#include <cstring>
#include <type_traits>
#include <boost/container_hash/hash.hpp>
#include <boost/static_assert.hpp>
#include <boost/type_traits/remove_cv.hpp>
#include <boost/type_traits/remove_reference.hpp>
#ifdef BOOST_HAS_PRAGMA_ONCE
# pragma once
@ -58,24 +56,17 @@ namespace detail {
/// std::cout << ti.pretty_name();
/// \endcode
class ctti_data {
#ifndef BOOST_NO_CXX11_DELETED_FUNCTIONS
public:
ctti_data() = delete;
ctti_data(const ctti_data&) = delete;
ctti_data& operator=(const ctti_data&) = delete;
#else
private:
ctti_data();
ctti_data(const ctti_data&);
ctti_data& operator=(const ctti_data&);
#endif
};
} // namespace detail
/// Helper method for getting detail::ctti_data of a template parameter T.
template <class T>
inline const detail::ctti_data& ctti_construct() BOOST_NOEXCEPT {
inline const detail::ctti_data& ctti_construct() noexcept {
// Standard C++11, 5.2.10 Reinterpret cast:
// An object pointer can be explicitly converted to an object pointer of a different type. When a prvalue
// v of type "pointer to T1" is converted to the type "pointer to cv T2", the result is static_cast<cv
@ -105,55 +96,55 @@ inline const detail::ctti_data& ctti_construct() BOOST_NOEXCEPT {
class ctti_type_index: public type_index_facade<ctti_type_index, detail::ctti_data> {
const char* data_;
inline std::size_t get_raw_name_length() const BOOST_NOEXCEPT;
inline std::size_t get_raw_name_length() const noexcept;
BOOST_CXX14_CONSTEXPR inline explicit ctti_type_index(const char* data) BOOST_NOEXCEPT
BOOST_CXX14_CONSTEXPR inline explicit ctti_type_index(const char* data) noexcept
: data_(data)
{}
public:
typedef detail::ctti_data type_info_t;
BOOST_CXX14_CONSTEXPR inline ctti_type_index() BOOST_NOEXCEPT
BOOST_CXX14_CONSTEXPR inline ctti_type_index() noexcept
: data_(boost::detail::ctti<void>::n())
{}
inline ctti_type_index(const type_info_t& data) BOOST_NOEXCEPT
inline ctti_type_index(const type_info_t& data) noexcept
: data_(reinterpret_cast<const char*>(&data))
{}
inline const type_info_t& type_info() const BOOST_NOEXCEPT;
BOOST_CXX14_CONSTEXPR inline const char* raw_name() const BOOST_NOEXCEPT;
BOOST_CXX14_CONSTEXPR inline const char* name() const BOOST_NOEXCEPT;
inline const type_info_t& type_info() const noexcept;
BOOST_CXX14_CONSTEXPR inline const char* raw_name() const noexcept;
BOOST_CXX14_CONSTEXPR inline const char* name() const noexcept;
inline std::string pretty_name() const;
inline std::size_t hash_code() const BOOST_NOEXCEPT;
inline std::size_t hash_code() const noexcept;
BOOST_CXX14_CONSTEXPR inline bool equal(const ctti_type_index& rhs) const BOOST_NOEXCEPT;
BOOST_CXX14_CONSTEXPR inline bool before(const ctti_type_index& rhs) const BOOST_NOEXCEPT;
BOOST_CXX14_CONSTEXPR inline bool equal(const ctti_type_index& rhs) const noexcept;
BOOST_CXX14_CONSTEXPR inline bool before(const ctti_type_index& rhs) const noexcept;
template <class T>
BOOST_CXX14_CONSTEXPR inline static ctti_type_index type_id() BOOST_NOEXCEPT;
BOOST_CXX14_CONSTEXPR inline static ctti_type_index type_id() noexcept;
template <class T>
BOOST_CXX14_CONSTEXPR inline static ctti_type_index type_id_with_cvr() BOOST_NOEXCEPT;
BOOST_CXX14_CONSTEXPR inline static ctti_type_index type_id_with_cvr() noexcept;
template <class T>
inline static ctti_type_index type_id_runtime(const T& variable) BOOST_NOEXCEPT;
inline static ctti_type_index type_id_runtime(const T& variable) noexcept;
};
inline const ctti_type_index::type_info_t& ctti_type_index::type_info() const BOOST_NOEXCEPT {
inline const ctti_type_index::type_info_t& ctti_type_index::type_info() const noexcept {
return *reinterpret_cast<const detail::ctti_data*>(data_);
}
BOOST_CXX14_CONSTEXPR inline bool ctti_type_index::equal(const ctti_type_index& rhs) const BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline bool ctti_type_index::equal(const ctti_type_index& rhs) const noexcept {
const char* const left = raw_name();
const char* const right = rhs.raw_name();
return /*left == right ||*/ !boost::typeindex::detail::constexpr_strcmp(left, right);
}
BOOST_CXX14_CONSTEXPR inline bool ctti_type_index::before(const ctti_type_index& rhs) const BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline bool ctti_type_index::before(const ctti_type_index& rhs) const noexcept {
const char* const left = raw_name();
const char* const right = rhs.raw_name();
return /*left != right &&*/ boost::typeindex::detail::constexpr_strcmp(left, right) < 0;
@ -161,37 +152,37 @@ BOOST_CXX14_CONSTEXPR inline bool ctti_type_index::before(const ctti_type_index&
template <class T>
BOOST_CXX14_CONSTEXPR inline ctti_type_index ctti_type_index::type_id() BOOST_NOEXCEPT {
typedef BOOST_DEDUCED_TYPENAME boost::remove_reference<T>::type no_ref_t;
typedef BOOST_DEDUCED_TYPENAME boost::remove_cv<no_ref_t>::type no_cvr_t;
BOOST_CXX14_CONSTEXPR inline ctti_type_index ctti_type_index::type_id() noexcept {
typedef typename std::remove_reference<T>::type no_ref_t;
typedef typename std::remove_cv<no_ref_t>::type no_cvr_t;
return ctti_type_index(boost::detail::ctti<no_cvr_t>::n());
}
template <class T>
BOOST_CXX14_CONSTEXPR inline ctti_type_index ctti_type_index::type_id_with_cvr() BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline ctti_type_index ctti_type_index::type_id_with_cvr() noexcept {
return ctti_type_index(boost::detail::ctti<T>::n());
}
template <class T>
inline ctti_type_index ctti_type_index::type_id_runtime(const T& variable) BOOST_NOEXCEPT {
inline ctti_type_index ctti_type_index::type_id_runtime(const T& variable) noexcept {
return variable.boost_type_index_type_id_runtime_();
}
BOOST_CXX14_CONSTEXPR inline const char* ctti_type_index::raw_name() const BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline const char* ctti_type_index::raw_name() const noexcept {
return data_;
}
BOOST_CXX14_CONSTEXPR inline const char* ctti_type_index::name() const BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline const char* ctti_type_index::name() const noexcept {
return data_;
}
inline std::size_t ctti_type_index::get_raw_name_length() const BOOST_NOEXCEPT {
return std::strlen(raw_name() + detail::ctti_skip_size_at_end);
inline std::size_t ctti_type_index::get_raw_name_length() const noexcept {
return std::strlen(raw_name() + detail::skip().size_at_end);
}
@ -202,7 +193,7 @@ inline std::string ctti_type_index::pretty_name() const {
}
inline std::size_t ctti_type_index::hash_code() const BOOST_NOEXCEPT {
inline std::size_t ctti_type_index::hash_code() const noexcept {
return boost::hash_range(raw_name(), raw_name() + get_raw_name_length());
}

View File

@ -1,5 +1,5 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
@ -13,10 +13,10 @@
/// \brief Contains helper macros and implementation details of boost::typeindex::ctti_type_index.
/// Not intended for inclusion from user's code.
#include <cstring>
#include <boost/config.hpp>
#include <boost/static_assert.hpp>
#include <boost/type_traits/integral_constant.hpp>
#include <cstring>
#include <type_traits>
#ifdef BOOST_HAS_PRAGMA_ONCE
# pragma once
@ -35,74 +35,87 @@
#define BOOST_TYPE_INDEX_DETAIL_BUILTIN_STRCMP(str1, str2) __builtin_strcmp(str1, str2)
#endif
#define BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(begin_skip, end_skip, runtime_skip, runtime_skip_until) \
namespace boost { namespace typeindex { namespace detail { \
BOOST_STATIC_CONSTEXPR std::size_t ctti_skip_size_at_begin = begin_skip; \
BOOST_STATIC_CONSTEXPR std::size_t ctti_skip_size_at_end = end_skip; \
BOOST_STATIC_CONSTEXPR bool ctti_skip_more_at_runtime = runtime_skip; \
BOOST_STATIC_CONSTEXPR char ctti_skip_until_runtime[] = runtime_skip_until; \
}}} /* namespace boost::typeindex::detail */ \
/**/
/// @endcond
namespace boost { namespace typeindex { namespace detail {
struct ctti_skip {
std::size_t size_at_begin;
std::size_t size_at_end;
const char* until_runtime;
std::size_t until_runtime_length;
};
template <std::size_t N>
constexpr ctti_skip make_ctti_skip(std::size_t size_at_begin,
std::size_t size_at_end,
bool more_at_runtime,
const char (&until_runtime)[N])
{
return ctti_skip{size_at_begin, size_at_end, until_runtime, more_at_runtime ? N - 1 : 0};
}
template <std::size_t N>
constexpr ctti_skip make_ctti_skip(std::size_t size_at_begin,
std::size_t size_at_end,
const char (&until_runtime)[N])
{
return ctti_skip{size_at_begin, size_at_end, until_runtime, N - 1};
}
#if defined(BOOST_TYPE_INDEX_DOXYGEN_INVOKED)
/* Nothing to document. All the macro docs are moved to <boost/type_index.hpp> */
#elif defined(BOOST_TYPE_INDEX_CTTI_USER_DEFINED_PARSING)
# include <boost/preprocessor/facilities/expand.hpp>
BOOST_PP_EXPAND( BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS BOOST_TYPE_INDEX_CTTI_USER_DEFINED_PARSING )
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip BOOST_TYPE_INDEX_CTTI_USER_DEFINED_PARSING; }
#elif defined(_MSC_VER) && !defined(__clang__) && defined (BOOST_NO_CXX11_NOEXCEPT)
// sizeof("const char *__cdecl boost::detail::ctti<") - 1, sizeof(">::n(void)") - 1
BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(40, 10, false, "")
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip(40, 10, ""); }
#elif defined(_MSC_VER) && !defined(__clang__) && !defined (BOOST_NO_CXX11_NOEXCEPT)
// sizeof("const char *__cdecl boost::detail::ctti<") - 1, sizeof(">::n(void) noexcept") - 1
BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(40, 19, false, "")
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip(40, 19, ""); }
#elif defined(__clang__) && defined(__APPLE__)
// Someone made __clang_major__ equal to LLVM version rather than compiler version
// on APPLE platform.
//
// Using less efficient solution because there is no good way to detect real version of Clang.
// sizeof("static const char *boost::detail::ctti<") - 1, sizeof("]") - 1, true, "???????????>::n() [T = int"
BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(39, 1, true, "T = ")
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip(39, 1, "T = "); }
#elif defined(__clang__) && (__clang_major__ < 3 || (__clang_major__ == 3 && __clang_minor__ == 0))
// sizeof("static const char *boost::detail::ctti<") - 1, sizeof(">::n()") - 1
// note: checked on 3.0
BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(39, 6, false, "")
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip(39, 6, ""); }
#elif defined(__clang__) && (__clang_major__ >= 4 || (__clang_major__ == 3 && __clang_minor__ > 0))
// sizeof("static const char *boost::detail::ctti<") - 1, sizeof("]") - 1, true, "int>::n() [T = int"
// note: checked on 3.1, 3.4
BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(39, 1, true, "T = ")
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip(39, 1, "T = "); }
#elif defined(__EDG__) && !defined(BOOST_NO_CXX14_CONSTEXPR)
// sizeof("static cha boost::detail::ctti<T>::s() [with I = 40U, T = ") - 1, sizeof("]") - 1
// note: checked on 4.14
BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(58, 1, false, "")
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip(58, 1, ""); }
#elif defined(__EDG__) && defined(BOOST_NO_CXX14_CONSTEXPR)
// sizeof("static const char *boost::detail::ctti<T>::n() [with T = ") - 1, sizeof("]") - 1
// note: checked on 4.14
BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(57, 1, false, "")
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip(57, 1, ""); }
#elif defined(__GNUC__) && (__GNUC__ < 7) && !defined(BOOST_NO_CXX14_CONSTEXPR)
// sizeof("static constexpr char boost::detail::ctti<T>::s() [with unsigned int I = 0u; T = ") - 1, sizeof("]") - 1
BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(81, 1, false, "")
// sizeof("static constexpr char boost::detail::ctti<T>::s() [with unsigned int I = 0u; } T = ") - 1, sizeof("]") - 1
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip(81, 1, ""); }
#elif defined(__GNUC__) && (__GNUC__ >= 7) && !defined(BOOST_NO_CXX14_CONSTEXPR)
// sizeof("static constexpr char boost::detail::ctti<T>::s() [with unsigned int I = 0; T = ") - 1, sizeof("]") - 1
BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(80, 1, false, "")
// sizeof("static constexpr char boost::detail::ctti<T>::s() [with unsigned int I = 0; } T = ") - 1, sizeof("]") - 1
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip(80, 1, ""); }
#elif defined(__GNUC__) && defined(BOOST_NO_CXX14_CONSTEXPR)
// sizeof("static const char* boost::detail::ctti<T>::n() [with T = ") - 1, sizeof("]") - 1
BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(57, 1, false, "")
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip(57, 1, ""); }
#elif defined(__ghs__)
// sizeof("static const char *boost::detail::ctti<T>::n() [with T = ") - 1, sizeof("]") - 1
BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(57, 1, false, "")
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip(57, 1, ""); }
#else
// Deafult code for other platforms... Just skip nothing!
BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS(0, 0, false, "")
constexpr ctti_skip skip() noexcept { return detail::make_ctti_skip(0, 0, ""); }
#endif
#undef BOOST_TYPE_INDEX_REGISTER_CTTI_PARSING_PARAMS
namespace boost { namespace typeindex { namespace detail {
template <bool Condition>
BOOST_CXX14_CONSTEXPR inline void assert_compile_time_legths() BOOST_NOEXCEPT {
BOOST_STATIC_ASSERT_MSG(
BOOST_CXX14_CONSTEXPR inline void assert_compile_time_legths() noexcept {
static_assert(
Condition,
"TypeIndex library is misconfigured for your compiler. "
"Please define BOOST_TYPE_INDEX_CTTI_USER_DEFINED_PARSING to correct values. See section "
@ -111,8 +124,8 @@ namespace boost { namespace typeindex { namespace detail {
}
template <class T>
BOOST_CXX14_CONSTEXPR inline void failed_to_get_function_name() BOOST_NOEXCEPT {
BOOST_STATIC_ASSERT_MSG(
BOOST_CXX14_CONSTEXPR inline void failed_to_get_function_name() noexcept {
static_assert(
sizeof(T) && false,
"TypeIndex library could not detect your compiler. "
"Please make the BOOST_TYPE_INDEX_FUNCTION_SIGNATURE macro use "
@ -122,7 +135,7 @@ namespace boost { namespace typeindex { namespace detail {
}
#if defined(BOOST_TYPE_INDEX_DETAIL_IS_CONSTANT)
BOOST_CXX14_CONSTEXPR BOOST_FORCEINLINE bool is_constant_string(const char* str) BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR BOOST_FORCEINLINE bool is_constant_string(const char* str) noexcept {
while (BOOST_TYPE_INDEX_DETAIL_IS_CONSTANT(*str)) {
if (*str == '\0')
return true;
@ -132,17 +145,12 @@ namespace boost { namespace typeindex { namespace detail {
}
#endif // defined(BOOST_TYPE_INDEX_DETAIL_IS_CONSTANT)
template <unsigned int ArrayLength>
BOOST_CXX14_CONSTEXPR inline const char* skip_begining_runtime(const char* begin, boost::false_type) BOOST_NOEXCEPT {
return begin;
}
template<class ForwardIterator1, class ForwardIterator2>
BOOST_CXX14_CONSTEXPR inline ForwardIterator1 constexpr_search(
ForwardIterator1 first1,
ForwardIterator1 last1,
ForwardIterator2 first2,
ForwardIterator2 last2) BOOST_NOEXCEPT
ForwardIterator2 last2) noexcept
{
if (first2 == last2) {
return first1; // specified in C++11
@ -165,7 +173,7 @@ namespace boost { namespace typeindex { namespace detail {
return last1;
}
BOOST_CXX14_CONSTEXPR inline int constexpr_strcmp_loop(const char *v1, const char *v2) BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline int constexpr_strcmp_loop(const char *v1, const char *v2) noexcept {
while (*v1 != '\0' && *v1 == *v2) {
++v1;
++v2;
@ -174,7 +182,7 @@ namespace boost { namespace typeindex { namespace detail {
return static_cast<int>(*v1) - *v2;
}
BOOST_CXX14_CONSTEXPR inline int constexpr_strcmp(const char *v1, const char *v2) BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline int constexpr_strcmp(const char *v1, const char *v2) noexcept {
#if !defined(BOOST_NO_CXX14_CONSTEXPR) && defined(BOOST_TYPE_INDEX_DETAIL_IS_CONSTANT) && defined(BOOST_TYPE_INDEX_DETAIL_BUILTIN_STRCMP)
if (boost::typeindex::detail::is_constant_string(v1) && boost::typeindex::detail::is_constant_string(v2))
return boost::typeindex::detail::constexpr_strcmp_loop(v1, v2);
@ -187,21 +195,22 @@ namespace boost { namespace typeindex { namespace detail {
}
template <unsigned int ArrayLength>
BOOST_CXX14_CONSTEXPR inline const char* skip_begining_runtime(const char* begin, boost::true_type) BOOST_NOEXCEPT {
const char* const it = constexpr_search(
BOOST_CXX14_CONSTEXPR inline const char* skip_begining_runtime(const char* begin) noexcept {
constexpr auto skip_value = detail::skip(); // to have the same `.until_runtime` value in code below
const char* const it = detail::constexpr_search(
begin, begin + ArrayLength,
ctti_skip_until_runtime, ctti_skip_until_runtime + sizeof(ctti_skip_until_runtime) - 1
skip_value.until_runtime, skip_value.until_runtime + skip_value.until_runtime_length
);
return (it == begin + ArrayLength ? begin : it + sizeof(ctti_skip_until_runtime) - 1);
return (it == begin + ArrayLength ? begin : it + skip_value.until_runtime_length);
}
template <unsigned int ArrayLength>
BOOST_CXX14_CONSTEXPR inline const char* skip_begining(const char* begin) BOOST_NOEXCEPT {
assert_compile_time_legths<(ArrayLength > ctti_skip_size_at_begin + ctti_skip_size_at_end)>();
return skip_begining_runtime<ArrayLength - ctti_skip_size_at_begin>(
begin + ctti_skip_size_at_begin,
boost::integral_constant<bool, ctti_skip_more_at_runtime>()
);
BOOST_CXX14_CONSTEXPR inline const char* skip_begining(const char* begin) noexcept {
detail::assert_compile_time_legths<(ArrayLength > skip().size_at_begin + skip().size_at_end)>();
return skip().until_runtime_length
? detail::skip_begining_runtime<ArrayLength - skip().size_at_begin>(begin + skip().size_at_begin)
: begin + skip().size_at_begin
;
}
#if !defined(__clang__) && defined(__GNUC__) && !defined(BOOST_NO_CXX14_CONSTEXPR)
@ -257,7 +266,7 @@ struct ctti {
#if !defined(__clang__) && defined(__GNUC__) && !defined(BOOST_NO_CXX14_CONSTEXPR)
//helper functions
template <unsigned int I>
constexpr static char s() BOOST_NOEXCEPT { // step
constexpr static char s() noexcept { // step
constexpr unsigned int offset =
(I >= 10u ? 1u : 0u)
+ (I >= 100u ? 1u : 0u)
@ -277,12 +286,12 @@ struct ctti {
}
template <unsigned int ...Indexes>
constexpr static const char* impl(::boost::typeindex::detail::index_seq<Indexes...> ) BOOST_NOEXCEPT {
constexpr static const char* impl(::boost::typeindex::detail::index_seq<Indexes...> ) noexcept {
return ::boost::typeindex::detail::cstring<s<Indexes>()...>::data_;
}
template <unsigned int D = 0> // `D` means `Dummy`
constexpr static const char* n() BOOST_NOEXCEPT {
constexpr static const char* n() noexcept {
#if defined(BOOST_TYPE_INDEX_FUNCTION_SIGNATURE)
constexpr unsigned int size = sizeof(BOOST_TYPE_INDEX_FUNCTION_SIGNATURE);
#elif defined(__FUNCSIG__)
@ -300,19 +309,19 @@ struct ctti {
#endif
boost::typeindex::detail::assert_compile_time_legths<
(size > boost::typeindex::detail::ctti_skip_size_at_begin + boost::typeindex::detail::ctti_skip_size_at_end + sizeof("const *") - 1)
(size > boost::typeindex::detail::skip().size_at_begin + boost::typeindex::detail::skip().size_at_end + sizeof("const *") - 1)
>();
static_assert(!boost::typeindex::detail::ctti_skip_more_at_runtime, "Skipping for GCC in C++14 mode is unsupported");
static_assert(!boost::typeindex::detail::skip().until_runtime_length, "Skipping for GCC in C++14 mode is unsupported");
typedef typename boost::typeindex::detail::make_index_seq_impl<
boost::typeindex::detail::ctti_skip_size_at_begin,
size - sizeof("const *") + 1 - boost::typeindex::detail::ctti_skip_size_at_begin
boost::typeindex::detail::skip().size_at_begin,
size - sizeof("const *") + 1 - boost::typeindex::detail::skip().size_at_begin
>::type idx_seq;
return impl(idx_seq());
}
#else
/// Returns raw name. Must be as short, as possible, to avoid code bloat
BOOST_CXX14_CONSTEXPR static const char* n() BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR static const char* n() noexcept {
#if defined(BOOST_TYPE_INDEX_FUNCTION_SIGNATURE)
return boost::typeindex::detail::skip_begining< sizeof(BOOST_TYPE_INDEX_FUNCTION_SIGNATURE) >(BOOST_TYPE_INDEX_FUNCTION_SIGNATURE);
#elif defined(__FUNCSIG__)
@ -336,4 +345,6 @@ struct ctti {
}} // namespace boost::detail
#endif // BOOST_TYPE_INDEX_DETAIL_COMPILE_TIME_TYPE_INFO_HPP

View File

@ -1,5 +1,5 @@
//
// Copyright 2013-2020 Antony Polukhin.
// Copyright 2013-2025 Antony Polukhin.
//
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
@ -22,17 +22,17 @@
namespace boost { namespace typeindex { namespace detail {
template <class T>
inline const ctti_data& ctti_construct_typeid_ref(const T*) BOOST_NOEXCEPT {
return ctti_construct<T>();
inline const ctti_data& ctti_construct_typeid_ref(const T*) noexcept {
return boost::typeindex::ctti_construct<T>();
}
}}} // namespace boost::typeindex::detail
/// @cond
#define BOOST_TYPE_INDEX_REGISTER_CLASS \
virtual const boost::typeindex::detail::ctti_data& boost_type_index_type_id_runtime_() const BOOST_NOEXCEPT { \
return boost::typeindex::detail::ctti_construct_typeid_ref(this); \
} \
#define BOOST_TYPE_INDEX_REGISTER_CLASS \
virtual const boost::typeindex::detail::ctti_data& boost_type_index_type_id_runtime_() const noexcept { \
return boost::typeindex::detail::ctti_construct_typeid_ref(this); \
} \
/**/
/// @endcond

View File

@ -1,5 +1,5 @@
//
// Copyright 2013-2020 Antony Polukhin.
// Copyright 2013-2025 Antony Polukhin.
//
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
@ -22,17 +22,17 @@
namespace boost { namespace typeindex { namespace detail {
template <class T>
inline const stl_type_index::type_info_t& stl_construct_typeid_ref(const T*) BOOST_NOEXCEPT {
inline const stl_type_index::type_info_t& stl_construct_typeid_ref(const T*) noexcept {
return typeid(T);
}
}}} // namespace boost::typeindex::detail
/// @cond
#define BOOST_TYPE_INDEX_REGISTER_CLASS \
virtual const boost::typeindex::stl_type_index::type_info_t& boost_type_index_type_id_runtime_() const BOOST_NOEXCEPT { \
return boost::typeindex::detail::stl_construct_typeid_ref(this); \
} \
#define BOOST_TYPE_INDEX_REGISTER_CLASS \
virtual const boost::typeindex::stl_type_index::type_info_t& boost_type_index_type_id_runtime_() const noexcept { \
return boost::typeindex::detail::stl_construct_typeid_ref(this); \
} \
/**/
/// @endcond

View File

@ -14,13 +14,17 @@
/// boost::shared_ptr types.
#include <boost/type_index/runtime_cast/detail/runtime_cast_impl.hpp>
#include <boost/type_traits/is_base_and_derived.hpp>
#include <boost/smart_ptr/shared_ptr.hpp>
#include <type_traits>
#ifdef BOOST_HAS_PRAGMA_ONCE
# pragma once
#endif
namespace boost {
template<class T> class shared_ptr;
}
namespace boost { namespace typeindex {
/// \brief Creates a new instance of std::shared_ptr whose stored pointer is obtained from u's
@ -35,7 +39,7 @@ namespace boost { namespace typeindex {
/// If no such conversion exists, returns boost::shared_ptr<T>();
template<typename T, typename U>
boost::shared_ptr<T> runtime_pointer_cast(boost::shared_ptr<U> const& u) {
T* value = detail::runtime_cast_impl<T>(u.get(), boost::is_base_and_derived<T, U>());
T* value = detail::runtime_cast_impl<T>(u.get(), std::is_base_of<T, U>());
if(value)
return boost::shared_ptr<T>(u, value);
return boost::shared_ptr<T>();

View File

@ -18,7 +18,8 @@
/// desire opt in functionality instead of enabling it system wide.
#include <boost/type_index.hpp>
#include <boost/type_traits/integral_constant.hpp>
#include <type_traits>
#ifdef BOOST_HAS_PRAGMA_ONCE
# pragma once
@ -29,24 +30,24 @@ namespace boost { namespace typeindex {
namespace detail {
template<typename T, typename U>
T* runtime_cast_impl(U* u, boost::true_type) BOOST_NOEXCEPT {
T* runtime_cast_impl(U* u, std::integral_constant<bool, true>) noexcept {
return u;
}
template<typename T, typename U>
T const* runtime_cast_impl(U const* u, boost::true_type) BOOST_NOEXCEPT {
T const* runtime_cast_impl(U const* u, std::integral_constant<bool, true>) noexcept {
return u;
}
template<typename T, typename U>
T* runtime_cast_impl(U* u, boost::false_type) BOOST_NOEXCEPT {
T* runtime_cast_impl(U* u, std::integral_constant<bool, false>) noexcept {
return const_cast<T*>(static_cast<T const*>(
u->boost_type_index_find_instance_(boost::typeindex::type_id<T>())
));
}
template<typename T, typename U>
T const* runtime_cast_impl(U const* u, boost::false_type) BOOST_NOEXCEPT {
T const* runtime_cast_impl(U const* u, std::integral_constant<bool, false>) noexcept {
return static_cast<T const*>(u->boost_type_index_find_instance_(boost::typeindex::type_id<T>()));
}

View File

@ -14,8 +14,7 @@
/// pointer types.
#include <boost/type_index.hpp>
#include <boost/type_index/runtime_cast/detail/runtime_cast_impl.hpp>
#include <boost/type_traits/is_base_and_derived.hpp>
#include <boost/type_traits/remove_pointer.hpp>
#ifdef BOOST_HAS_PRAGMA_ONCE
# pragma once
@ -27,22 +26,22 @@ namespace boost { namespace typeindex {
/// \tparam T The desired target type. Like dynamic_cast, must be a pointer to complete class type.
/// \tparam U A complete class type of the source instance, u.
/// \return If there exists a valid conversion from U* to T, returns a T that points to
/// an address suitably offset from u. If no such conversion exists, returns NULL.
/// an address suitably offset from u. If no such conversion exists, returns nullptr.
template<typename T, typename U>
T runtime_cast(U* u) BOOST_NOEXCEPT {
typedef typename boost::remove_pointer<T>::type impl_type;
return detail::runtime_cast_impl<impl_type>(u, boost::is_base_and_derived<T, U>());
T runtime_cast(U* u) noexcept {
typedef typename std::remove_pointer<T>::type impl_type;
return detail::runtime_cast_impl<impl_type>(u, std::is_base_of<T, U>());
}
/// \brief Safely converts pointers to classes up, down, and sideways along the inheritance hierarchy.
/// \tparam T The desired target type. Like dynamic_cast, must be a pointer to complete class type.
/// \tparam U A complete class type of the source instance, u.
/// \return If there exists a valid conversion from U* to T, returns a T that points to
/// an address suitably offset from u. If no such conversion exists, returns NULL.
/// an address suitably offset from u. If no such conversion exists, returns nullptr.
template<typename T, typename U>
T runtime_cast(U const* u) BOOST_NOEXCEPT {
typedef typename boost::remove_pointer<T>::type impl_type;
return detail::runtime_cast_impl<impl_type>(u, boost::is_base_and_derived<T, U>());
T runtime_cast(U const* u) noexcept {
typedef typename std::remove_pointer<T>::type impl_type;
return detail::runtime_cast_impl<impl_type>(u, std::is_base_of<T, U>());
}
/// \brief Safely converts pointers to classes up, down, and sideways along the inheritance
@ -51,10 +50,10 @@ T runtime_cast(U const* u) BOOST_NOEXCEPT {
/// \tparam U A complete class type of the source instance, u.
/// \return If there exists a valid conversion from U const* to T*, returns a T*
/// that points to an address suitably offset from u.
/// If no such conversion exists, returns NULL.
/// If no such conversion exists, returns nullptr.
template<typename T, typename U>
T* runtime_pointer_cast(U* u) BOOST_NOEXCEPT {
return detail::runtime_cast_impl<T>(u, boost::is_base_and_derived<T, U>());
T* runtime_pointer_cast(U* u) noexcept {
return detail::runtime_cast_impl<T>(u, std::is_base_of<T, U>());
}
/// \brief Safely converts pointers to classes up, down, and sideways along the inheritance
@ -63,10 +62,10 @@ T* runtime_pointer_cast(U* u) BOOST_NOEXCEPT {
/// \tparam U A complete class type of the source instance, u.
/// \return If there exists a valid conversion from U const* to T const*, returns a T const*
/// that points to an address suitably offset from u.
/// If no such conversion exists, returns NULL.
/// If no such conversion exists, returns nullptr.
template<typename T, typename U>
T const* runtime_pointer_cast(U const* u) BOOST_NOEXCEPT {
return detail::runtime_cast_impl<T>(u, boost::is_base_and_derived<T, U>());
T const* runtime_pointer_cast(U const* u) noexcept {
return detail::runtime_cast_impl<T>(u, std::is_base_of<T, U>());
}
}} // namespace boost::typeindex

View File

@ -13,12 +13,11 @@
/// \brief Contains the overload of boost::typeindex::runtime_cast for
/// reference types.
#include <boost/core/addressof.hpp>
#include <boost/type_index/runtime_cast/detail/runtime_cast_impl.hpp>
#include <boost/throw_exception.hpp>
#include <boost/type_traits/add_reference.hpp>
#include <boost/type_traits/remove_reference.hpp>
#include <boost/type_traits/is_base_and_derived.hpp>
#include <memory>
#include <type_traits>
#ifdef BOOST_HAS_PRAGMA_ONCE
# pragma once
@ -28,7 +27,7 @@ namespace boost { namespace typeindex {
/// \brief Indicates that runtime_cast was unable to perform the desired cast operation
/// because the source instance was not also an instance of the target type.
struct bad_runtime_cast : std::exception
struct BOOST_SYMBOL_VISIBLE bad_runtime_cast : std::exception
{};
/// \brief Safely converts references to classes up, down, and sideways along the inheritance hierarchy.
@ -37,10 +36,10 @@ struct bad_runtime_cast : std::exception
/// \return If there exists a valid conversion from U& to T, returns a T that references an address
/// suitably offset from u. If no such conversion exists, throws boost::typeindex::bad_runtime_cast.
template<typename T, typename U>
typename boost::add_reference<T>::type runtime_cast(U& u) {
typedef typename boost::remove_reference<T>::type impl_type;
typename std::add_lvalue_reference<T>::type runtime_cast(U& u) {
typedef typename std::remove_reference<T>::type impl_type;
impl_type* value = detail::runtime_cast_impl<impl_type>(
boost::addressof(u), boost::is_base_and_derived<T, U>());
std::addressof(u), std::is_base_of<T, U>());
if(!value)
BOOST_THROW_EXCEPTION(bad_runtime_cast());
return *value;
@ -52,10 +51,10 @@ typename boost::add_reference<T>::type runtime_cast(U& u) {
/// \return If there exists a valid conversion from U const& to T const, returns a T const that references an address
/// suitably offset from u. If no such conversion exists, throws boost::typeindex::bad_runtime_cast.
template<typename T, typename U>
typename boost::add_reference<const T>::type runtime_cast(U const& u) {
typedef typename boost::remove_reference<T>::type impl_type;
typename std::add_lvalue_reference<const T>::type runtime_cast(U const& u) {
typedef typename std::remove_reference<T>::type impl_type;
impl_type* value = detail::runtime_cast_impl<impl_type>(
boost::addressof(u), boost::is_base_and_derived<T, U>());
std::addressof(u), std::is_base_of<T, U>());
if(!value)
BOOST_THROW_EXCEPTION(bad_runtime_cast());
return *value;

View File

@ -13,31 +13,34 @@
/// \brief Contains the macros BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST and
/// BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS
#include <boost/type_index.hpp>
#include <boost/preprocessor/seq/for_each.hpp>
#ifdef BOOST_HAS_PRAGMA_ONCE
# pragma once
#endif
namespace boost { namespace typeindex {
namespace detail {
namespace boost { namespace typeindex { namespace detail {
template<typename T>
inline type_index runtime_class_construct_type_id(T const*) {
return type_id<T>();
return boost::typeindex::type_id<T>();
}
} // namespace detail
template <class Self>
constexpr const void* find_instance(boost::typeindex::type_index const&, const Self*) noexcept {
return nullptr;
}
}} // namespace boost::typeindex
template <class Base, class... OtherBases, class Self>
const void* find_instance(boost::typeindex::type_index const& idx, const Self* self) noexcept {
if (const void* ptr = self->Base::boost_type_index_find_instance_(idx)) {
return ptr;
}
/// @cond
return boost::typeindex::detail::find_instance<OtherBases...>(idx, self);
}
#define BOOST_TYPE_INDEX_CHECK_BASE_(r, data, Base) \
if(void const* ret_val = this->Base::boost_type_index_find_instance_(idx)) return ret_val;
}}} // namespace boost::typeindex::detail
/// @endcond
/// \def BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS
/// \brief Macro used to make a class compatible with boost::typeindex::runtime_cast
@ -55,21 +58,21 @@ inline type_index runtime_class_construct_type_id(T const*) {
/// \b Example:
/// \code
/// struct base1 {
/// BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(BOOST_TYPE_INDEX_NO_BASE_CLASS)
/// BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS()
/// virtual ~base1();
/// };
///
/// struct base2 {
/// BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(BOOST_TYPE_INDEX_NO_BASE_CLASS)
/// BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS()
/// virtual ~base2();
/// };
///
/// struct derived1 : base1 {
/// BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS((base1))
/// BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(base1)
/// };
///
/// struct derived2 : base1, base2 {
/// BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS((base1)(base2))
/// BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(base1, base2)
/// };
///
/// ...
@ -82,9 +85,9 @@ inline type_index runtime_class_construct_type_id(T const*) {
///
/// \param base_class_seq A Boost.Preprocessor sequence of the current class' direct bases, or
/// BOOST_TYPE_INDEX_NO_BASE_CLASS if this class has no direct base classes.
#define BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(base_class_seq) \
BOOST_TYPE_INDEX_REGISTER_CLASS \
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(base_class_seq)
#define BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(...) \
BOOST_TYPE_INDEX_REGISTER_CLASS \
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(__VA_ARGS__)
/// \def BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST
/// \brief Macro used to make a class compatible with boost::typeindex::runtime_cast without including
@ -96,21 +99,21 @@ inline type_index runtime_class_construct_type_id(T const*) {
/// \b Example:
/// \code
/// struct base1 {
/// BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(BOOST_TYPE_INDEX_NO_BASE_CLASS)
/// BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST()
/// virtual ~base1();
/// };
///
/// struct base2 {
/// BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(BOOST_TYPE_INDEX_NO_BASE_CLASS)
/// BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST()
/// virtual ~base2();
/// };
///
/// struct derived1 : base1 {
/// BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST((base1))
/// BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(base1)
/// };
///
/// struct derived2 : base1, base2 {
/// BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST((base1)(base2))
/// BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(base1, base2)
/// };
///
/// ...
@ -122,17 +125,17 @@ inline type_index runtime_class_construct_type_id(T const*) {
///
/// \param base_class_seq A Boost.Preprocessor sequence of the current class' direct bases, or
/// BOOST_TYPE_INDEX_NO_BASE_CLASS if this class has no direct base classes.
#define BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(base_class_seq) \
virtual void const* boost_type_index_find_instance_(boost::typeindex::type_index const& idx) const BOOST_NOEXCEPT { \
if(idx == boost::typeindex::detail::runtime_class_construct_type_id(this)) \
return this; \
BOOST_PP_SEQ_FOR_EACH(BOOST_TYPE_INDEX_CHECK_BASE_, _, base_class_seq) \
return NULL; \
#define BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(...) \
virtual void const* boost_type_index_find_instance_(boost::typeindex::type_index const& idx) const noexcept { \
if(idx == boost::typeindex::detail::runtime_class_construct_type_id(this)) \
return this; \
return boost::typeindex::detail::find_instance<__VA_ARGS__>(idx, this); \
}
/// \def BOOST_TYPE_INDEX_NO_BASE_CLASS
/// \brief Instructs BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS and BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST
/// that this class has no base classes.
#define BOOST_TYPE_INDEX_NO_BASE_CLASS BOOST_PP_SEQ_NIL
/// \deprecated Just remove and use BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS() or BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST()
#define BOOST_TYPE_INDEX_NO_BASE_CLASS /**/
#endif // BOOST_TYPE_INDEX_RUNTIME_CAST_REGISTER_RUNTIME_CLASS_HPP

View File

@ -14,7 +14,6 @@
/// std::shared_ptr types.
#include <boost/type_index/runtime_cast/detail/runtime_cast_impl.hpp>
#include <boost/type_traits/is_base_and_derived.hpp>
#include <memory>
#ifdef BOOST_HAS_PRAGMA_ONCE
@ -35,7 +34,7 @@ namespace boost { namespace typeindex {
/// If no such conversion exists, returns std::shared_ptr<T>();
template<typename T, typename U>
std::shared_ptr<T> runtime_pointer_cast(std::shared_ptr<U> const& u) {
T* value = detail::runtime_cast_impl<T>(u.get(), boost::is_base_and_derived<T, U>());
T* value = detail::runtime_cast_impl<T>(u.get(), std::is_base_of<T, U>());
if(value)
return std::shared_ptr<T>(u, value);
return std::shared_ptr<T>();

View File

@ -1,5 +1,5 @@
//
// Copyright 2013-2020 Antony Polukhin.
// Copyright 2013-2025 Antony Polukhin.
//
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
@ -29,30 +29,9 @@
#include <typeinfo>
#include <cstring> // std::strcmp, std::strlen, std::strstr
#include <stdexcept>
#include <boost/static_assert.hpp>
#include <type_traits>
#include <boost/throw_exception.hpp>
#include <boost/core/demangle.hpp>
#include <boost/type_traits/conditional.hpp>
#include <boost/type_traits/is_const.hpp>
#include <boost/type_traits/is_reference.hpp>
#include <boost/type_traits/is_volatile.hpp>
#include <boost/type_traits/remove_cv.hpp>
#include <boost/type_traits/remove_reference.hpp>
#if (defined(_MSC_VER) && _MSC_VER > 1600) \
|| (defined(__GNUC__) && __GNUC__ == 4 && __GNUC_MINOR__ > 5 && defined(__GXX_EXPERIMENTAL_CXX0X__)) \
|| (defined(__GNUC__) && __GNUC__ > 4 && __cplusplus >= 201103)
# define BOOST_TYPE_INDEX_STD_TYPE_INDEX_HAS_HASH_CODE
#else
# include <boost/container_hash/hash.hpp>
#endif
#if (defined(__EDG_VERSION__) && __EDG_VERSION__ < 245) \
|| (defined(__sgi) && defined(_COMPILER_VERSION) && _COMPILER_VERSION <= 744)
# include <boost/type_traits/is_signed.hpp>
# include <boost/type_traits/make_signed.hpp>
# include <boost/type_traits/type_identity.hpp>
#endif
#ifdef BOOST_HAS_PRAGMA_ONCE
# pragma once
@ -86,40 +65,40 @@ private:
const type_info_t* data_;
public:
inline stl_type_index() BOOST_NOEXCEPT
inline stl_type_index() noexcept
: data_(&typeid(void))
{}
inline stl_type_index(const type_info_t& data) BOOST_NOEXCEPT
inline stl_type_index(const type_info_t& data) noexcept
: data_(&data)
{}
inline const type_info_t& type_info() const BOOST_NOEXCEPT;
inline const type_info_t& type_info() const noexcept;
inline const char* raw_name() const BOOST_NOEXCEPT;
inline const char* name() const BOOST_NOEXCEPT;
inline const char* raw_name() const noexcept;
inline const char* name() const noexcept;
inline std::string pretty_name() const;
inline std::size_t hash_code() const BOOST_NOEXCEPT;
inline bool equal(const stl_type_index& rhs) const BOOST_NOEXCEPT;
inline bool before(const stl_type_index& rhs) const BOOST_NOEXCEPT;
inline std::size_t hash_code() const noexcept;
inline bool equal(const stl_type_index& rhs) const noexcept;
inline bool before(const stl_type_index& rhs) const noexcept;
template <class T>
inline static stl_type_index type_id() BOOST_NOEXCEPT;
inline static stl_type_index type_id() noexcept;
template <class T>
inline static stl_type_index type_id_with_cvr() BOOST_NOEXCEPT;
inline static stl_type_index type_id_with_cvr() noexcept;
template <class T>
inline static stl_type_index type_id_runtime(const T& value) BOOST_NOEXCEPT;
inline static stl_type_index type_id_runtime(const T& value) noexcept;
};
inline const stl_type_index::type_info_t& stl_type_index::type_info() const BOOST_NOEXCEPT {
inline const stl_type_index::type_info_t& stl_type_index::type_info() const noexcept {
return *data_;
}
inline const char* stl_type_index::raw_name() const BOOST_NOEXCEPT {
inline const char* stl_type_index::raw_name() const noexcept {
#ifdef _MSC_VER
return data_->raw_name();
#else
@ -127,7 +106,7 @@ inline const char* stl_type_index::raw_name() const BOOST_NOEXCEPT {
#endif
}
inline const char* stl_type_index::name() const BOOST_NOEXCEPT {
inline const char* stl_type_index::name() const noexcept {
return data_->name();
}
@ -180,12 +159,8 @@ inline std::string stl_type_index::pretty_name() const {
}
inline std::size_t stl_type_index::hash_code() const BOOST_NOEXCEPT {
#ifdef BOOST_TYPE_INDEX_STD_TYPE_INDEX_HAS_HASH_CODE
inline std::size_t stl_type_index::hash_code() const noexcept {
return data_->hash_code();
#else
return boost::hash_range(raw_name(), raw_name() + std::strlen(raw_name()));
#endif
}
@ -203,7 +178,7 @@ inline std::size_t stl_type_index::hash_code() const BOOST_NOEXCEPT {
/// @endcond
inline bool stl_type_index::equal(const stl_type_index& rhs) const BOOST_NOEXCEPT {
inline bool stl_type_index::equal(const stl_type_index& rhs) const noexcept {
#ifdef BOOST_TYPE_INDEX_CLASSINFO_COMPARE_BY_NAMES
return raw_name() == rhs.raw_name() || !std::strcmp(raw_name(), rhs.raw_name());
#else
@ -211,7 +186,7 @@ inline bool stl_type_index::equal(const stl_type_index& rhs) const BOOST_NOEXCEP
#endif
}
inline bool stl_type_index::before(const stl_type_index& rhs) const BOOST_NOEXCEPT {
inline bool stl_type_index::before(const stl_type_index& rhs) const noexcept {
#ifdef BOOST_TYPE_INDEX_CLASSINFO_COMPARE_BY_NAMES
return raw_name() != rhs.raw_name() && std::strcmp(raw_name(), rhs.raw_name()) < 0;
#else
@ -223,26 +198,9 @@ inline bool stl_type_index::before(const stl_type_index& rhs) const BOOST_NOEXCE
template <class T>
inline stl_type_index stl_type_index::type_id() BOOST_NOEXCEPT {
typedef BOOST_DEDUCED_TYPENAME boost::remove_reference<T>::type no_ref_t;
typedef BOOST_DEDUCED_TYPENAME boost::remove_cv<no_ref_t>::type no_cvr_prefinal_t;
# if (defined(__EDG_VERSION__) && __EDG_VERSION__ < 245) \
|| (defined(__sgi) && defined(_COMPILER_VERSION) && _COMPILER_VERSION <= 744)
// Old EDG-based compilers seem to mistakenly distinguish 'integral' from 'signed integral'
// in typeid() expressions. Full template specialization for 'integral' fixes that issue:
typedef BOOST_DEDUCED_TYPENAME boost::conditional<
boost::is_signed<no_cvr_prefinal_t>::value,
boost::make_signed<no_cvr_prefinal_t>,
boost::type_identity<no_cvr_prefinal_t>
>::type no_cvr_prefinal_lazy_t;
typedef BOOST_DEDUCED_TYPENAME no_cvr_prefinal_t::type no_cvr_t;
#else
typedef no_cvr_prefinal_t no_cvr_t;
#endif
inline stl_type_index stl_type_index::type_id() noexcept {
typedef typename std::remove_reference<T>::type no_ref_t;
typedef typename std::remove_cv<no_ref_t>::type no_cvr_t;
return typeid(no_cvr_t);
}
@ -251,9 +209,9 @@ namespace detail {
}
template <class T>
inline stl_type_index stl_type_index::type_id_with_cvr() BOOST_NOEXCEPT {
typedef BOOST_DEDUCED_TYPENAME boost::conditional<
boost::is_reference<T>::value || boost::is_const<T>::value || boost::is_volatile<T>::value,
inline stl_type_index stl_type_index::type_id_with_cvr() noexcept {
typedef typename std::conditional<
std::is_reference<T>::value || std::is_const<T>::value || std::is_volatile<T>::value,
detail::cvr_saver<T>,
T
>::type type;
@ -263,7 +221,7 @@ inline stl_type_index stl_type_index::type_id_with_cvr() BOOST_NOEXCEPT {
template <class T>
inline stl_type_index stl_type_index::type_id_runtime(const T& value) BOOST_NOEXCEPT {
inline stl_type_index stl_type_index::type_id_runtime(const T& value) noexcept {
#ifdef BOOST_NO_RTTI
return value.boost_type_index_type_id_runtime_();
#else
@ -273,6 +231,4 @@ inline stl_type_index stl_type_index::type_id_runtime(const T& value) BOOST_NOEX
}} // namespace boost::typeindex
#undef BOOST_TYPE_INDEX_STD_TYPE_INDEX_HAS_HASH_CODE
#endif // BOOST_TYPE_INDEX_STL_TYPE_INDEX_HPP

View File

@ -1,5 +1,5 @@
//
// Copyright 2013-2020 Antony Polukhin.
// Copyright 2013-2025 Antony Polukhin.
//
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
@ -13,14 +13,8 @@
#include <boost/container_hash/hash_fwd.hpp>
#include <string>
#include <cstring>
#if !defined(BOOST_NO_IOSTREAM)
#if !defined(BOOST_NO_IOSFWD)
#include <type_traits>
#include <iosfwd> // for std::basic_ostream
#else
#include <ostream>
#endif
#endif
#ifdef BOOST_HAS_PRAGMA_ONCE
# pragma once
@ -62,7 +56,7 @@ template <class Derived, class TypeInfo>
class type_index_facade {
private:
/// @cond
BOOST_CXX14_CONSTEXPR const Derived & derived() const BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR const Derived & derived() const noexcept {
return *static_cast<Derived const*>(this);
}
/// @endcond
@ -71,7 +65,7 @@ public:
/// \b Override: This function \b may be redefined in Derived class. Overrides \b must not throw.
/// \return Name of a type. By default returns Derived::raw_name().
inline const char* name() const BOOST_NOEXCEPT {
inline const char* name() const noexcept {
return derived().raw_name();
}
@ -83,7 +77,7 @@ public:
/// \b Override: This function \b may be redefined in Derived class. Overrides \b must not throw.
/// \return True if two types are equal. By default compares types by raw_name().
inline bool equal(const Derived& rhs) const BOOST_NOEXCEPT {
inline bool equal(const Derived& rhs) const noexcept {
const char* const left = derived().raw_name();
const char* const right = rhs.raw_name();
return left == right || !std::strcmp(left, right);
@ -91,7 +85,7 @@ public:
/// \b Override: This function \b may be redefined in Derived class. Overrides \b must not throw.
/// \return True if rhs is greater than this. By default compares types by raw_name().
inline bool before(const Derived& rhs) const BOOST_NOEXCEPT {
inline bool before(const Derived& rhs) const noexcept {
const char* const left = derived().raw_name();
const char* const right = rhs.raw_name();
return left != right && std::strcmp(left, right) < 0;
@ -101,7 +95,7 @@ public:
/// \return Hash code of a type. By default hashes types by raw_name().
/// \note Derived class header \b must include <boost/container_hash/hash.hpp>, \b unless this function is redefined in
/// Derived class to not use boost::hash_range().
inline std::size_t hash_code() const BOOST_NOEXCEPT {
inline std::size_t hash_code() const noexcept {
const char* const name_raw = derived().raw_name();
return boost::hash_range(name_raw, name_raw + std::strlen(name_raw));
}
@ -110,11 +104,11 @@ public:
protected:
/// \b Override: This function \b must be redefined in Derived class. Overrides \b must not throw.
/// \return Pointer to unredable/raw type name.
inline const char* raw_name() const BOOST_NOEXCEPT;
inline const char* raw_name() const noexcept;
/// \b Override: This function \b may be redefined in Derived class. Overrides \b must not throw.
/// \return Const reference to underlying low level type_info_t.
inline const type_info_t& type_info() const BOOST_NOEXCEPT;
inline const type_info_t& type_info() const noexcept;
/// This is a factory method that is used to create instances of Derived classes.
/// boost::typeindex::type_id() will call this method, if Derived has same type as boost::typeindex::type_index.
@ -124,7 +118,7 @@ protected:
/// \tparam T Type for which type_index must be created.
/// \return type_index for type T.
template <class T>
static Derived type_id() BOOST_NOEXCEPT;
static Derived type_id() noexcept;
/// This is a factory method that is used to create instances of Derived classes.
/// boost::typeindex::type_id_with_cvr() will call this method, if Derived has same type as boost::typeindex::type_index.
@ -134,7 +128,7 @@ protected:
/// \tparam T Type for which type_index must be created.
/// \return type_index for type T.
template <class T>
static Derived type_id_with_cvr() BOOST_NOEXCEPT;
static Derived type_id_with_cvr() noexcept;
/// This is a factory method that is used to create instances of Derived classes.
/// boost::typeindex::type_id_runtime(const T&) will call this method, if Derived has same type as boost::typeindex::type_index.
@ -143,7 +137,7 @@ protected:
/// \param variable Variable which runtime type will be stored in type_index.
/// \return type_index with runtime type of variable.
template <class T>
static Derived type_id_runtime(const T& variable) BOOST_NOEXCEPT;
static Derived type_id_runtime(const T& variable) noexcept;
#endif
@ -151,96 +145,96 @@ protected:
/// @cond
template <class Derived, class TypeInfo>
BOOST_CXX14_CONSTEXPR inline bool operator == (const type_index_facade<Derived, TypeInfo>& lhs, const type_index_facade<Derived, TypeInfo>& rhs) BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline bool operator == (const type_index_facade<Derived, TypeInfo>& lhs, const type_index_facade<Derived, TypeInfo>& rhs) noexcept {
return static_cast<Derived const&>(lhs).equal(static_cast<Derived const&>(rhs));
}
template <class Derived, class TypeInfo>
BOOST_CXX14_CONSTEXPR inline bool operator < (const type_index_facade<Derived, TypeInfo>& lhs, const type_index_facade<Derived, TypeInfo>& rhs) BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline bool operator < (const type_index_facade<Derived, TypeInfo>& lhs, const type_index_facade<Derived, TypeInfo>& rhs) noexcept {
return static_cast<Derived const&>(lhs).before(static_cast<Derived const&>(rhs));
}
template <class Derived, class TypeInfo>
BOOST_CXX14_CONSTEXPR inline bool operator > (const type_index_facade<Derived, TypeInfo>& lhs, const type_index_facade<Derived, TypeInfo>& rhs) BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline bool operator > (const type_index_facade<Derived, TypeInfo>& lhs, const type_index_facade<Derived, TypeInfo>& rhs) noexcept {
return rhs < lhs;
}
template <class Derived, class TypeInfo>
BOOST_CXX14_CONSTEXPR inline bool operator <= (const type_index_facade<Derived, TypeInfo>& lhs, const type_index_facade<Derived, TypeInfo>& rhs) BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline bool operator <= (const type_index_facade<Derived, TypeInfo>& lhs, const type_index_facade<Derived, TypeInfo>& rhs) noexcept {
return !(lhs > rhs);
}
template <class Derived, class TypeInfo>
BOOST_CXX14_CONSTEXPR inline bool operator >= (const type_index_facade<Derived, TypeInfo>& lhs, const type_index_facade<Derived, TypeInfo>& rhs) BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline bool operator >= (const type_index_facade<Derived, TypeInfo>& lhs, const type_index_facade<Derived, TypeInfo>& rhs) noexcept {
return !(lhs < rhs);
}
template <class Derived, class TypeInfo>
BOOST_CXX14_CONSTEXPR inline bool operator != (const type_index_facade<Derived, TypeInfo>& lhs, const type_index_facade<Derived, TypeInfo>& rhs) BOOST_NOEXCEPT {
BOOST_CXX14_CONSTEXPR inline bool operator != (const type_index_facade<Derived, TypeInfo>& lhs, const type_index_facade<Derived, TypeInfo>& rhs) noexcept {
return !(lhs == rhs);
}
// ######################### COMPARISONS with Derived ############################ //
template <class Derived, class TypeInfo>
inline bool operator == (const TypeInfo& lhs, const type_index_facade<Derived, TypeInfo>& rhs) BOOST_NOEXCEPT {
inline bool operator == (const TypeInfo& lhs, const type_index_facade<Derived, TypeInfo>& rhs) noexcept {
return Derived(lhs) == rhs;
}
template <class Derived, class TypeInfo>
inline bool operator < (const TypeInfo& lhs, const type_index_facade<Derived, TypeInfo>& rhs) BOOST_NOEXCEPT {
inline bool operator < (const TypeInfo& lhs, const type_index_facade<Derived, TypeInfo>& rhs) noexcept {
return Derived(lhs) < rhs;
}
template <class Derived, class TypeInfo>
inline bool operator > (const TypeInfo& lhs, const type_index_facade<Derived, TypeInfo>& rhs) BOOST_NOEXCEPT {
inline bool operator > (const TypeInfo& lhs, const type_index_facade<Derived, TypeInfo>& rhs) noexcept {
return rhs < Derived(lhs);
}
template <class Derived, class TypeInfo>
inline bool operator <= (const TypeInfo& lhs, const type_index_facade<Derived, TypeInfo>& rhs) BOOST_NOEXCEPT {
inline bool operator <= (const TypeInfo& lhs, const type_index_facade<Derived, TypeInfo>& rhs) noexcept {
return !(Derived(lhs) > rhs);
}
template <class Derived, class TypeInfo>
inline bool operator >= (const TypeInfo& lhs, const type_index_facade<Derived, TypeInfo>& rhs) BOOST_NOEXCEPT {
inline bool operator >= (const TypeInfo& lhs, const type_index_facade<Derived, TypeInfo>& rhs) noexcept {
return !(Derived(lhs) < rhs);
}
template <class Derived, class TypeInfo>
inline bool operator != (const TypeInfo& lhs, const type_index_facade<Derived, TypeInfo>& rhs) BOOST_NOEXCEPT {
inline bool operator != (const TypeInfo& lhs, const type_index_facade<Derived, TypeInfo>& rhs) noexcept {
return !(Derived(lhs) == rhs);
}
template <class Derived, class TypeInfo>
inline bool operator == (const type_index_facade<Derived, TypeInfo>& lhs, const TypeInfo& rhs) BOOST_NOEXCEPT {
inline bool operator == (const type_index_facade<Derived, TypeInfo>& lhs, const TypeInfo& rhs) noexcept {
return lhs == Derived(rhs);
}
template <class Derived, class TypeInfo>
inline bool operator < (const type_index_facade<Derived, TypeInfo>& lhs, const TypeInfo& rhs) BOOST_NOEXCEPT {
inline bool operator < (const type_index_facade<Derived, TypeInfo>& lhs, const TypeInfo& rhs) noexcept {
return lhs < Derived(rhs);
}
template <class Derived, class TypeInfo>
inline bool operator > (const type_index_facade<Derived, TypeInfo>& lhs, const TypeInfo& rhs) BOOST_NOEXCEPT {
inline bool operator > (const type_index_facade<Derived, TypeInfo>& lhs, const TypeInfo& rhs) noexcept {
return Derived(rhs) < lhs;
}
template <class Derived, class TypeInfo>
inline bool operator <= (const type_index_facade<Derived, TypeInfo>& lhs, const TypeInfo& rhs) BOOST_NOEXCEPT {
inline bool operator <= (const type_index_facade<Derived, TypeInfo>& lhs, const TypeInfo& rhs) noexcept {
return !(lhs > Derived(rhs));
}
template <class Derived, class TypeInfo>
inline bool operator >= (const type_index_facade<Derived, TypeInfo>& lhs, const TypeInfo& rhs) BOOST_NOEXCEPT {
inline bool operator >= (const type_index_facade<Derived, TypeInfo>& lhs, const TypeInfo& rhs) noexcept {
return !(lhs < Derived(rhs));
}
template <class Derived, class TypeInfo>
inline bool operator != (const type_index_facade<Derived, TypeInfo>& lhs, const TypeInfo& rhs) BOOST_NOEXCEPT {
inline bool operator != (const type_index_facade<Derived, TypeInfo>& lhs, const TypeInfo& rhs) noexcept {
return !(lhs == Derived(rhs));
}
@ -262,16 +256,6 @@ bool operator ==, !=, <, ... (const TypeInfo& lhs, const type_index_facade& rhs)
#endif
#ifndef BOOST_NO_IOSTREAM
#ifdef BOOST_NO_TEMPLATED_IOSTREAMS
/// @cond
/// Ostream operator that will output demangled name
template <class Derived, class TypeInfo>
inline std::ostream& operator<<(std::ostream& ostr, const type_index_facade<Derived, TypeInfo>& ind) {
ostr << static_cast<Derived const&>(ind).pretty_name();
return ostr;
}
/// @endcond
#else
/// Ostream operator that will output demangled name.
template <class CharT, class TriatT, class Derived, class TypeInfo>
inline std::basic_ostream<CharT, TriatT>& operator<<(
@ -281,13 +265,12 @@ inline std::basic_ostream<CharT, TriatT>& operator<<(
ostr << static_cast<Derived const&>(ind).pretty_name();
return ostr;
}
#endif // BOOST_NO_TEMPLATED_IOSTREAMS
#endif // BOOST_NO_IOSTREAM
/// This free function is used by Boost's unordered containers.
/// \note <boost/container_hash/hash.hpp> has to be included if this function is used.
template <class Derived, class TypeInfo>
inline std::size_t hash_value(const type_index_facade<Derived, TypeInfo>& lhs) BOOST_NOEXCEPT {
inline std::size_t hash_value(const type_index_facade<Derived, TypeInfo>& lhs) noexcept {
return static_cast<Derived const&>(lhs).hash_code();
}

View File

@ -1,11 +1,13 @@
<!DOCTYPE html>
<!--
Copyright 2014 Antony Polukhin
Copyright 2014-2025 Antony Polukhin
antoshkka at gmail dot com
Distributed under the Boost Software License,
Version 1.0. (See accompanying file LICENSE_1_0.txt
or copy at http://boost.org/LICENSE_1_0.txt)
boost-no-inspect
-->
<html>
<head>
@ -29,7 +31,7 @@
<a href="../../doc/html/boost_typeindex.html">../../doc/html/boost_typeindex.html</a>
</p>
<p>
&copy; 2014 Antony Polukhin
&copy; 2014-2024 Antony Polukhin
</p>
</body>
</html>

View File

@ -10,5 +10,6 @@
"description": "Runtime/Compile time copyable type info.",
"category": [
"Emulation"
]
],
"cxxstd": "11"
}

View File

@ -1,13 +1,24 @@
# Copyright 2012-2020 Antony Polukhin
# Copyright 2012-2025 Antony Polukhin
#
# Distributed under the Boost Software License, Version 1.0. (See accompanying
# file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
#
require-b2 5.0.1 ;
import-search /boost/config/checks ;
import-search /boost/config/checks ;
import config : requires ;
import testing ;
import feature ;
import os ;
project
: source-location .
: requirements
<library>/boost/type_index//boost_type_index
[ requires cxx11_rvalue_references ]
;
# Variable that contains all the stuff required for linking together <rtti>on and <rtti>off
compat = <define>BOOST_TYPE_INDEX_FORCE_NO_RTTI_COMPATIBILITY ;
@ -38,11 +49,11 @@ lib test_lib_rtti_compat : test_lib_rtti_compat-obj : <link>shared $(nortti) $(c
exe testing_crossmodule_anonymous_no_rtti : testing_crossmodule_anonymous.cpp test_lib_anonymous_nortti : <rtti>off $(norttidefines) ;
test-suite type_index
:
[ run type_index_test.cpp ]
[ run type_index_runtime_cast_test.cpp ]
:
[ run type_index_test.cpp /boost/lexical_cast//boost_lexical_cast ]
[ run type_index_runtime_cast_test.cpp /boost/smart_ptr//boost_smart_ptr ]
[ run type_index_constexpr_test.cpp ]
[ run type_index_test.cpp : : : <rtti>off $(norttidefines) : type_index_test_no_rtti ]
[ run type_index_test.cpp /boost/lexical_cast//boost_lexical_cast : : : <rtti>off $(norttidefines) : type_index_test_no_rtti ]
[ run ctti_print_name.cpp : : : <test-info>always_show_run_output ]
[ run testing_crossmodule.cpp test_lib_rtti ]
[ run testing_crossmodule.cpp test_lib_nortti : : : <rtti>off $(norttidefines) : testing_crossmodule_no_rtti ]
@ -57,25 +68,25 @@ test-suite type_index
# Mixing RTTI on and off
# MSVC sometimes overrides the /GR-, without `detect_missmatch` this test may link.
# TODO: Disabled on MSVC. Enable again when there'll be an understanding of how to write this test correctly wor MSVC.
# TODO: Disabled on MSVC. Enable again when there'll be an understanding of how to write this test correctly wor MSVC.
[ link-fail testing_crossmodule.cpp test_lib_rtti : $(nortti) <toolset>msvc:<build>no : link_fail_nortti_rtti ]
[ link-fail testing_crossmodule.cpp test_lib_nortti : <toolset>msvc:<build>no : link_fail_rtti_nortti ]
[ run testing_crossmodule.cpp test_lib_rtti_compat : : : $(nortti) $(compat) : testing_crossmodule_nortti_rtti_compat ]
[ run testing_crossmodule.cpp test_lib_nortti_compat : : : $(compat) : testing_crossmodule_rtti_nortti_compat ]
;
# Assuring that examples compile and run. Adding sources from `examples` directory to the `type_index` test suite.
# Assuring that examples compile and run. Adding sources from `examples` directory to the `type_index` test suite.
for local p in [ glob ../examples/*.cpp ]
{
# RTTI on
type_index += [ run $(p) ] ;
type_index += [ run $(p) /boost/unordered//boost_unordered : : : <include>../examples ] ;
# RTTI off
local target_name = $(p[1]:B)_no_rtti ;
if $(target_name) != "table_of_names_no_rtti"
{
type_index += [ run $(p) : : : <rtti>off $(norttidefines) : $(target_name) ] ;
type_index += [ run $(p) /boost/unordered//boost_unordered : : : <include>../examples <rtti>off $(norttidefines) : $(target_name) ] ;
}
}

View File

@ -2,7 +2,7 @@
# subject to the Boost Software License, Version 1.0. (See accompanying
# file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
#
# Copyright 2016-2020 Antony Polukhin.
# Copyright 2016-2025 Antony Polukhin.
#
# See https://svn.boost.org/trac/boost/wiki/TravisCoverals for description of this file
@ -32,8 +32,6 @@ skip_tags: true
environment:
matrix:
- APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2015
TOOLSET: msvc-9.0,msvc-10.0,msvc-11.0,msvc-12.0
- APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2017
TOOLSET: msvc-14.1,clang-win
CXXSTD: 14,17

View File

@ -1,5 +1,5 @@
// Copyright Klemens Morgenstern, 2012-2015.
// Copyright 2019-2020 Antony Polukhin.
// Copyright 2019-2025 Antony Polukhin.
//
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at

View File

@ -1,5 +1,5 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at

View File

@ -1,5 +1,5 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying

View File

@ -1,5 +1,5 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying

View File

@ -1,5 +1,5 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying

View File

@ -1,5 +1,5 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying

View File

@ -1,5 +1,5 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at

View File

@ -1,5 +1,5 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at

View File

@ -1,5 +1,5 @@
//
// Copyright 2018-2020 Antony Polukhin.
// Copyright 2018-2025 Antony Polukhin.
//
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at

View File

@ -1,5 +1,5 @@
//
// Copyright 2015-2020 Antony Polukhin.
// Copyright 2015-2025 Antony Polukhin.
//
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at

View File

@ -28,81 +28,81 @@
std::string name;
struct base {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(BOOST_TYPE_INDEX_NO_BASE_CLASS)
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST()
IMPLEMENT_CLASS(base)
};
struct single_derived : base {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST((base))
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(base)
IMPLEMENT_CLASS(single_derived)
};
struct base1 {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(BOOST_TYPE_INDEX_NO_BASE_CLASS)
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST()
IMPLEMENT_CLASS(base1)
};
struct base2 {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(BOOST_TYPE_INDEX_NO_BASE_CLASS)
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST()
IMPLEMENT_CLASS(base2)
};
struct multiple_derived : base1, base2 {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST((base1)(base2))
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(base1, base2)
IMPLEMENT_CLASS(multiple_derived)
};
struct baseV1 : virtual base {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST((base))
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(base)
IMPLEMENT_CLASS(baseV1)
};
struct baseV2 : virtual base {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST((base))
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(base)
IMPLEMENT_CLASS(baseV2)
};
struct multiple_virtual_derived : baseV1, baseV2 {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST((baseV1)(baseV2))
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(baseV1, baseV2)
IMPLEMENT_CLASS(multiple_virtual_derived)
};
struct unrelated {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(BOOST_TYPE_INDEX_NO_BASE_CLASS)
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST()
IMPLEMENT_CLASS(unrelated)
};
struct unrelated_with_base : base {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST((base))
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(base)
IMPLEMENT_CLASS(unrelated_with_base)
};
struct unrelatedV1 : virtual base {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST((base))
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(base)
IMPLEMENT_CLASS(unrelatedV1)
};
struct level1_a : base {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST((base))
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(base)
IMPLEMENT_CLASS(level1_a)
};
struct level1_b : base {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST((base))
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(base)
IMPLEMENT_CLASS(level1_b)
};
struct level2 : level1_a, level1_b {
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST((level1_a)(level1_b))
BOOST_TYPE_INDEX_IMPLEMENT_RUNTIME_CAST(level1_a, level1_b)
IMPLEMENT_CLASS(level2)
};
struct reg_base {
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(BOOST_TYPE_INDEX_NO_BASE_CLASS)
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS()
};
struct reg_derived : reg_base {
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS((reg_base))
BOOST_TYPE_INDEX_REGISTER_RUNTIME_CLASS(reg_base)
};
void no_base()

View File

@ -1,5 +1,5 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at

View File

@ -1,16 +1,15 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
#include <boost/type_index/ctti_type_index.hpp>
#include <boost/type_traits/alignment_of.hpp>
int main() {
BOOST_STATIC_ASSERT_MSG(
boost::alignment_of<boost::typeindex::detail::ctti_data>::value == boost::alignment_of<char>::value,
static_assert(
alignof(boost::typeindex::detail::ctti_data) == alignof(char),
"Alignments of boost::typeindex::detail::ctti_data and char differ. "
"It is unsafe to reinterpret_cast between them."
);

View File

@ -1,5 +1,5 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at

View File

@ -1,5 +1,5 @@
//
// Copyright 2012-2020 Antony Polukhin.
// Copyright 2012-2025 Antony Polukhin.
//
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at