update abseil-cpp library, update the folder name of yaml-cpp library
This commit is contained in:
parent
fa56ea3e2c
commit
1bcd41beb5
@ -27,12 +27,13 @@ add_executable(${PROJECT_NAME} ${SOURCE})
|
||||
# Eigen3
|
||||
include_directories(ThirdParty/eigen-3.3.9)
|
||||
|
||||
# yaml-cpp
|
||||
add_subdirectory(ThirdParty/yaml-cpp ThirdParty/yaml-cpp)
|
||||
# yaml-cpp-0.7.0
|
||||
add_subdirectory(ThirdParty/yaml-cpp-0.7.0)
|
||||
target_link_libraries(${PROJECT_NAME} yaml-cpp)
|
||||
|
||||
# abseil
|
||||
add_subdirectory(ThirdParty/abseil-cpp ThirdParty/abseil-cpp)
|
||||
set(ABSL_PROPAGATE_CXX_STD true)
|
||||
add_subdirectory(ThirdParty/abseil-cpp-20220623.1)
|
||||
target_link_libraries(${PROJECT_NAME}
|
||||
absl::strings
|
||||
absl::str_format
|
||||
|
@ -1,4 +1,5 @@
|
||||
include(CMakeParseArguments)
|
||||
include(GNUInstallDirs)
|
||||
|
||||
set(ABSL_INTERNAL_DLL_FILES
|
||||
"algorithm/algorithm.h"
|
||||
@ -16,8 +17,6 @@ set(ABSL_INTERNAL_DLL_FILES
|
||||
"base/internal/dynamic_annotations.h"
|
||||
"base/internal/endian.h"
|
||||
"base/internal/errno_saver.h"
|
||||
"base/internal/exponential_biased.cc"
|
||||
"base/internal/exponential_biased.h"
|
||||
"base/internal/fast_type_id.h"
|
||||
"base/internal/hide_ptr.h"
|
||||
"base/internal/identity.h"
|
||||
@ -27,8 +26,7 @@ set(ABSL_INTERNAL_DLL_FILES
|
||||
"base/internal/low_level_alloc.h"
|
||||
"base/internal/low_level_scheduling.h"
|
||||
"base/internal/per_thread_tls.h"
|
||||
"base/internal/periodic_sampler.cc"
|
||||
"base/internal/periodic_sampler.h"
|
||||
"base/internal/prefetch.h"
|
||||
"base/internal/pretty_function.h"
|
||||
"base/internal/raw_logging.cc"
|
||||
"base/internal/raw_logging.h"
|
||||
@ -81,10 +79,9 @@ set(ABSL_INTERNAL_DLL_FILES
|
||||
"container/internal/hashtablez_sampler.cc"
|
||||
"container/internal/hashtablez_sampler.h"
|
||||
"container/internal/hashtablez_sampler_force_weak_definition.cc"
|
||||
"container/internal/have_sse.h"
|
||||
"container/internal/inlined_vector.h"
|
||||
"container/internal/layout.h"
|
||||
"container/internal/node_hash_policy.h"
|
||||
"container/internal/node_slot_policy.h"
|
||||
"container/internal/raw_hash_map.h"
|
||||
"container/internal/raw_hash_set.cc"
|
||||
"container/internal/raw_hash_set.h"
|
||||
@ -94,7 +91,6 @@ set(ABSL_INTERNAL_DLL_FILES
|
||||
"debugging/failure_signal_handler.cc"
|
||||
"debugging/failure_signal_handler.h"
|
||||
"debugging/leak_check.h"
|
||||
"debugging/leak_check_disable.cc"
|
||||
"debugging/stacktrace.cc"
|
||||
"debugging/stacktrace.h"
|
||||
"debugging/symbolize.cc"
|
||||
@ -113,9 +109,11 @@ set(ABSL_INTERNAL_DLL_FILES
|
||||
"debugging/internal/symbolize.h"
|
||||
"debugging/internal/vdso_support.cc"
|
||||
"debugging/internal/vdso_support.h"
|
||||
"functional/any_invocable.h"
|
||||
"functional/internal/front_binder.h"
|
||||
"functional/bind_front.h"
|
||||
"functional/function_ref.h"
|
||||
"functional/internal/any_invocable.h"
|
||||
"functional/internal/function_ref.h"
|
||||
"hash/hash.h"
|
||||
"hash/internal/city.h"
|
||||
@ -123,14 +121,20 @@ set(ABSL_INTERNAL_DLL_FILES
|
||||
"hash/internal/hash.h"
|
||||
"hash/internal/hash.cc"
|
||||
"hash/internal/spy_hash_state.h"
|
||||
"hash/internal/wyhash.h"
|
||||
"hash/internal/wyhash.cc"
|
||||
"hash/internal/low_level_hash.h"
|
||||
"hash/internal/low_level_hash.cc"
|
||||
"memory/memory.h"
|
||||
"meta/type_traits.h"
|
||||
"numeric/bits.h"
|
||||
"numeric/int128.cc"
|
||||
"numeric/int128.h"
|
||||
"numeric/internal/bits.h"
|
||||
"numeric/internal/representation.h"
|
||||
"profiling/internal/exponential_biased.cc"
|
||||
"profiling/internal/exponential_biased.h"
|
||||
"profiling/internal/periodic_sampler.cc"
|
||||
"profiling/internal/periodic_sampler.h"
|
||||
"profiling/internal/sample_recorder.h"
|
||||
"random/bernoulli_distribution.h"
|
||||
"random/beta_distribution.h"
|
||||
"random/bit_gen_ref.h"
|
||||
@ -193,18 +197,44 @@ set(ABSL_INTERNAL_DLL_FILES
|
||||
"strings/charconv.h"
|
||||
"strings/cord.cc"
|
||||
"strings/cord.h"
|
||||
"strings/cord_analysis.cc"
|
||||
"strings/cord_analysis.h"
|
||||
"strings/cord_buffer.cc"
|
||||
"strings/cord_buffer.h"
|
||||
"strings/escaping.cc"
|
||||
"strings/escaping.h"
|
||||
"strings/internal/cord_internal.cc"
|
||||
"strings/internal/cord_internal.h"
|
||||
"strings/internal/cord_rep_flat.h"
|
||||
"strings/internal/cord_rep_ring.cc"
|
||||
"strings/internal/cord_rep_ring.h"
|
||||
"strings/internal/cord_rep_ring_reader.h"
|
||||
"strings/internal/charconv_bigint.cc"
|
||||
"strings/internal/charconv_bigint.h"
|
||||
"strings/internal/charconv_parse.cc"
|
||||
"strings/internal/charconv_parse.h"
|
||||
"strings/internal/cord_data_edge.h"
|
||||
"strings/internal/cord_internal.cc"
|
||||
"strings/internal/cord_internal.h"
|
||||
"strings/internal/cord_rep_btree.cc"
|
||||
"strings/internal/cord_rep_btree.h"
|
||||
"strings/internal/cord_rep_btree_navigator.cc"
|
||||
"strings/internal/cord_rep_btree_navigator.h"
|
||||
"strings/internal/cord_rep_btree_reader.cc"
|
||||
"strings/internal/cord_rep_btree_reader.h"
|
||||
"strings/internal/cord_rep_crc.cc"
|
||||
"strings/internal/cord_rep_crc.h"
|
||||
"strings/internal/cord_rep_consume.h"
|
||||
"strings/internal/cord_rep_consume.cc"
|
||||
"strings/internal/cord_rep_flat.h"
|
||||
"strings/internal/cord_rep_ring.cc"
|
||||
"strings/internal/cord_rep_ring.h"
|
||||
"strings/internal/cord_rep_ring_reader.h"
|
||||
"strings/internal/cordz_functions.cc"
|
||||
"strings/internal/cordz_functions.h"
|
||||
"strings/internal/cordz_handle.cc"
|
||||
"strings/internal/cordz_handle.h"
|
||||
"strings/internal/cordz_info.cc"
|
||||
"strings/internal/cordz_info.h"
|
||||
"strings/internal/cordz_sample_token.cc"
|
||||
"strings/internal/cordz_sample_token.h"
|
||||
"strings/internal/cordz_statistics.h"
|
||||
"strings/internal/cordz_update_scope.h"
|
||||
"strings/internal/cordz_update_tracker.h"
|
||||
"strings/internal/stl_type_traits.h"
|
||||
"strings/internal/string_constant.h"
|
||||
"strings/match.cc"
|
||||
@ -319,6 +349,7 @@ set(ABSL_INTERNAL_DLL_FILES
|
||||
"types/internal/span.h"
|
||||
"types/variant.h"
|
||||
"utility/utility.h"
|
||||
"debugging/leak_check.cc"
|
||||
)
|
||||
|
||||
set(ABSL_INTERNAL_DLL_TARGETS
|
||||
@ -329,7 +360,6 @@ set(ABSL_INTERNAL_DLL_TARGETS
|
||||
"debugging_internal"
|
||||
"demangle_internal"
|
||||
"leak_check"
|
||||
"leak_check_disable"
|
||||
"stack_consumption"
|
||||
"debugging"
|
||||
"hash"
|
||||
@ -360,6 +390,7 @@ set(ABSL_INTERNAL_DLL_TARGETS
|
||||
"kernel_timeout_internal"
|
||||
"synchronization"
|
||||
"thread_pool"
|
||||
"any_invocable"
|
||||
"bind_front"
|
||||
"function_ref"
|
||||
"atomic_hook"
|
||||
@ -429,13 +460,13 @@ set(ABSL_INTERNAL_DLL_TARGETS
|
||||
"hashtablez_sampler"
|
||||
"hashtable_debug"
|
||||
"hashtable_debug_hooks"
|
||||
"have_sse"
|
||||
"node_hash_policy"
|
||||
"node_slot_policy"
|
||||
"raw_hash_map"
|
||||
"container_common"
|
||||
"raw_hash_set"
|
||||
"layout"
|
||||
"tracked"
|
||||
"sample_recorder"
|
||||
)
|
||||
|
||||
function(absl_internal_dll_contains)
|
||||
@ -499,7 +530,7 @@ function(absl_make_dll)
|
||||
abseil_dll
|
||||
PUBLIC
|
||||
"$<BUILD_INTERFACE:${ABSL_COMMON_INCLUDE_DIRS}>"
|
||||
$<INSTALL_INTERFACE:${ABSL_INSTALL_INCLUDEDIR}>
|
||||
$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>
|
||||
)
|
||||
|
||||
target_compile_options(
|
||||
@ -517,8 +548,8 @@ function(absl_make_dll)
|
||||
${ABSL_CC_LIB_DEFINES}
|
||||
)
|
||||
install(TARGETS abseil_dll EXPORT ${PROJECT_NAME}Targets
|
||||
RUNTIME DESTINATION ${ABSL_INSTALL_BINDIR}
|
||||
LIBRARY DESTINATION ${ABSL_INSTALL_LIBDIR}
|
||||
ARCHIVE DESTINATION ${ABSL_INSTALL_LIBDIR}
|
||||
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
|
||||
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
|
||||
ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
|
||||
)
|
||||
endfunction()
|
@ -17,7 +17,6 @@
|
||||
include(CMakeParseArguments)
|
||||
include(AbseilConfigureCopts)
|
||||
include(AbseilDll)
|
||||
include(AbseilInstallDirs)
|
||||
|
||||
# The IDE folder for Abseil that will be used if Abseil is included in a CMake
|
||||
# project that sets
|
||||
@ -41,7 +40,8 @@ endif()
|
||||
# LINKOPTS: List of link options
|
||||
# PUBLIC: Add this so that this library will be exported under absl::
|
||||
# Also in IDE, target will appear in Abseil folder while non PUBLIC will be in Abseil/internal.
|
||||
# TESTONLY: When added, this target will only be built if BUILD_TESTING=ON.
|
||||
# TESTONLY: When added, this target will only be built if both
|
||||
# BUILD_TESTING=ON and ABSL_BUILD_TESTING=ON.
|
||||
#
|
||||
# Note:
|
||||
# By default, absl_cc_library will always create a library named absl_${NAME},
|
||||
@ -83,7 +83,8 @@ function(absl_cc_library)
|
||||
${ARGN}
|
||||
)
|
||||
|
||||
if(ABSL_CC_LIB_TESTONLY AND NOT BUILD_TESTING)
|
||||
if(NOT ABSL_CC_LIB_PUBLIC AND ABSL_CC_LIB_TESTONLY AND
|
||||
NOT (BUILD_TESTING AND ABSL_BUILD_TESTING))
|
||||
return()
|
||||
endif()
|
||||
|
||||
@ -142,7 +143,8 @@ function(absl_cc_library)
|
||||
endif()
|
||||
|
||||
# Generate a pkg-config file for every library:
|
||||
if(_build_type STREQUAL "static" OR _build_type STREQUAL "shared")
|
||||
if((_build_type STREQUAL "static" OR _build_type STREQUAL "shared")
|
||||
AND ABSL_ENABLE_INSTALL)
|
||||
if(NOT ABSL_CC_LIB_TESTONLY)
|
||||
if(absl_VERSION)
|
||||
set(PC_VERSION "${absl_VERSION}")
|
||||
@ -151,6 +153,10 @@ function(absl_cc_library)
|
||||
endif()
|
||||
foreach(dep ${ABSL_CC_LIB_DEPS})
|
||||
if(${dep} MATCHES "^absl::(.*)")
|
||||
# Join deps with commas.
|
||||
if(PC_DEPS)
|
||||
set(PC_DEPS "${PC_DEPS},")
|
||||
endif()
|
||||
set(PC_DEPS "${PC_DEPS} absl_${CMAKE_MATCH_1} = ${PC_VERSION}")
|
||||
endif()
|
||||
endforeach()
|
||||
@ -164,21 +170,22 @@ function(absl_cc_library)
|
||||
set(PC_CFLAGS "${PC_CFLAGS} ${cflag}")
|
||||
endif()
|
||||
endforeach()
|
||||
string(REPLACE ";" " " PC_LINKOPTS "${ABSL_CC_LIB_LINKOPTS}")
|
||||
FILE(GENERATE OUTPUT "${CMAKE_BINARY_DIR}/lib/pkgconfig/absl_${_NAME}.pc" CONTENT "\
|
||||
prefix=${CMAKE_INSTALL_PREFIX}\n\
|
||||
exec_prefix=\${prefix}\n\
|
||||
libdir=\${prefix}/lib\n\
|
||||
includedir=\${prefix}/include\n\
|
||||
libdir=${CMAKE_INSTALL_FULL_LIBDIR}\n\
|
||||
includedir=${CMAKE_INSTALL_FULL_INCLUDEDIR}\n\
|
||||
\n\
|
||||
Name: absl_${_NAME}\n\
|
||||
Description: Abseil ${_NAME} library\n\
|
||||
URL: https://abseil.io/\n\
|
||||
Version: ${PC_VERSION}\n\
|
||||
Requires.private:${PC_DEPS}\n\
|
||||
Libs: -L\${libdir} $<JOIN:${ABSL_CC_LIB_LINKOPTS}, > $<$<NOT:$<BOOL:${ABSL_CC_LIB_IS_INTERFACE}>>:-labsl_${_NAME}>\n\
|
||||
Requires:${PC_DEPS}\n\
|
||||
Libs: -L\${libdir} ${PC_LINKOPTS} $<$<NOT:$<BOOL:${ABSL_CC_LIB_IS_INTERFACE}>>:-labsl_${_NAME}>\n\
|
||||
Cflags: -I\${includedir}${PC_CFLAGS}\n")
|
||||
INSTALL(FILES "${CMAKE_BINARY_DIR}/lib/pkgconfig/absl_${_NAME}.pc"
|
||||
DESTINATION "${CMAKE_INSTALL_PREFIX}/lib/pkgconfig")
|
||||
DESTINATION "${CMAKE_INSTALL_LIBDIR}/pkgconfig")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
@ -235,7 +242,7 @@ Cflags: -I\${includedir}${PC_CFLAGS}\n")
|
||||
target_include_directories(${_NAME}
|
||||
PUBLIC
|
||||
"$<BUILD_INTERFACE:${ABSL_COMMON_INCLUDE_DIRS}>"
|
||||
$<INSTALL_INTERFACE:${ABSL_INSTALL_INCLUDEDIR}>
|
||||
$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>
|
||||
)
|
||||
target_compile_options(${_NAME}
|
||||
PRIVATE ${ABSL_CC_LIB_COPTS})
|
||||
@ -250,9 +257,23 @@ Cflags: -I\${includedir}${PC_CFLAGS}\n")
|
||||
set_property(TARGET ${_NAME} PROPERTY FOLDER ${ABSL_IDE_FOLDER}/internal)
|
||||
endif()
|
||||
|
||||
# INTERFACE libraries can't have the CXX_STANDARD property set
|
||||
if(ABSL_PROPAGATE_CXX_STD)
|
||||
# Abseil libraries require C++11 as the current minimum standard.
|
||||
# Top-level application CMake projects should ensure a consistent C++
|
||||
# standard for all compiled sources by setting CMAKE_CXX_STANDARD.
|
||||
target_compile_features(${_NAME} PUBLIC cxx_std_11)
|
||||
else()
|
||||
# Note: This is legacy (before CMake 3.8) behavior. Setting the
|
||||
# target-level CXX_STANDARD property to ABSL_CXX_STANDARD (which is
|
||||
# initialized by CMAKE_CXX_STANDARD) should have no real effect, since
|
||||
# that is the default value anyway.
|
||||
#
|
||||
# CXX_STANDARD_REQUIRED does guard against the top-level CMake project
|
||||
# not having enabled CMAKE_CXX_STANDARD_REQUIRED (which prevents
|
||||
# "decaying" to an older standard if the requested one isn't available).
|
||||
set_property(TARGET ${_NAME} PROPERTY CXX_STANDARD ${ABSL_CXX_STANDARD})
|
||||
set_property(TARGET ${_NAME} PROPERTY CXX_STANDARD_REQUIRED ON)
|
||||
endif()
|
||||
|
||||
# When being installed, we lose the absl_ prefix. We want to put it back
|
||||
# to have properly named lib files. This is a no-op when we are not being
|
||||
@ -260,8 +281,7 @@ Cflags: -I\${includedir}${PC_CFLAGS}\n")
|
||||
if(ABSL_ENABLE_INSTALL)
|
||||
set_target_properties(${_NAME} PROPERTIES
|
||||
OUTPUT_NAME "absl_${_NAME}"
|
||||
# TODO(b/173696973): Figure out how to set SOVERSION for LTS releases.
|
||||
SOVERSION 0
|
||||
SOVERSION "2206.0.0"
|
||||
)
|
||||
endif()
|
||||
else()
|
||||
@ -270,7 +290,7 @@ Cflags: -I\${includedir}${PC_CFLAGS}\n")
|
||||
target_include_directories(${_NAME}
|
||||
INTERFACE
|
||||
"$<BUILD_INTERFACE:${ABSL_COMMON_INCLUDE_DIRS}>"
|
||||
$<INSTALL_INTERFACE:${ABSL_INSTALL_INCLUDEDIR}>
|
||||
$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>
|
||||
)
|
||||
|
||||
if (_build_type STREQUAL "dll")
|
||||
@ -284,15 +304,25 @@ Cflags: -I\${includedir}${PC_CFLAGS}\n")
|
||||
${ABSL_DEFAULT_LINKOPTS}
|
||||
)
|
||||
target_compile_definitions(${_NAME} INTERFACE ${ABSL_CC_LIB_DEFINES})
|
||||
|
||||
if(ABSL_PROPAGATE_CXX_STD)
|
||||
# Abseil libraries require C++11 as the current minimum standard.
|
||||
# Top-level application CMake projects should ensure a consistent C++
|
||||
# standard for all compiled sources by setting CMAKE_CXX_STANDARD.
|
||||
target_compile_features(${_NAME} INTERFACE cxx_std_11)
|
||||
|
||||
# (INTERFACE libraries can't have the CXX_STANDARD property set, so there
|
||||
# is no legacy behavior else case).
|
||||
endif()
|
||||
endif()
|
||||
|
||||
# TODO currently we don't install googletest alongside abseil sources, so
|
||||
# installed abseil can't be tested.
|
||||
if(NOT ABSL_CC_LIB_TESTONLY AND ABSL_ENABLE_INSTALL)
|
||||
install(TARGETS ${_NAME} EXPORT ${PROJECT_NAME}Targets
|
||||
RUNTIME DESTINATION ${ABSL_INSTALL_BINDIR}
|
||||
LIBRARY DESTINATION ${ABSL_INSTALL_LIBDIR}
|
||||
ARCHIVE DESTINATION ${ABSL_INSTALL_LIBDIR}
|
||||
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
|
||||
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
|
||||
ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
|
||||
)
|
||||
endif()
|
||||
|
||||
@ -333,11 +363,11 @@ endfunction()
|
||||
# "awesome_test.cc"
|
||||
# DEPS
|
||||
# absl::awesome
|
||||
# gmock
|
||||
# gtest_main
|
||||
# GTest::gmock
|
||||
# GTest::gtest_main
|
||||
# )
|
||||
function(absl_cc_test)
|
||||
if(NOT BUILD_TESTING)
|
||||
if(NOT (BUILD_TESTING AND ABSL_BUILD_TESTING))
|
||||
return()
|
||||
endif()
|
||||
|
||||
@ -387,8 +417,23 @@ function(absl_cc_test)
|
||||
# Add all Abseil targets to a folder in the IDE for organization.
|
||||
set_property(TARGET ${_NAME} PROPERTY FOLDER ${ABSL_IDE_FOLDER}/test)
|
||||
|
||||
if(ABSL_PROPAGATE_CXX_STD)
|
||||
# Abseil libraries require C++11 as the current minimum standard.
|
||||
# Top-level application CMake projects should ensure a consistent C++
|
||||
# standard for all compiled sources by setting CMAKE_CXX_STANDARD.
|
||||
target_compile_features(${_NAME} PUBLIC cxx_std_11)
|
||||
else()
|
||||
# Note: This is legacy (before CMake 3.8) behavior. Setting the
|
||||
# target-level CXX_STANDARD property to ABSL_CXX_STANDARD (which is
|
||||
# initialized by CMAKE_CXX_STANDARD) should have no real effect, since
|
||||
# that is the default value anyway.
|
||||
#
|
||||
# CXX_STANDARD_REQUIRED does guard against the top-level CMake project
|
||||
# not having enabled CMAKE_CXX_STANDARD_REQUIRED (which prevents
|
||||
# "decaying" to an older standard if the requested one isn't available).
|
||||
set_property(TARGET ${_NAME} PROPERTY CXX_STANDARD ${ABSL_CXX_STANDARD})
|
||||
set_property(TARGET ${_NAME} PROPERTY CXX_STANDARD_REQUIRED ON)
|
||||
endif()
|
||||
|
||||
add_test(NAME ${_NAME} COMMAND ${_NAME})
|
||||
endfunction()
|
188
ThirdParty/abseil-cpp-20220623.1/CMake/README.md
vendored
Normal file
188
ThirdParty/abseil-cpp-20220623.1/CMake/README.md
vendored
Normal file
@ -0,0 +1,188 @@
|
||||
# Abseil CMake Build Instructions
|
||||
|
||||
Abseil comes with a CMake build script ([CMakeLists.txt](../CMakeLists.txt))
|
||||
that can be used on a wide range of platforms ("C" stands for cross-platform.).
|
||||
If you don't have CMake installed already, you can download it for free from
|
||||
<https://www.cmake.org/>.
|
||||
|
||||
CMake works by generating native makefiles or build projects that can
|
||||
be used in the compiler environment of your choice.
|
||||
|
||||
For API/ABI compatibility reasons, we strongly recommend building Abseil in a
|
||||
subdirectory of your project or as an embedded dependency.
|
||||
|
||||
## Incorporating Abseil Into a CMake Project
|
||||
|
||||
The recommendations below are similar to those for using CMake within the
|
||||
googletest framework
|
||||
(<https://github.com/google/googletest/blob/master/googletest/README.md#incorporating-into-an-existing-cmake-project>)
|
||||
|
||||
### Step-by-Step Instructions
|
||||
|
||||
1. If you want to build the Abseil tests, integrate the Abseil dependency
|
||||
[Google Test](https://github.com/google/googletest) into your CMake
|
||||
project. To disable Abseil tests, you have to pass either
|
||||
`-DBUILD_TESTING=OFF` or `-DABSL_BUILD_TESTING=OFF` when configuring your
|
||||
project with CMake.
|
||||
|
||||
2. Download Abseil and copy it into a subdirectory in your CMake project or add
|
||||
Abseil as a [git submodule](https://git-scm.com/docs/git-submodule) in your
|
||||
CMake project.
|
||||
|
||||
3. You can then use the CMake command
|
||||
[`add_subdirectory()`](https://cmake.org/cmake/help/latest/command/add_subdirectory.html)
|
||||
to include Abseil directly in your CMake project.
|
||||
|
||||
4. Add the **absl::** target you wish to use to the
|
||||
[`target_link_libraries()`](https://cmake.org/cmake/help/latest/command/target_link_libraries.html)
|
||||
section of your executable or of your library.<br>
|
||||
Here is a short CMakeLists.txt example of an application project using Abseil.
|
||||
|
||||
```cmake
|
||||
cmake_minimum_required(VERSION 3.8.2)
|
||||
project(my_app_project)
|
||||
|
||||
# Pick the C++ standard to compile with.
|
||||
# Abseil currently supports C++11, C++14, and C++17.
|
||||
set(CMAKE_CXX_STANDARD 11)
|
||||
set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
||||
|
||||
add_subdirectory(abseil-cpp)
|
||||
|
||||
add_executable(my_exe source.cpp)
|
||||
target_link_libraries(my_exe absl::base absl::synchronization absl::strings)
|
||||
```
|
||||
|
||||
Note that if you are developing a library designed for use by other clients, you
|
||||
should instead leave `CMAKE_CXX_STANDARD` unset (or only set if being built as
|
||||
the current top-level CMake project) and configure the minimum required C++
|
||||
standard at the target level. If you require a later minimum C++ standard than
|
||||
Abseil does, it's a good idea to also enforce that `CMAKE_CXX_STANDARD` (which
|
||||
will control Abseil library targets) is set to at least that minimum. For
|
||||
example:
|
||||
|
||||
```cmake
|
||||
cmake_minimum_required(VERSION 3.8.2)
|
||||
project(my_lib_project)
|
||||
|
||||
# Leave C++ standard up to the root application, so set it only if this is the
|
||||
# current top-level CMake project.
|
||||
if(CMAKE_SOURCE_DIR STREQUAL my_lib_project_SOURCE_DIR)
|
||||
set(CMAKE_CXX_STANDARD 17)
|
||||
set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
||||
endif()
|
||||
|
||||
add_subdirectory(abseil-cpp)
|
||||
|
||||
add_library(my_lib source.cpp)
|
||||
target_link_libraries(my_lib absl::base absl::synchronization absl::strings)
|
||||
|
||||
# Enforce that my_lib requires C++17. Important to document for clients that they
|
||||
# must set CMAKE_CXX_STANDARD to 17 or higher for proper Abseil ABI compatibility
|
||||
# (since otherwise, Abseil library targets could be compiled with a lower C++
|
||||
# standard than my_lib).
|
||||
target_compile_features(my_lib PUBLIC cxx_std_17)
|
||||
if(CMAKE_CXX_STANDARD LESS 17)
|
||||
message(FATAL_ERROR
|
||||
"my_lib_project requires CMAKE_CXX_STANDARD >= 17 (got: ${CMAKE_CXX_STANDARD})")
|
||||
endif()
|
||||
```
|
||||
|
||||
Then the top-level application project that uses your library is responsible for
|
||||
setting a consistent `CMAKE_CXX_STANDARD` that is sufficiently high.
|
||||
|
||||
### Running Abseil Tests with CMake
|
||||
|
||||
Use the `-DABSL_BUILD_TESTING=ON` flag to run Abseil tests. Note that
|
||||
BUILD_TESTING must also be on (the default).
|
||||
|
||||
You will need to provide Abseil with a Googletest dependency. There are two
|
||||
options for how to do this:
|
||||
|
||||
* Use `-DABSL_USE_GOOGLETEST_HEAD`. This will automatically download the latest
|
||||
Googletest source into the build directory at configure time. Googletest will
|
||||
then be compiled directly alongside Abseil's tests.
|
||||
* Manually integrate Googletest with your build. See
|
||||
https://github.com/google/googletest/blob/master/googletest/README.md#using-cmake
|
||||
for more information on using Googletest in a CMake project.
|
||||
|
||||
For example, to run just the Abseil tests, you could use this script:
|
||||
|
||||
```
|
||||
cd path/to/abseil-cpp
|
||||
mkdir build
|
||||
cd build
|
||||
cmake -DABSL_BUILD_TESTING=ON -DABSL_USE_GOOGLETEST_HEAD=ON ..
|
||||
make -j
|
||||
ctest
|
||||
```
|
||||
|
||||
Currently, we only run our tests with CMake in a Linux environment, but we are
|
||||
working on the rest of our supported platforms. See
|
||||
https://github.com/abseil/abseil-cpp/projects/1 and
|
||||
https://github.com/abseil/abseil-cpp/issues/109 for more information.
|
||||
|
||||
### Available Abseil CMake Public Targets
|
||||
|
||||
Here's a non-exhaustive list of Abseil CMake public targets:
|
||||
|
||||
```cmake
|
||||
absl::algorithm
|
||||
absl::base
|
||||
absl::debugging
|
||||
absl::flat_hash_map
|
||||
absl::flags
|
||||
absl::memory
|
||||
absl::meta
|
||||
absl::numeric
|
||||
absl::random_random
|
||||
absl::strings
|
||||
absl::synchronization
|
||||
absl::time
|
||||
absl::utility
|
||||
```
|
||||
|
||||
## Traditional CMake Set-Up
|
||||
|
||||
For larger projects, it may make sense to use the traditional CMake set-up where you build and install projects separately.
|
||||
|
||||
First, you'd need to build and install Google Test:
|
||||
```
|
||||
cmake -S /source/googletest -B /build/googletest -DCMAKE_BUILD_TYPE=Release -DCMAKE_INSTALL_PREFIX=/installation/dir -DBUILD_GMOCK=ON
|
||||
cmake --build /build/googletest --target install
|
||||
```
|
||||
|
||||
Then you need to configure and build Abseil. Make sure you enable `ABSL_USE_EXTERNAL_GOOGLETEST` and `ABSL_FIND_GOOGLETEST`. You also need to enable `ABSL_ENABLE_INSTALL` so that you can install Abseil itself.
|
||||
```
|
||||
cmake -S /source/abseil-cpp -B /build/abseil-cpp -DCMAKE_PREFIX_PATH=/installation/dir -DCMAKE_INSTALL_PREFIX=/installation/dir -DABSL_ENABLE_INSTALL=ON -DABSL_USE_EXTERNAL_GOOGLETEST=ON -DABSL_FIND_GOOGLETEST=ON
|
||||
cmake --build /temporary/build/abseil-cpp
|
||||
```
|
||||
|
||||
(`CMAKE_PREFIX_PATH` is where you already have Google Test installed; `CMAKE_INSTALL_PREFIX` is where you want to have Abseil installed; they can be different.)
|
||||
|
||||
Run the tests:
|
||||
```
|
||||
ctest --test-dir /temporary/build/abseil-cpp
|
||||
```
|
||||
|
||||
And finally install:
|
||||
```
|
||||
cmake --build /temporary/build/abseil-cpp --target install
|
||||
```
|
||||
|
||||
# CMake Option Synposis
|
||||
|
||||
## Enable Standard CMake Installation
|
||||
|
||||
`-DABSL_ENABLE_INSTALL=ON`
|
||||
|
||||
## Google Test Options
|
||||
|
||||
`-DABSL_BUILD_TESTING=ON` must be set to enable testing
|
||||
|
||||
- Have Abseil download and build Google Test for you: `-DABSL_USE_EXTERNAL_GOOGLETEST=OFF` (default)
|
||||
- Download and build latest Google Test: `-DABSL_USE_GOOGLETEST_HEAD=ON`
|
||||
- Download specific Google Test version (ZIP archive): `-DABSL_GOOGLETEST_DOWNLOAD_URL=https://.../version.zip`
|
||||
- Use Google Test from specific local directory: `-DABSL_LOCAL_GOOGLETEST_DIR=/path/to/googletest`
|
||||
- Use Google Test included elsewhere in your project: `-DABSL_USE_EXTERNAL_GOOGLETEST=ON`
|
||||
- Use standard CMake `find_package(CTest)` to find installed Google Test: `-DABSL_USE_EXTERNAL_GOOGLETEST=ON -DABSL_FIND_GOOGLETEST=ON`
|
@ -18,10 +18,8 @@
|
||||
cmake_minimum_required(VERSION 3.5)
|
||||
project(absl_cmake_testing CXX)
|
||||
|
||||
set(CMAKE_CXX_STANDARD 11)
|
||||
|
||||
add_executable(simple simple.cc)
|
||||
|
||||
find_package(absl REQUIRED)
|
||||
|
||||
target_link_libraries(simple absl::strings)
|
||||
target_link_libraries(simple absl::strings absl::config)
|
@ -14,8 +14,17 @@
|
||||
// limitations under the License.
|
||||
|
||||
#include <iostream>
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/strings/substitute.h"
|
||||
|
||||
#if !defined(ABSL_LTS_RELEASE_VERSION) || ABSL_LTS_RELEASE_VERSION != 99998877
|
||||
#error ABSL_LTS_RELEASE_VERSION is not set correctly.
|
||||
#endif
|
||||
|
||||
#if !defined(ABSL_LTS_RELEASE_PATCH_LEVEL) || ABSL_LTS_RELEASE_PATCH_LEVEL != 0
|
||||
#error ABSL_LTS_RELEASE_PATCH_LEVEL is not set correctly.
|
||||
#endif
|
||||
|
||||
int main(int argc, char** argv) {
|
||||
for (int i = 0; i < argc; ++i) {
|
||||
std::cout << absl::Substitute("Arg $0: $1\n", i, argv[i]);
|
112
ThirdParty/abseil-cpp-20220623.1/CMake/install_test_project/test.sh
vendored
Normal file
112
ThirdParty/abseil-cpp-20220623.1/CMake/install_test_project/test.sh
vendored
Normal file
@ -0,0 +1,112 @@
|
||||
#!/bin/bash
|
||||
#
|
||||
# Copyright 2019 The Abseil Authors.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# https://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
#
|
||||
# Unit and integration tests for Abseil LTS CMake installation
|
||||
|
||||
# Fail on any error. Treat unset variables an error. Print commands as executed.
|
||||
set -euox pipefail
|
||||
|
||||
absl_dir=/abseil-cpp
|
||||
absl_build_dir=/buildfs
|
||||
googletest_builddir=/googletest_builddir
|
||||
project_dir="${absl_dir}"/CMake/install_test_project
|
||||
project_build_dir=/buildfs/project-build
|
||||
|
||||
build_shared_libs="OFF"
|
||||
if [ "${LINK_TYPE:-}" = "DYNAMIC" ]; then
|
||||
build_shared_libs="ON"
|
||||
fi
|
||||
|
||||
# Build and install GoogleTest
|
||||
mkdir "${googletest_builddir}"
|
||||
pushd "${googletest_builddir}"
|
||||
curl -L "${ABSL_GOOGLETEST_DOWNLOAD_URL}" --output "${ABSL_GOOGLETEST_COMMIT}".zip
|
||||
unzip "${ABSL_GOOGLETEST_COMMIT}".zip
|
||||
pushd "googletest-${ABSL_GOOGLETEST_COMMIT}"
|
||||
mkdir build
|
||||
pushd build
|
||||
cmake -DCMAKE_BUILD_TYPE=Release -DBUILD_SHARED_LIBS="${build_shared_libs}" ..
|
||||
make -j $(nproc)
|
||||
make install
|
||||
ldconfig
|
||||
popd
|
||||
popd
|
||||
popd
|
||||
|
||||
# Run the LTS transformations
|
||||
./create_lts.py 99998877
|
||||
|
||||
# Build and install Abseil
|
||||
pushd "${absl_build_dir}"
|
||||
cmake "${absl_dir}" \
|
||||
-DABSL_USE_EXTERNAL_GOOGLETEST=ON \
|
||||
-DABSL_FIND_GOOGLETEST=ON \
|
||||
-DCMAKE_BUILD_TYPE=Release \
|
||||
-DABSL_BUILD_TESTING=ON \
|
||||
-DBUILD_SHARED_LIBS="${build_shared_libs}"
|
||||
make -j $(nproc)
|
||||
ctest -j $(nproc) --output-on-failure
|
||||
make install
|
||||
ldconfig
|
||||
popd
|
||||
|
||||
# Test the project against the installed Abseil
|
||||
mkdir -p "${project_build_dir}"
|
||||
pushd "${project_build_dir}"
|
||||
cmake "${project_dir}"
|
||||
cmake --build . --target simple
|
||||
|
||||
output="$(${project_build_dir}/simple "printme" 2>&1)"
|
||||
if [[ "${output}" != *"Arg 1: printme"* ]]; then
|
||||
echo "Faulty output on simple project:"
|
||||
echo "${output}"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
popd
|
||||
|
||||
if ! grep absl::strings "/usr/local/lib/cmake/absl/abslTargets.cmake"; then
|
||||
cat "/usr/local/lib/cmake/absl/abslTargets.cmake"
|
||||
echo "CMake targets named incorrectly"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
pushd "${HOME}"
|
||||
cat > hello-abseil.cc << EOF
|
||||
#include <cstdlib>
|
||||
|
||||
#include "absl/strings/str_format.h"
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
absl::PrintF("Hello Abseil!\n");
|
||||
return EXIT_SUCCESS;
|
||||
}
|
||||
EOF
|
||||
|
||||
if [ "${LINK_TYPE:-}" != "DYNAMIC" ]; then
|
||||
pc_args=($(pkg-config --cflags --libs --static absl_str_format))
|
||||
g++ -static -o hello-abseil hello-abseil.cc "${pc_args[@]}"
|
||||
else
|
||||
pc_args=($(pkg-config --cflags --libs absl_str_format))
|
||||
g++ -o hello-abseil hello-abseil.cc "${pc_args[@]}"
|
||||
fi
|
||||
hello="$(./hello-abseil)"
|
||||
[[ "${hello}" == "Hello Abseil!" ]]
|
||||
|
||||
popd
|
||||
|
||||
echo "Install test complete!"
|
||||
exit 0
|
@ -41,11 +41,12 @@ if (POLICY CMP0077)
|
||||
cmake_policy(SET CMP0077 NEW)
|
||||
endif (POLICY CMP0077)
|
||||
|
||||
# Set BUILD_TESTING to OFF by default.
|
||||
# This must come before the project() and include(CTest) lines.
|
||||
OPTION(BUILD_TESTING "Build tests" OFF)
|
||||
# Allow the user to specify the MSVC runtime
|
||||
if (POLICY CMP0091)
|
||||
cmake_policy(SET CMP0091 NEW)
|
||||
endif (POLICY CMP0091)
|
||||
|
||||
project(absl CXX)
|
||||
project(absl LANGUAGES CXX VERSION 20220623)
|
||||
include(CTest)
|
||||
|
||||
# Output directory is correct by default for most build setups. However, when
|
||||
@ -62,13 +63,20 @@ else()
|
||||
option(ABSL_ENABLE_INSTALL "Enable install rule" ON)
|
||||
endif()
|
||||
|
||||
option(ABSL_PROPAGATE_CXX_STD
|
||||
"Use CMake C++ standard meta features (e.g. cxx_std_11) that propagate to targets that link to Abseil"
|
||||
OFF) # TODO: Default to ON for CMake 3.8 and greater.
|
||||
if((${CMAKE_VERSION} VERSION_GREATER_EQUAL 3.8) AND (NOT ABSL_PROPAGATE_CXX_STD))
|
||||
message(WARNING "A future Abseil release will default ABSL_PROPAGATE_CXX_STD to ON for CMake 3.8 and up. We recommend enabling this option to ensure your project still builds correctly.")
|
||||
endif()
|
||||
|
||||
list(APPEND CMAKE_MODULE_PATH
|
||||
${CMAKE_CURRENT_LIST_DIR}/CMake
|
||||
${CMAKE_CURRENT_LIST_DIR}/absl/copts
|
||||
)
|
||||
|
||||
include(AbseilInstallDirs)
|
||||
include(CMakePackageConfigHelpers)
|
||||
include(GNUInstallDirs)
|
||||
include(AbseilDll)
|
||||
include(AbseilHelpers)
|
||||
|
||||
@ -97,8 +105,20 @@ endif()
|
||||
## pthread
|
||||
find_package(Threads REQUIRED)
|
||||
|
||||
include(CMakeDependentOption)
|
||||
|
||||
option(ABSL_BUILD_TESTING
|
||||
"If ON, Abseil will build all of Abseil's own tests." OFF)
|
||||
|
||||
option(ABSL_USE_EXTERNAL_GOOGLETEST
|
||||
"If ON, Abseil will assume that the targets for GoogleTest are already provided by the including project. This makes sense when Abseil is used with add_subproject." OFF)
|
||||
"If ON, Abseil will assume that the targets for GoogleTest are already provided by the including project. This makes sense when Abseil is used with add_subdirectory." OFF)
|
||||
|
||||
cmake_dependent_option(ABSL_FIND_GOOGLETEST
|
||||
"If ON, Abseil will use find_package(GTest) rather than assuming that GoogleTest is already provided by the including project."
|
||||
ON
|
||||
"ABSL_USE_EXTERNAL_GOOGLETEST"
|
||||
OFF)
|
||||
|
||||
|
||||
option(ABSL_USE_GOOGLETEST_HEAD
|
||||
"If ON, abseil will download HEAD from GoogleTest at config time." OFF)
|
||||
@ -109,17 +129,29 @@ set(ABSL_LOCAL_GOOGLETEST_DIR "/usr/src/googletest" CACHE PATH
|
||||
"If ABSL_USE_GOOGLETEST_HEAD is OFF and ABSL_GOOGLETEST_URL is not set, specifies the directory of a local GoogleTest checkout."
|
||||
)
|
||||
|
||||
set(BUILD_TESTING False)
|
||||
|
||||
if(BUILD_TESTING)
|
||||
if(BUILD_TESTING AND ABSL_BUILD_TESTING)
|
||||
## check targets
|
||||
if (NOT ABSL_USE_EXTERNAL_GOOGLETEST)
|
||||
if (ABSL_USE_EXTERNAL_GOOGLETEST)
|
||||
if (ABSL_FIND_GOOGLETEST)
|
||||
find_package(GTest REQUIRED)
|
||||
elseif(NOT TARGET GTest::gtest)
|
||||
if(TARGET gtest)
|
||||
# When Google Test is included directly rather than through find_package, the aliases are missing.
|
||||
add_library(GTest::gtest ALIAS gtest)
|
||||
add_library(GTest::gtest_main ALIAS gtest_main)
|
||||
add_library(GTest::gmock ALIAS gmock)
|
||||
add_library(GTest::gmock_main ALIAS gmock_main)
|
||||
else()
|
||||
message(FATAL_ERROR "ABSL_USE_EXTERNAL_GOOGLETEST is ON and ABSL_FIND_GOOGLETEST is OFF, which means that the top-level project must build the Google Test project. However, the target gtest was not found.")
|
||||
endif()
|
||||
endif()
|
||||
else()
|
||||
set(absl_gtest_build_dir ${CMAKE_BINARY_DIR}/googletest-build)
|
||||
if(ABSL_USE_GOOGLETEST_HEAD AND ABSL_GOOGLETEST_DOWNLOAD_URL)
|
||||
message(FATAL_ERROR "Do not set both ABSL_USE_GOOGLETEST_HEAD and ABSL_GOOGLETEST_DOWNLOAD_URL")
|
||||
endif()
|
||||
if(ABSL_USE_GOOGLETEST_HEAD)
|
||||
set(absl_gtest_download_url "https://github.com/google/googletest/archive/master.zip")
|
||||
set(absl_gtest_download_url "https://github.com/google/googletest/archive/main.zip")
|
||||
elseif(ABSL_GOOGLETEST_DOWNLOAD_URL)
|
||||
set(absl_gtest_download_url ${ABSL_GOOGLETEST_DOWNLOAD_URL})
|
||||
endif()
|
||||
@ -131,46 +163,30 @@ if(BUILD_TESTING)
|
||||
include(CMake/Googletest/DownloadGTest.cmake)
|
||||
endif()
|
||||
|
||||
check_target(gtest)
|
||||
check_target(gtest_main)
|
||||
check_target(gmock)
|
||||
|
||||
list(APPEND ABSL_TEST_COMMON_LIBRARIES
|
||||
gtest_main
|
||||
gtest
|
||||
gmock
|
||||
${CMAKE_THREAD_LIBS_INIT}
|
||||
)
|
||||
check_target(GTest::gtest)
|
||||
check_target(GTest::gtest_main)
|
||||
check_target(GTest::gmock)
|
||||
check_target(GTest::gmock_main)
|
||||
endif()
|
||||
|
||||
add_subdirectory(absl)
|
||||
|
||||
if(ABSL_ENABLE_INSTALL)
|
||||
# absl:lts-remove-begin(system installation is supported for LTS releases)
|
||||
# We don't support system-wide installation
|
||||
list(APPEND SYSTEM_INSTALL_DIRS "/usr/local" "/usr" "/opt/" "/opt/local" "c:/Program Files/${PROJECT_NAME}")
|
||||
if(NOT DEFINED CMAKE_INSTALL_PREFIX OR CMAKE_INSTALL_PREFIX IN_LIST SYSTEM_INSTALL_DIRS)
|
||||
message(WARNING "\
|
||||
The default and system-level install directories are unsupported except in LTS \
|
||||
releases of Abseil. Please set CMAKE_INSTALL_PREFIX to install Abseil in your \
|
||||
source or build tree directly.\
|
||||
")
|
||||
endif()
|
||||
# absl:lts-remove-end
|
||||
|
||||
|
||||
# install as a subdirectory only
|
||||
install(EXPORT ${PROJECT_NAME}Targets
|
||||
NAMESPACE absl::
|
||||
DESTINATION "${ABSL_INSTALL_CONFIGDIR}"
|
||||
DESTINATION "${CMAKE_INSTALL_LIBDIR}/cmake/${PROJECT_NAME}"
|
||||
)
|
||||
|
||||
configure_package_config_file(
|
||||
CMake/abslConfig.cmake.in
|
||||
"${PROJECT_BINARY_DIR}/${PROJECT_NAME}Config.cmake"
|
||||
INSTALL_DESTINATION "${ABSL_INSTALL_CONFIGDIR}"
|
||||
INSTALL_DESTINATION "${CMAKE_INSTALL_LIBDIR}/cmake/${PROJECT_NAME}"
|
||||
)
|
||||
install(FILES "${PROJECT_BINARY_DIR}/${PROJECT_NAME}Config.cmake"
|
||||
DESTINATION "${ABSL_INSTALL_CONFIGDIR}"
|
||||
DESTINATION "${CMAKE_INSTALL_LIBDIR}/cmake/${PROJECT_NAME}"
|
||||
)
|
||||
|
||||
# Abseil only has a version in LTS releases. This mechanism is accomplished
|
||||
@ -183,12 +199,12 @@ if(ABSL_ENABLE_INSTALL)
|
||||
)
|
||||
|
||||
install(FILES "${PROJECT_BINARY_DIR}/${PROJECT_NAME}ConfigVersion.cmake"
|
||||
DESTINATION ${ABSL_INSTALL_CONFIGDIR}
|
||||
DESTINATION "${CMAKE_INSTALL_LIBDIR}/cmake/${PROJECT_NAME}"
|
||||
)
|
||||
endif() # absl_VERSION
|
||||
|
||||
install(DIRECTORY absl
|
||||
DESTINATION ${ABSL_INSTALL_INCLUDEDIR}
|
||||
DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}
|
||||
FILES_MATCHING
|
||||
PATTERN "*.inc"
|
||||
PATTERN "*.h"
|
@ -27,7 +27,10 @@ compiler, there several ways to do this:
|
||||
file](https://docs.bazel.build/versions/master/guide.html#bazelrc)
|
||||
|
||||
If you are using CMake as the build system, you'll need to add a line like
|
||||
`set(CMAKE_CXX_STANDARD 17)` to your top level `CMakeLists.txt` file. See the
|
||||
`set(CMAKE_CXX_STANDARD 17)` to your top level `CMakeLists.txt` file. If you
|
||||
are developing a library designed to be used by other clients, you should
|
||||
instead leave `CMAKE_CXX_STANDARD` unset and configure the minimum C++ standard
|
||||
required by each of your library targets via `target_compile_features`. See the
|
||||
[CMake build
|
||||
instructions](https://github.com/abseil/abseil-cpp/blob/master/CMake/README.md)
|
||||
for more information.
|
@ -92,6 +92,9 @@ Abseil contains the following C++ library components:
|
||||
available within C++14 and C++17 versions of the C++ `<type_traits>` library.
|
||||
* [`numeric`](absl/numeric/)
|
||||
<br /> The `numeric` library contains C++11-compatible 128-bit integers.
|
||||
* [`profiling`](absl/profiling/)
|
||||
<br /> The `profiling` library contains utility code for profiling C++
|
||||
entities. It is currently a private dependency of other Abseil libraries.
|
||||
* [`status`](absl/status/)
|
||||
<br /> The `status` contains abstractions for error handling, specifically
|
||||
`absl::Status` and `absl::StatusOr<T>`.
|
61
ThirdParty/abseil-cpp-20220623.1/WORKSPACE
vendored
Normal file
61
ThirdParty/abseil-cpp-20220623.1/WORKSPACE
vendored
Normal file
@ -0,0 +1,61 @@
|
||||
#
|
||||
# Copyright 2019 The Abseil Authors.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# https://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
#
|
||||
|
||||
workspace(name = "com_google_absl")
|
||||
|
||||
load("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive")
|
||||
|
||||
# GoogleTest/GoogleMock framework. Used by most unit-tests.
|
||||
http_archive(
|
||||
name = "com_google_googletest",
|
||||
sha256 = "ce7366fe57eb49928311189cb0e40e0a8bf3d3682fca89af30d884c25e983786",
|
||||
strip_prefix = "googletest-release-1.12.0",
|
||||
# Keep this URL in sync with ABSL_GOOGLETEST_COMMIT in ci/cmake_common.sh.
|
||||
urls = ["https://github.com/google/googletest/archive/refs/tags/release-1.12.0.zip"],
|
||||
)
|
||||
|
||||
# RE2 (the regular expression library used by GoogleTest)
|
||||
# Note this must use a commit from the `abseil` branch of the RE2 project.
|
||||
# https://github.com/google/re2/tree/abseil
|
||||
http_archive(
|
||||
name = "com_googlesource_code_re2",
|
||||
sha256 = "0a890c2aa0bb05b2ce906a15efb520d0f5ad4c7d37b8db959c43772802991887",
|
||||
strip_prefix = "re2-a427f10b9fb4622dd6d8643032600aa1b50fbd12",
|
||||
urls = ["https://github.com/google/re2/archive/a427f10b9fb4622dd6d8643032600aa1b50fbd12.zip"], # 2022-06-09
|
||||
)
|
||||
|
||||
# Google benchmark.
|
||||
http_archive(
|
||||
name = "com_github_google_benchmark", # 2021-09-20T09:19:51Z
|
||||
sha256 = "62e2f2e6d8a744d67e4bbc212fcfd06647080de4253c97ad5c6749e09faf2cb0",
|
||||
strip_prefix = "benchmark-0baacde3618ca617da95375e0af13ce1baadea47",
|
||||
urls = ["https://github.com/google/benchmark/archive/0baacde3618ca617da95375e0af13ce1baadea47.zip"],
|
||||
)
|
||||
|
||||
# Bazel Skylib.
|
||||
http_archive(
|
||||
name = "bazel_skylib",
|
||||
urls = ["https://github.com/bazelbuild/bazel-skylib/releases/download/1.2.1/bazel-skylib-1.2.1.tar.gz"],
|
||||
sha256 = "f7be3474d42aae265405a592bb7da8e171919d74c16f082a5457840f06054728",
|
||||
)
|
||||
|
||||
# Bazel platform rules.
|
||||
http_archive(
|
||||
name = "platforms",
|
||||
sha256 = "a879ea428c6d56ab0ec18224f976515948822451473a80d06c2e50af0bbe5121",
|
||||
strip_prefix = "platforms-da5541f26b7de1dc8e04c075c99df5351742a4a2",
|
||||
urls = ["https://github.com/bazelbuild/platforms/archive/da5541f26b7de1dc8e04c075c99df5351742a4a2.zip"], # 2022-05-27
|
||||
)
|
@ -13,6 +13,8 @@
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
load("@bazel_skylib//lib:selects.bzl", "selects")
|
||||
|
||||
package(default_visibility = ["//visibility:public"])
|
||||
|
||||
licenses(["notice"])
|
||||
@ -44,14 +46,14 @@ config_setting(
|
||||
config_setting(
|
||||
name = "osx",
|
||||
constraint_values = [
|
||||
"@bazel_tools//platforms:osx",
|
||||
"@platforms//os:osx",
|
||||
],
|
||||
)
|
||||
|
||||
config_setting(
|
||||
name = "ios",
|
||||
constraint_values = [
|
||||
"@bazel_tools//platforms:ios",
|
||||
"@platforms//os:ios",
|
||||
],
|
||||
)
|
||||
|
||||
@ -64,9 +66,52 @@ config_setting(
|
||||
)
|
||||
|
||||
config_setting(
|
||||
name = "wasm",
|
||||
name = "cpu_wasm",
|
||||
values = {
|
||||
"cpu": "wasm",
|
||||
},
|
||||
visibility = [":__subpackages__"],
|
||||
)
|
||||
|
||||
config_setting(
|
||||
name = "cpu_wasm32",
|
||||
values = {
|
||||
"cpu": "wasm32",
|
||||
},
|
||||
visibility = [":__subpackages__"],
|
||||
)
|
||||
|
||||
config_setting(
|
||||
name = "platforms_wasm32",
|
||||
constraint_values = [
|
||||
"@platforms//cpu:wasm32",
|
||||
],
|
||||
visibility = [":__subpackages__"],
|
||||
)
|
||||
|
||||
config_setting(
|
||||
name = "platforms_wasm64",
|
||||
constraint_values = [
|
||||
"@platforms//cpu:wasm64",
|
||||
],
|
||||
visibility = [":__subpackages__"],
|
||||
)
|
||||
|
||||
selects.config_setting_group(
|
||||
name = "wasm",
|
||||
match_any = [
|
||||
":cpu_wasm",
|
||||
":cpu_wasm32",
|
||||
":platforms_wasm32",
|
||||
":platforms_wasm64",
|
||||
],
|
||||
visibility = [":__subpackages__"],
|
||||
)
|
||||
|
||||
config_setting(
|
||||
name = "fuchsia",
|
||||
values = {
|
||||
"cpu": "fuchsia",
|
||||
},
|
||||
visibility = [":__subpackages__"],
|
||||
)
|
@ -16,6 +16,7 @@
|
||||
|
||||
add_subdirectory(base)
|
||||
add_subdirectory(algorithm)
|
||||
add_subdirectory(cleanup)
|
||||
add_subdirectory(container)
|
||||
add_subdirectory(debugging)
|
||||
add_subdirectory(flags)
|
||||
@ -24,6 +25,7 @@ add_subdirectory(hash)
|
||||
add_subdirectory(memory)
|
||||
add_subdirectory(meta)
|
||||
add_subdirectory(numeric)
|
||||
add_subdirectory(profiling)
|
||||
add_subdirectory(random)
|
||||
add_subdirectory(status)
|
||||
add_subdirectory(strings)
|
@ -14,7 +14,6 @@
|
||||
# limitations under the License.
|
||||
#
|
||||
|
||||
load("@rules_cc//cc:defs.bzl", "cc_library", "cc_test")
|
||||
load(
|
||||
"//absl:copts/configure_copts.bzl",
|
||||
"ABSL_DEFAULT_COPTS",
|
||||
@ -44,6 +43,7 @@ cc_test(
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
deps = [
|
||||
":algorithm",
|
||||
"//absl/base:config",
|
||||
"@com_google_googletest//:gtest_main",
|
||||
],
|
||||
)
|
@ -35,7 +35,8 @@ absl_cc_test(
|
||||
${ABSL_TEST_COPTS}
|
||||
DEPS
|
||||
absl::algorithm
|
||||
gmock_main
|
||||
absl::config
|
||||
GTest::gmock_main
|
||||
)
|
||||
|
||||
absl_cc_library(
|
||||
@ -65,5 +66,5 @@ absl_cc_test(
|
||||
absl::core_headers
|
||||
absl::memory
|
||||
absl::span
|
||||
gmock_main
|
||||
GTest::gmock_main
|
||||
)
|
@ -20,6 +20,7 @@
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
#include "gtest/gtest.h"
|
||||
#include "absl/base/config.h"
|
||||
|
||||
namespace {
|
||||
|
||||
@ -50,7 +51,15 @@ TEST(EqualTest, EmptyRange) {
|
||||
std::vector<int> empty1;
|
||||
std::vector<int> empty2;
|
||||
|
||||
// https://gcc.gnu.org/bugzilla/show_bug.cgi?id=105705
|
||||
#if ABSL_INTERNAL_HAVE_MIN_GNUC_VERSION(12, 0)
|
||||
#pragma GCC diagnostic push
|
||||
#pragma GCC diagnostic ignored "-Wnonnull"
|
||||
#endif
|
||||
EXPECT_FALSE(absl::equal(v1.begin(), v1.end(), empty1.begin(), empty1.end()));
|
||||
#if ABSL_INTERNAL_HAVE_MIN_GNUC_VERSION(12, 0)
|
||||
#pragma GCC diagnostic pop
|
||||
#endif
|
||||
EXPECT_FALSE(absl::equal(empty1.begin(), empty1.end(), v1.begin(), v1.end()));
|
||||
EXPECT_TRUE(
|
||||
absl::equal(empty1.begin(), empty1.end(), empty2.begin(), empty2.end()));
|
@ -166,7 +166,7 @@ container_algorithm_internal::ContainerDifferenceType<const C> c_distance(
|
||||
// c_all_of()
|
||||
//
|
||||
// Container-based version of the <algorithm> `std::all_of()` function to
|
||||
// test a condition on all elements within a container.
|
||||
// test if all elements within a container satisfy a condition.
|
||||
template <typename C, typename Pred>
|
||||
bool c_all_of(const C& c, Pred&& pred) {
|
||||
return std::all_of(container_algorithm_internal::c_begin(c),
|
||||
@ -905,11 +905,11 @@ void c_sort(C& c) {
|
||||
|
||||
// Overload of c_sort() for performing a `comp` comparison other than the
|
||||
// default `operator<`.
|
||||
template <typename C, typename Compare>
|
||||
void c_sort(C& c, Compare&& comp) {
|
||||
template <typename C, typename LessThan>
|
||||
void c_sort(C& c, LessThan&& comp) {
|
||||
std::sort(container_algorithm_internal::c_begin(c),
|
||||
container_algorithm_internal::c_end(c),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_stable_sort()
|
||||
@ -925,11 +925,11 @@ void c_stable_sort(C& c) {
|
||||
|
||||
// Overload of c_stable_sort() for performing a `comp` comparison other than the
|
||||
// default `operator<`.
|
||||
template <typename C, typename Compare>
|
||||
void c_stable_sort(C& c, Compare&& comp) {
|
||||
template <typename C, typename LessThan>
|
||||
void c_stable_sort(C& c, LessThan&& comp) {
|
||||
std::stable_sort(container_algorithm_internal::c_begin(c),
|
||||
container_algorithm_internal::c_end(c),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_is_sorted()
|
||||
@ -944,11 +944,11 @@ bool c_is_sorted(const C& c) {
|
||||
|
||||
// c_is_sorted() overload for performing a `comp` comparison other than the
|
||||
// default `operator<`.
|
||||
template <typename C, typename Compare>
|
||||
bool c_is_sorted(const C& c, Compare&& comp) {
|
||||
template <typename C, typename LessThan>
|
||||
bool c_is_sorted(const C& c, LessThan&& comp) {
|
||||
return std::is_sorted(container_algorithm_internal::c_begin(c),
|
||||
container_algorithm_internal::c_end(c),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_partial_sort()
|
||||
@ -966,14 +966,14 @@ void c_partial_sort(
|
||||
|
||||
// Overload of c_partial_sort() for performing a `comp` comparison other than
|
||||
// the default `operator<`.
|
||||
template <typename RandomAccessContainer, typename Compare>
|
||||
template <typename RandomAccessContainer, typename LessThan>
|
||||
void c_partial_sort(
|
||||
RandomAccessContainer& sequence,
|
||||
container_algorithm_internal::ContainerIter<RandomAccessContainer> middle,
|
||||
Compare&& comp) {
|
||||
LessThan&& comp) {
|
||||
std::partial_sort(container_algorithm_internal::c_begin(sequence), middle,
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_partial_sort_copy()
|
||||
@ -994,15 +994,15 @@ c_partial_sort_copy(const C& sequence, RandomAccessContainer& result) {
|
||||
|
||||
// Overload of c_partial_sort_copy() for performing a `comp` comparison other
|
||||
// than the default `operator<`.
|
||||
template <typename C, typename RandomAccessContainer, typename Compare>
|
||||
template <typename C, typename RandomAccessContainer, typename LessThan>
|
||||
container_algorithm_internal::ContainerIter<RandomAccessContainer>
|
||||
c_partial_sort_copy(const C& sequence, RandomAccessContainer& result,
|
||||
Compare&& comp) {
|
||||
LessThan&& comp) {
|
||||
return std::partial_sort_copy(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
container_algorithm_internal::c_begin(result),
|
||||
container_algorithm_internal::c_end(result),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_is_sorted_until()
|
||||
@ -1018,12 +1018,12 @@ container_algorithm_internal::ContainerIter<C> c_is_sorted_until(C& c) {
|
||||
|
||||
// Overload of c_is_sorted_until() for performing a `comp` comparison other than
|
||||
// the default `operator<`.
|
||||
template <typename C, typename Compare>
|
||||
template <typename C, typename LessThan>
|
||||
container_algorithm_internal::ContainerIter<C> c_is_sorted_until(
|
||||
C& c, Compare&& comp) {
|
||||
C& c, LessThan&& comp) {
|
||||
return std::is_sorted_until(container_algorithm_internal::c_begin(c),
|
||||
container_algorithm_internal::c_end(c),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_nth_element()
|
||||
@ -1043,14 +1043,14 @@ void c_nth_element(
|
||||
|
||||
// Overload of c_nth_element() for performing a `comp` comparison other than
|
||||
// the default `operator<`.
|
||||
template <typename RandomAccessContainer, typename Compare>
|
||||
template <typename RandomAccessContainer, typename LessThan>
|
||||
void c_nth_element(
|
||||
RandomAccessContainer& sequence,
|
||||
container_algorithm_internal::ContainerIter<RandomAccessContainer> nth,
|
||||
Compare&& comp) {
|
||||
LessThan&& comp) {
|
||||
std::nth_element(container_algorithm_internal::c_begin(sequence), nth,
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
@ -1072,12 +1072,12 @@ container_algorithm_internal::ContainerIter<Sequence> c_lower_bound(
|
||||
|
||||
// Overload of c_lower_bound() for performing a `comp` comparison other than
|
||||
// the default `operator<`.
|
||||
template <typename Sequence, typename T, typename Compare>
|
||||
template <typename Sequence, typename T, typename LessThan>
|
||||
container_algorithm_internal::ContainerIter<Sequence> c_lower_bound(
|
||||
Sequence& sequence, T&& value, Compare&& comp) {
|
||||
Sequence& sequence, T&& value, LessThan&& comp) {
|
||||
return std::lower_bound(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<T>(value), std::forward<Compare>(comp));
|
||||
std::forward<T>(value), std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_upper_bound()
|
||||
@ -1095,12 +1095,12 @@ container_algorithm_internal::ContainerIter<Sequence> c_upper_bound(
|
||||
|
||||
// Overload of c_upper_bound() for performing a `comp` comparison other than
|
||||
// the default `operator<`.
|
||||
template <typename Sequence, typename T, typename Compare>
|
||||
template <typename Sequence, typename T, typename LessThan>
|
||||
container_algorithm_internal::ContainerIter<Sequence> c_upper_bound(
|
||||
Sequence& sequence, T&& value, Compare&& comp) {
|
||||
Sequence& sequence, T&& value, LessThan&& comp) {
|
||||
return std::upper_bound(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<T>(value), std::forward<Compare>(comp));
|
||||
std::forward<T>(value), std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_equal_range()
|
||||
@ -1118,12 +1118,12 @@ c_equal_range(Sequence& sequence, T&& value) {
|
||||
|
||||
// Overload of c_equal_range() for performing a `comp` comparison other than
|
||||
// the default `operator<`.
|
||||
template <typename Sequence, typename T, typename Compare>
|
||||
template <typename Sequence, typename T, typename LessThan>
|
||||
container_algorithm_internal::ContainerIterPairType<Sequence, Sequence>
|
||||
c_equal_range(Sequence& sequence, T&& value, Compare&& comp) {
|
||||
c_equal_range(Sequence& sequence, T&& value, LessThan&& comp) {
|
||||
return std::equal_range(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<T>(value), std::forward<Compare>(comp));
|
||||
std::forward<T>(value), std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_binary_search()
|
||||
@ -1140,12 +1140,12 @@ bool c_binary_search(Sequence&& sequence, T&& value) {
|
||||
|
||||
// Overload of c_binary_search() for performing a `comp` comparison other than
|
||||
// the default `operator<`.
|
||||
template <typename Sequence, typename T, typename Compare>
|
||||
bool c_binary_search(Sequence&& sequence, T&& value, Compare&& comp) {
|
||||
template <typename Sequence, typename T, typename LessThan>
|
||||
bool c_binary_search(Sequence&& sequence, T&& value, LessThan&& comp) {
|
||||
return std::binary_search(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<T>(value),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
@ -1166,14 +1166,14 @@ OutputIterator c_merge(const C1& c1, const C2& c2, OutputIterator result) {
|
||||
|
||||
// Overload of c_merge() for performing a `comp` comparison other than
|
||||
// the default `operator<`.
|
||||
template <typename C1, typename C2, typename OutputIterator, typename Compare>
|
||||
template <typename C1, typename C2, typename OutputIterator, typename LessThan>
|
||||
OutputIterator c_merge(const C1& c1, const C2& c2, OutputIterator result,
|
||||
Compare&& comp) {
|
||||
LessThan&& comp) {
|
||||
return std::merge(container_algorithm_internal::c_begin(c1),
|
||||
container_algorithm_internal::c_end(c1),
|
||||
container_algorithm_internal::c_begin(c2),
|
||||
container_algorithm_internal::c_end(c2), result,
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_inplace_merge()
|
||||
@ -1189,13 +1189,13 @@ void c_inplace_merge(C& c,
|
||||
|
||||
// Overload of c_inplace_merge() for performing a merge using a `comp` other
|
||||
// than `operator<`.
|
||||
template <typename C, typename Compare>
|
||||
template <typename C, typename LessThan>
|
||||
void c_inplace_merge(C& c,
|
||||
container_algorithm_internal::ContainerIter<C> middle,
|
||||
Compare&& comp) {
|
||||
LessThan&& comp) {
|
||||
std::inplace_merge(container_algorithm_internal::c_begin(c), middle,
|
||||
container_algorithm_internal::c_end(c),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_includes()
|
||||
@ -1213,13 +1213,13 @@ bool c_includes(const C1& c1, const C2& c2) {
|
||||
|
||||
// Overload of c_includes() for performing a merge using a `comp` other than
|
||||
// `operator<`.
|
||||
template <typename C1, typename C2, typename Compare>
|
||||
bool c_includes(const C1& c1, const C2& c2, Compare&& comp) {
|
||||
template <typename C1, typename C2, typename LessThan>
|
||||
bool c_includes(const C1& c1, const C2& c2, LessThan&& comp) {
|
||||
return std::includes(container_algorithm_internal::c_begin(c1),
|
||||
container_algorithm_internal::c_end(c1),
|
||||
container_algorithm_internal::c_begin(c2),
|
||||
container_algorithm_internal::c_end(c2),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_set_union()
|
||||
@ -1243,7 +1243,7 @@ OutputIterator c_set_union(const C1& c1, const C2& c2, OutputIterator output) {
|
||||
|
||||
// Overload of c_set_union() for performing a merge using a `comp` other than
|
||||
// `operator<`.
|
||||
template <typename C1, typename C2, typename OutputIterator, typename Compare,
|
||||
template <typename C1, typename C2, typename OutputIterator, typename LessThan,
|
||||
typename = typename std::enable_if<
|
||||
!container_algorithm_internal::IsUnorderedContainer<C1>::value,
|
||||
void>::type,
|
||||
@ -1251,18 +1251,18 @@ template <typename C1, typename C2, typename OutputIterator, typename Compare,
|
||||
!container_algorithm_internal::IsUnorderedContainer<C2>::value,
|
||||
void>::type>
|
||||
OutputIterator c_set_union(const C1& c1, const C2& c2, OutputIterator output,
|
||||
Compare&& comp) {
|
||||
LessThan&& comp) {
|
||||
return std::set_union(container_algorithm_internal::c_begin(c1),
|
||||
container_algorithm_internal::c_end(c1),
|
||||
container_algorithm_internal::c_begin(c2),
|
||||
container_algorithm_internal::c_end(c2), output,
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_set_intersection()
|
||||
//
|
||||
// Container-based version of the <algorithm> `std::set_intersection()` function
|
||||
// to return an iterator containing the intersection of two containers.
|
||||
// to return an iterator containing the intersection of two sorted containers.
|
||||
template <typename C1, typename C2, typename OutputIterator,
|
||||
typename = typename std::enable_if<
|
||||
!container_algorithm_internal::IsUnorderedContainer<C1>::value,
|
||||
@ -1272,6 +1272,11 @@ template <typename C1, typename C2, typename OutputIterator,
|
||||
void>::type>
|
||||
OutputIterator c_set_intersection(const C1& c1, const C2& c2,
|
||||
OutputIterator output) {
|
||||
// In debug builds, ensure that both containers are sorted with respect to the
|
||||
// default comparator. std::set_intersection requires the containers be sorted
|
||||
// using operator<.
|
||||
assert(absl::c_is_sorted(c1));
|
||||
assert(absl::c_is_sorted(c2));
|
||||
return std::set_intersection(container_algorithm_internal::c_begin(c1),
|
||||
container_algorithm_internal::c_end(c1),
|
||||
container_algorithm_internal::c_begin(c2),
|
||||
@ -1280,7 +1285,7 @@ OutputIterator c_set_intersection(const C1& c1, const C2& c2,
|
||||
|
||||
// Overload of c_set_intersection() for performing a merge using a `comp` other
|
||||
// than `operator<`.
|
||||
template <typename C1, typename C2, typename OutputIterator, typename Compare,
|
||||
template <typename C1, typename C2, typename OutputIterator, typename LessThan,
|
||||
typename = typename std::enable_if<
|
||||
!container_algorithm_internal::IsUnorderedContainer<C1>::value,
|
||||
void>::type,
|
||||
@ -1288,12 +1293,17 @@ template <typename C1, typename C2, typename OutputIterator, typename Compare,
|
||||
!container_algorithm_internal::IsUnorderedContainer<C2>::value,
|
||||
void>::type>
|
||||
OutputIterator c_set_intersection(const C1& c1, const C2& c2,
|
||||
OutputIterator output, Compare&& comp) {
|
||||
OutputIterator output, LessThan&& comp) {
|
||||
// In debug builds, ensure that both containers are sorted with respect to the
|
||||
// default comparator. std::set_intersection requires the containers be sorted
|
||||
// using the same comparator.
|
||||
assert(absl::c_is_sorted(c1, comp));
|
||||
assert(absl::c_is_sorted(c2, comp));
|
||||
return std::set_intersection(container_algorithm_internal::c_begin(c1),
|
||||
container_algorithm_internal::c_end(c1),
|
||||
container_algorithm_internal::c_begin(c2),
|
||||
container_algorithm_internal::c_end(c2), output,
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_set_difference()
|
||||
@ -1318,7 +1328,7 @@ OutputIterator c_set_difference(const C1& c1, const C2& c2,
|
||||
|
||||
// Overload of c_set_difference() for performing a merge using a `comp` other
|
||||
// than `operator<`.
|
||||
template <typename C1, typename C2, typename OutputIterator, typename Compare,
|
||||
template <typename C1, typename C2, typename OutputIterator, typename LessThan,
|
||||
typename = typename std::enable_if<
|
||||
!container_algorithm_internal::IsUnorderedContainer<C1>::value,
|
||||
void>::type,
|
||||
@ -1326,12 +1336,12 @@ template <typename C1, typename C2, typename OutputIterator, typename Compare,
|
||||
!container_algorithm_internal::IsUnorderedContainer<C2>::value,
|
||||
void>::type>
|
||||
OutputIterator c_set_difference(const C1& c1, const C2& c2,
|
||||
OutputIterator output, Compare&& comp) {
|
||||
OutputIterator output, LessThan&& comp) {
|
||||
return std::set_difference(container_algorithm_internal::c_begin(c1),
|
||||
container_algorithm_internal::c_end(c1),
|
||||
container_algorithm_internal::c_begin(c2),
|
||||
container_algorithm_internal::c_end(c2), output,
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_set_symmetric_difference()
|
||||
@ -1357,7 +1367,7 @@ OutputIterator c_set_symmetric_difference(const C1& c1, const C2& c2,
|
||||
|
||||
// Overload of c_set_symmetric_difference() for performing a merge using a
|
||||
// `comp` other than `operator<`.
|
||||
template <typename C1, typename C2, typename OutputIterator, typename Compare,
|
||||
template <typename C1, typename C2, typename OutputIterator, typename LessThan,
|
||||
typename = typename std::enable_if<
|
||||
!container_algorithm_internal::IsUnorderedContainer<C1>::value,
|
||||
void>::type,
|
||||
@ -1366,13 +1376,13 @@ template <typename C1, typename C2, typename OutputIterator, typename Compare,
|
||||
void>::type>
|
||||
OutputIterator c_set_symmetric_difference(const C1& c1, const C2& c2,
|
||||
OutputIterator output,
|
||||
Compare&& comp) {
|
||||
LessThan&& comp) {
|
||||
return std::set_symmetric_difference(
|
||||
container_algorithm_internal::c_begin(c1),
|
||||
container_algorithm_internal::c_end(c1),
|
||||
container_algorithm_internal::c_begin(c2),
|
||||
container_algorithm_internal::c_end(c2), output,
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
@ -1391,11 +1401,11 @@ void c_push_heap(RandomAccessContainer& sequence) {
|
||||
|
||||
// Overload of c_push_heap() for performing a push operation on a heap using a
|
||||
// `comp` other than `operator<`.
|
||||
template <typename RandomAccessContainer, typename Compare>
|
||||
void c_push_heap(RandomAccessContainer& sequence, Compare&& comp) {
|
||||
template <typename RandomAccessContainer, typename LessThan>
|
||||
void c_push_heap(RandomAccessContainer& sequence, LessThan&& comp) {
|
||||
std::push_heap(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_pop_heap()
|
||||
@ -1410,11 +1420,11 @@ void c_pop_heap(RandomAccessContainer& sequence) {
|
||||
|
||||
// Overload of c_pop_heap() for performing a pop operation on a heap using a
|
||||
// `comp` other than `operator<`.
|
||||
template <typename RandomAccessContainer, typename Compare>
|
||||
void c_pop_heap(RandomAccessContainer& sequence, Compare&& comp) {
|
||||
template <typename RandomAccessContainer, typename LessThan>
|
||||
void c_pop_heap(RandomAccessContainer& sequence, LessThan&& comp) {
|
||||
std::pop_heap(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_make_heap()
|
||||
@ -1429,11 +1439,11 @@ void c_make_heap(RandomAccessContainer& sequence) {
|
||||
|
||||
// Overload of c_make_heap() for performing heap comparisons using a
|
||||
// `comp` other than `operator<`
|
||||
template <typename RandomAccessContainer, typename Compare>
|
||||
void c_make_heap(RandomAccessContainer& sequence, Compare&& comp) {
|
||||
template <typename RandomAccessContainer, typename LessThan>
|
||||
void c_make_heap(RandomAccessContainer& sequence, LessThan&& comp) {
|
||||
std::make_heap(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_sort_heap()
|
||||
@ -1448,11 +1458,11 @@ void c_sort_heap(RandomAccessContainer& sequence) {
|
||||
|
||||
// Overload of c_sort_heap() for performing heap comparisons using a
|
||||
// `comp` other than `operator<`
|
||||
template <typename RandomAccessContainer, typename Compare>
|
||||
void c_sort_heap(RandomAccessContainer& sequence, Compare&& comp) {
|
||||
template <typename RandomAccessContainer, typename LessThan>
|
||||
void c_sort_heap(RandomAccessContainer& sequence, LessThan&& comp) {
|
||||
std::sort_heap(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_is_heap()
|
||||
@ -1467,11 +1477,11 @@ bool c_is_heap(const RandomAccessContainer& sequence) {
|
||||
|
||||
// Overload of c_is_heap() for performing heap comparisons using a
|
||||
// `comp` other than `operator<`
|
||||
template <typename RandomAccessContainer, typename Compare>
|
||||
bool c_is_heap(const RandomAccessContainer& sequence, Compare&& comp) {
|
||||
template <typename RandomAccessContainer, typename LessThan>
|
||||
bool c_is_heap(const RandomAccessContainer& sequence, LessThan&& comp) {
|
||||
return std::is_heap(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_is_heap_until()
|
||||
@ -1487,12 +1497,12 @@ c_is_heap_until(RandomAccessContainer& sequence) {
|
||||
|
||||
// Overload of c_is_heap_until() for performing heap comparisons using a
|
||||
// `comp` other than `operator<`
|
||||
template <typename RandomAccessContainer, typename Compare>
|
||||
template <typename RandomAccessContainer, typename LessThan>
|
||||
container_algorithm_internal::ContainerIter<RandomAccessContainer>
|
||||
c_is_heap_until(RandomAccessContainer& sequence, Compare&& comp) {
|
||||
c_is_heap_until(RandomAccessContainer& sequence, LessThan&& comp) {
|
||||
return std::is_heap_until(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
@ -1513,12 +1523,12 @@ container_algorithm_internal::ContainerIter<Sequence> c_min_element(
|
||||
|
||||
// Overload of c_min_element() for performing a `comp` comparison other than
|
||||
// `operator<`.
|
||||
template <typename Sequence, typename Compare>
|
||||
template <typename Sequence, typename LessThan>
|
||||
container_algorithm_internal::ContainerIter<Sequence> c_min_element(
|
||||
Sequence& sequence, Compare&& comp) {
|
||||
Sequence& sequence, LessThan&& comp) {
|
||||
return std::min_element(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_max_element()
|
||||
@ -1535,12 +1545,12 @@ container_algorithm_internal::ContainerIter<Sequence> c_max_element(
|
||||
|
||||
// Overload of c_max_element() for performing a `comp` comparison other than
|
||||
// `operator<`.
|
||||
template <typename Sequence, typename Compare>
|
||||
template <typename Sequence, typename LessThan>
|
||||
container_algorithm_internal::ContainerIter<Sequence> c_max_element(
|
||||
Sequence& sequence, Compare&& comp) {
|
||||
Sequence& sequence, LessThan&& comp) {
|
||||
return std::max_element(container_algorithm_internal::c_begin(sequence),
|
||||
container_algorithm_internal::c_end(sequence),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_minmax_element()
|
||||
@ -1558,12 +1568,12 @@ c_minmax_element(C& c) {
|
||||
|
||||
// Overload of c_minmax_element() for performing `comp` comparisons other than
|
||||
// `operator<`.
|
||||
template <typename C, typename Compare>
|
||||
template <typename C, typename LessThan>
|
||||
container_algorithm_internal::ContainerIterPairType<C, C>
|
||||
c_minmax_element(C& c, Compare&& comp) {
|
||||
c_minmax_element(C& c, LessThan&& comp) {
|
||||
return std::minmax_element(container_algorithm_internal::c_begin(c),
|
||||
container_algorithm_internal::c_end(c),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
@ -1588,15 +1598,15 @@ bool c_lexicographical_compare(Sequence1&& sequence1, Sequence2&& sequence2) {
|
||||
|
||||
// Overload of c_lexicographical_compare() for performing a lexicographical
|
||||
// comparison using a `comp` operator instead of `operator<`.
|
||||
template <typename Sequence1, typename Sequence2, typename Compare>
|
||||
template <typename Sequence1, typename Sequence2, typename LessThan>
|
||||
bool c_lexicographical_compare(Sequence1&& sequence1, Sequence2&& sequence2,
|
||||
Compare&& comp) {
|
||||
LessThan&& comp) {
|
||||
return std::lexicographical_compare(
|
||||
container_algorithm_internal::c_begin(sequence1),
|
||||
container_algorithm_internal::c_end(sequence1),
|
||||
container_algorithm_internal::c_begin(sequence2),
|
||||
container_algorithm_internal::c_end(sequence2),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_next_permutation()
|
||||
@ -1612,11 +1622,11 @@ bool c_next_permutation(C& c) {
|
||||
|
||||
// Overload of c_next_permutation() for performing a lexicographical
|
||||
// comparison using a `comp` operator instead of `operator<`.
|
||||
template <typename C, typename Compare>
|
||||
bool c_next_permutation(C& c, Compare&& comp) {
|
||||
template <typename C, typename LessThan>
|
||||
bool c_next_permutation(C& c, LessThan&& comp) {
|
||||
return std::next_permutation(container_algorithm_internal::c_begin(c),
|
||||
container_algorithm_internal::c_end(c),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
// c_prev_permutation()
|
||||
@ -1632,11 +1642,11 @@ bool c_prev_permutation(C& c) {
|
||||
|
||||
// Overload of c_prev_permutation() for performing a lexicographical
|
||||
// comparison using a `comp` operator instead of `operator<`.
|
||||
template <typename C, typename Compare>
|
||||
bool c_prev_permutation(C& c, Compare&& comp) {
|
||||
template <typename C, typename LessThan>
|
||||
bool c_prev_permutation(C& c, LessThan&& comp) {
|
||||
return std::prev_permutation(container_algorithm_internal::c_begin(c),
|
||||
container_algorithm_internal::c_end(c),
|
||||
std::forward<Compare>(comp));
|
||||
std::forward<LessThan>(comp));
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
@ -14,7 +14,6 @@
|
||||
# limitations under the License.
|
||||
#
|
||||
|
||||
load("@rules_cc//cc:defs.bzl", "cc_binary", "cc_library", "cc_test")
|
||||
load(
|
||||
"//absl:copts/configure_copts.bzl",
|
||||
"ABSL_DEFAULT_COPTS",
|
||||
@ -76,6 +75,7 @@ cc_library(
|
||||
":atomic_hook",
|
||||
":config",
|
||||
":core_headers",
|
||||
":errno_saver",
|
||||
":log_severity",
|
||||
],
|
||||
)
|
||||
@ -158,7 +158,9 @@ cc_library(
|
||||
"internal/direct_mmap.h",
|
||||
"internal/low_level_alloc.h",
|
||||
],
|
||||
copts = ABSL_DEFAULT_COPTS,
|
||||
copts = ABSL_DEFAULT_COPTS + select({
|
||||
"//conditions:default": [],
|
||||
}),
|
||||
linkopts = select({
|
||||
"//absl:msvc_compiler": [],
|
||||
"//absl:clang-cl_compiler": [],
|
||||
@ -433,6 +435,9 @@ cc_test(
|
||||
srcs = ["spinlock_test_common.cc"],
|
||||
copts = ABSL_TEST_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
tags = [
|
||||
"no_test_wasm",
|
||||
],
|
||||
deps = [
|
||||
":base",
|
||||
":base_internal",
|
||||
@ -558,6 +563,7 @@ cc_test(
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
tags = [
|
||||
"no_test_ios_x86_64",
|
||||
"no_test_wasm",
|
||||
],
|
||||
deps = [
|
||||
":malloc_internal",
|
||||
@ -571,6 +577,9 @@ cc_test(
|
||||
srcs = ["internal/thread_identity_test.cc"],
|
||||
copts = ABSL_TEST_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
tags = [
|
||||
"no_test_wasm",
|
||||
],
|
||||
deps = [
|
||||
":base",
|
||||
":core_headers",
|
||||
@ -593,75 +602,6 @@ cc_test(
|
||||
],
|
||||
)
|
||||
|
||||
cc_library(
|
||||
name = "exponential_biased",
|
||||
srcs = ["internal/exponential_biased.cc"],
|
||||
hdrs = ["internal/exponential_biased.h"],
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
visibility = [
|
||||
"//absl:__subpackages__",
|
||||
],
|
||||
deps = [
|
||||
":config",
|
||||
":core_headers",
|
||||
],
|
||||
)
|
||||
|
||||
cc_test(
|
||||
name = "exponential_biased_test",
|
||||
size = "small",
|
||||
srcs = ["internal/exponential_biased_test.cc"],
|
||||
copts = ABSL_TEST_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
visibility = ["//visibility:private"],
|
||||
deps = [
|
||||
":exponential_biased",
|
||||
"//absl/strings",
|
||||
"@com_google_googletest//:gtest_main",
|
||||
],
|
||||
)
|
||||
|
||||
cc_library(
|
||||
name = "periodic_sampler",
|
||||
srcs = ["internal/periodic_sampler.cc"],
|
||||
hdrs = ["internal/periodic_sampler.h"],
|
||||
copts = ABSL_DEFAULT_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
deps = [
|
||||
":core_headers",
|
||||
":exponential_biased",
|
||||
],
|
||||
)
|
||||
|
||||
cc_test(
|
||||
name = "periodic_sampler_test",
|
||||
size = "small",
|
||||
srcs = ["internal/periodic_sampler_test.cc"],
|
||||
copts = ABSL_TEST_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
visibility = ["//visibility:private"],
|
||||
deps = [
|
||||
":core_headers",
|
||||
":periodic_sampler",
|
||||
"@com_google_googletest//:gtest_main",
|
||||
],
|
||||
)
|
||||
|
||||
cc_binary(
|
||||
name = "periodic_sampler_benchmark",
|
||||
testonly = 1,
|
||||
srcs = ["internal/periodic_sampler_benchmark.cc"],
|
||||
copts = ABSL_TEST_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
tags = ["benchmark"],
|
||||
visibility = ["//visibility:private"],
|
||||
deps = [
|
||||
":core_headers",
|
||||
":periodic_sampler",
|
||||
"@com_github_google_benchmark//:benchmark_main",
|
||||
],
|
||||
)
|
||||
|
||||
cc_library(
|
||||
name = "scoped_set_env",
|
||||
testonly = 1,
|
||||
@ -772,6 +712,31 @@ cc_test(
|
||||
],
|
||||
)
|
||||
|
||||
cc_library(
|
||||
name = "prefetch",
|
||||
hdrs = ["internal/prefetch.h"],
|
||||
copts = ABSL_DEFAULT_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
visibility = [
|
||||
"//absl:__subpackages__",
|
||||
],
|
||||
deps = [
|
||||
":config",
|
||||
],
|
||||
)
|
||||
|
||||
cc_test(
|
||||
name = "prefetch_test",
|
||||
size = "small",
|
||||
srcs = ["internal/prefetch_test.cc"],
|
||||
copts = ABSL_TEST_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
deps = [
|
||||
":prefetch",
|
||||
"@com_google_googletest//:gtest_main",
|
||||
],
|
||||
)
|
||||
|
||||
cc_test(
|
||||
name = "unique_small_name_test",
|
||||
size = "small",
|
@ -16,6 +16,7 @@
|
||||
|
||||
find_library(LIBRT rt)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
atomic_hook
|
||||
@ -28,6 +29,7 @@ absl_cc_library(
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
errno_saver
|
||||
@ -52,6 +54,7 @@ absl_cc_library(
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
raw_logging_internal
|
||||
@ -63,11 +66,13 @@ absl_cc_library(
|
||||
absl::atomic_hook
|
||||
absl::config
|
||||
absl::core_headers
|
||||
absl::errno_saver
|
||||
absl::log_severity
|
||||
COPTS
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
spinlock_wait
|
||||
@ -131,6 +136,7 @@ absl_cc_library(
|
||||
PUBLIC
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
malloc_internal
|
||||
@ -151,6 +157,7 @@ absl_cc_library(
|
||||
Threads::Threads
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
base_internal
|
||||
@ -207,6 +214,7 @@ absl_cc_library(
|
||||
PUBLIC
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
throw_delegate
|
||||
@ -221,6 +229,7 @@ absl_cc_library(
|
||||
absl::raw_logging_internal
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
exception_testing
|
||||
@ -230,10 +239,11 @@ absl_cc_library(
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
DEPS
|
||||
absl::config
|
||||
gtest
|
||||
GTest::gtest
|
||||
TESTONLY
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
pretty_function
|
||||
@ -243,6 +253,7 @@ absl_cc_library(
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
exception_safety_testing
|
||||
@ -259,7 +270,7 @@ absl_cc_library(
|
||||
absl::meta
|
||||
absl::strings
|
||||
absl::utility
|
||||
gtest
|
||||
GTest::gtest
|
||||
TESTONLY
|
||||
)
|
||||
|
||||
@ -273,9 +284,10 @@ absl_cc_test(
|
||||
DEPS
|
||||
absl::exception_safety_testing
|
||||
absl::memory
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
atomic_hook_test_helper
|
||||
@ -300,8 +312,8 @@ absl_cc_test(
|
||||
absl::atomic_hook_test_helper
|
||||
absl::atomic_hook
|
||||
absl::core_headers
|
||||
gmock
|
||||
gtest_main
|
||||
GTest::gmock
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
@ -314,7 +326,7 @@ absl_cc_test(
|
||||
DEPS
|
||||
absl::base
|
||||
absl::core_headers
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
@ -327,8 +339,8 @@ absl_cc_test(
|
||||
DEPS
|
||||
absl::errno_saver
|
||||
absl::strerror
|
||||
gmock
|
||||
gtest_main
|
||||
GTest::gmock
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
@ -342,7 +354,7 @@ absl_cc_test(
|
||||
absl::base
|
||||
absl::config
|
||||
absl::throw_delegate
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
@ -357,7 +369,7 @@ absl_cc_test(
|
||||
${ABSL_TEST_COPTS}
|
||||
DEPS
|
||||
absl::base_internal
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
@ -371,10 +383,11 @@ absl_cc_test(
|
||||
absl::base_internal
|
||||
absl::memory
|
||||
absl::strings
|
||||
gmock
|
||||
gtest_main
|
||||
GTest::gmock
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
spinlock_test_common
|
||||
@ -388,7 +401,7 @@ absl_cc_library(
|
||||
absl::base_internal
|
||||
absl::core_headers
|
||||
absl::synchronization
|
||||
gtest
|
||||
GTest::gtest
|
||||
TESTONLY
|
||||
)
|
||||
|
||||
@ -406,9 +419,10 @@ absl_cc_test(
|
||||
absl::config
|
||||
absl::core_headers
|
||||
absl::synchronization
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
endian
|
||||
@ -435,7 +449,7 @@ absl_cc_test(
|
||||
absl::base
|
||||
absl::config
|
||||
absl::endian
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
@ -448,7 +462,7 @@ absl_cc_test(
|
||||
DEPS
|
||||
absl::config
|
||||
absl::synchronization
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
@ -462,7 +476,7 @@ absl_cc_test(
|
||||
absl::base
|
||||
absl::core_headers
|
||||
absl::synchronization
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
@ -475,7 +489,7 @@ absl_cc_test(
|
||||
DEPS
|
||||
absl::raw_logging_internal
|
||||
absl::strings
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
@ -488,7 +502,7 @@ absl_cc_test(
|
||||
DEPS
|
||||
absl::base
|
||||
absl::synchronization
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
@ -516,63 +530,10 @@ absl_cc_test(
|
||||
absl::core_headers
|
||||
absl::synchronization
|
||||
Threads::Threads
|
||||
gtest_main
|
||||
)
|
||||
|
||||
absl_cc_library(
|
||||
NAME
|
||||
exponential_biased
|
||||
SRCS
|
||||
"internal/exponential_biased.cc"
|
||||
HDRS
|
||||
"internal/exponential_biased.h"
|
||||
COPTS
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
DEPS
|
||||
absl::config
|
||||
absl::core_headers
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
NAME
|
||||
exponential_biased_test
|
||||
SRCS
|
||||
"internal/exponential_biased_test.cc"
|
||||
COPTS
|
||||
${ABSL_TEST_COPTS}
|
||||
DEPS
|
||||
absl::exponential_biased
|
||||
absl::strings
|
||||
gmock_main
|
||||
)
|
||||
|
||||
absl_cc_library(
|
||||
NAME
|
||||
periodic_sampler
|
||||
SRCS
|
||||
"internal/periodic_sampler.cc"
|
||||
HDRS
|
||||
"internal/periodic_sampler.h"
|
||||
COPTS
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
DEPS
|
||||
absl::core_headers
|
||||
absl::exponential_biased
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
NAME
|
||||
periodic_sampler_test
|
||||
SRCS
|
||||
"internal/periodic_sampler_test.cc"
|
||||
COPTS
|
||||
${ABSL_TEST_COPTS}
|
||||
DEPS
|
||||
absl::core_headers
|
||||
absl::periodic_sampler
|
||||
gmock_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
scoped_set_env
|
||||
@ -596,7 +557,7 @@ absl_cc_test(
|
||||
${ABSL_TEST_COPTS}
|
||||
DEPS
|
||||
absl::scoped_set_env
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
@ -620,10 +581,11 @@ absl_cc_test(
|
||||
absl::flags_marshalling
|
||||
absl::log_severity
|
||||
absl::strings
|
||||
gmock
|
||||
gtest_main
|
||||
GTest::gmock
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
strerror
|
||||
@ -651,10 +613,11 @@ absl_cc_test(
|
||||
DEPS
|
||||
absl::strerror
|
||||
absl::strings
|
||||
gmock
|
||||
gtest_main
|
||||
GTest::gmock
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
fast_type_id
|
||||
@ -677,7 +640,33 @@ absl_cc_test(
|
||||
${ABSL_TEST_COPTS}
|
||||
DEPS
|
||||
absl::fast_type_id
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
prefetch
|
||||
HDRS
|
||||
"internal/prefetch.h"
|
||||
COPTS
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
LINKOPTS
|
||||
${ABSL_DEFAULT_LINKOPTS}
|
||||
DEPS
|
||||
absl::config
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
NAME
|
||||
prefetch_test
|
||||
SRCS
|
||||
"internal/prefetch_test.cc"
|
||||
COPTS
|
||||
${ABSL_TEST_COPTS}
|
||||
DEPS
|
||||
absl::prefetch
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
absl_cc_test(
|
||||
@ -690,5 +679,5 @@ absl_cc_test(
|
||||
DEPS
|
||||
absl::core_headers
|
||||
absl::optional
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
@ -131,14 +131,15 @@
|
||||
// ABSL_ATTRIBUTE_WEAK
|
||||
//
|
||||
// Tags a function as weak for the purposes of compilation and linking.
|
||||
// Weak attributes currently do not work properly in LLVM's Windows backend,
|
||||
// so disable them there. See https://bugs.llvm.org/show_bug.cgi?id=37598
|
||||
// Weak attributes did not work properly in LLVM's Windows backend before
|
||||
// 9.0.0, so disable them there. See https://bugs.llvm.org/show_bug.cgi?id=37598
|
||||
// for further information.
|
||||
// The MinGW compiler doesn't complain about the weak attribute until the link
|
||||
// step, presumably because Windows doesn't use ELF binaries.
|
||||
#if (ABSL_HAVE_ATTRIBUTE(weak) || \
|
||||
(defined(__GNUC__) && !defined(__clang__))) && \
|
||||
!(defined(__llvm__) && defined(_WIN32)) && !defined(__MINGW32__)
|
||||
(!defined(_WIN32) || (defined(__clang__) && __clang_major__ >= 9)) && \
|
||||
!defined(__MINGW32__)
|
||||
#undef ABSL_ATTRIBUTE_WEAK
|
||||
#define ABSL_ATTRIBUTE_WEAK __attribute__((weak))
|
||||
#define ABSL_HAVE_ATTRIBUTE_WEAK 1
|
||||
@ -212,6 +213,9 @@
|
||||
// https://gcc.gnu.org/gcc-4.8/changes.html
|
||||
#if ABSL_HAVE_ATTRIBUTE(no_sanitize_address)
|
||||
#define ABSL_ATTRIBUTE_NO_SANITIZE_ADDRESS __attribute__((no_sanitize_address))
|
||||
#elif defined(_MSC_VER) && _MSC_VER >= 1928
|
||||
// https://docs.microsoft.com/en-us/cpp/cpp/no-sanitize-address
|
||||
#define ABSL_ATTRIBUTE_NO_SANITIZE_ADDRESS __declspec(no_sanitize_address)
|
||||
#else
|
||||
#define ABSL_ATTRIBUTE_NO_SANITIZE_ADDRESS
|
||||
#endif
|
||||
@ -281,10 +285,7 @@
|
||||
// ABSL_ATTRIBUTE_RETURNS_NONNULL
|
||||
//
|
||||
// Tells the compiler that a particular function never returns a null pointer.
|
||||
#if ABSL_HAVE_ATTRIBUTE(returns_nonnull) || \
|
||||
(defined(__GNUC__) && \
|
||||
(__GNUC__ > 5 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 9)) && \
|
||||
!defined(__clang__))
|
||||
#if ABSL_HAVE_ATTRIBUTE(returns_nonnull)
|
||||
#define ABSL_ATTRIBUTE_RETURNS_NONNULL __attribute__((returns_nonnull))
|
||||
#else
|
||||
#define ABSL_ATTRIBUTE_RETURNS_NONNULL
|
||||
@ -314,15 +315,22 @@
|
||||
__attribute__((section(#name))) __attribute__((noinline))
|
||||
#endif
|
||||
|
||||
|
||||
// ABSL_ATTRIBUTE_SECTION_VARIABLE
|
||||
//
|
||||
// Tells the compiler/linker to put a given variable into a section and define
|
||||
// `__start_ ## name` and `__stop_ ## name` symbols to bracket the section.
|
||||
// This functionality is supported by GNU linker.
|
||||
#ifndef ABSL_ATTRIBUTE_SECTION_VARIABLE
|
||||
#ifdef _AIX
|
||||
// __attribute__((section(#name))) on AIX is achived by using the `.csect` psudo
|
||||
// op which includes an additional integer as part of its syntax indcating
|
||||
// alignment. If data fall under different alignments then you might get a
|
||||
// compilation error indicating a `Section type conflict`.
|
||||
#define ABSL_ATTRIBUTE_SECTION_VARIABLE(name)
|
||||
#else
|
||||
#define ABSL_ATTRIBUTE_SECTION_VARIABLE(name) __attribute__((section(#name)))
|
||||
#endif
|
||||
#endif
|
||||
|
||||
// ABSL_DECLARE_ATTRIBUTE_SECTION_VARS
|
||||
//
|
||||
@ -395,6 +403,9 @@
|
||||
//
|
||||
// Tells the compiler to warn about unused results.
|
||||
//
|
||||
// For code or headers that are assured to only build with C++17 and up, prefer
|
||||
// just using the standard `[[nodiscard]]` directly over this macro.
|
||||
//
|
||||
// When annotating a function, it must appear as the first part of the
|
||||
// declaration or definition. The compiler will warn if the return value from
|
||||
// such a function is unused:
|
||||
@ -421,9 +432,10 @@
|
||||
// https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66425
|
||||
//
|
||||
// Note: past advice was to place the macro after the argument list.
|
||||
#if ABSL_HAVE_ATTRIBUTE(nodiscard)
|
||||
#define ABSL_MUST_USE_RESULT [[nodiscard]]
|
||||
#elif defined(__clang__) && ABSL_HAVE_ATTRIBUTE(warn_unused_result)
|
||||
//
|
||||
// TODO(b/176172494): Use ABSL_HAVE_CPP_ATTRIBUTE(nodiscard) when all code is
|
||||
// compliant with the stricter [[nodiscard]].
|
||||
#if defined(__clang__) && ABSL_HAVE_ATTRIBUTE(warn_unused_result)
|
||||
#define ABSL_MUST_USE_RESULT __attribute__((warn_unused_result))
|
||||
#else
|
||||
#define ABSL_MUST_USE_RESULT
|
||||
@ -524,6 +536,13 @@
|
||||
// ABSL_ATTRIBUTE_UNUSED
|
||||
//
|
||||
// Prevents the compiler from complaining about variables that appear unused.
|
||||
//
|
||||
// For code or headers that are assured to only build with C++17 and up, prefer
|
||||
// just using the standard '[[maybe_unused]]' directly over this macro.
|
||||
//
|
||||
// Due to differences in positioning requirements between the old, compiler
|
||||
// specific __attribute__ syntax and the now standard [[maybe_unused]], this
|
||||
// macro does not attempt to take advantage of '[[maybe_unused]]'.
|
||||
#if ABSL_HAVE_ATTRIBUTE(unused) || (defined(__GNUC__) && !defined(__clang__))
|
||||
#undef ABSL_ATTRIBUTE_UNUSED
|
||||
#define ABSL_ATTRIBUTE_UNUSED __attribute__((__unused__))
|
||||
@ -544,13 +563,19 @@
|
||||
// ABSL_ATTRIBUTE_PACKED
|
||||
//
|
||||
// Instructs the compiler not to use natural alignment for a tagged data
|
||||
// structure, but instead to reduce its alignment to 1. This attribute can
|
||||
// either be applied to members of a structure or to a structure in its
|
||||
// entirety. Applying this attribute (judiciously) to a structure in its
|
||||
// entirety to optimize the memory footprint of very commonly-used structs is
|
||||
// fine. Do not apply this attribute to a structure in its entirety if the
|
||||
// purpose is to control the offsets of the members in the structure. Instead,
|
||||
// apply this attribute only to structure members that need it.
|
||||
// structure, but instead to reduce its alignment to 1.
|
||||
//
|
||||
// Therefore, DO NOT APPLY THIS ATTRIBUTE TO STRUCTS CONTAINING ATOMICS. Doing
|
||||
// so can cause atomic variables to be mis-aligned and silently violate
|
||||
// atomicity on x86.
|
||||
//
|
||||
// This attribute can either be applied to members of a structure or to a
|
||||
// structure in its entirety. Applying this attribute (judiciously) to a
|
||||
// structure in its entirety to optimize the memory footprint of very
|
||||
// commonly-used structs is fine. Do not apply this attribute to a structure in
|
||||
// its entirety if the purpose is to control the offsets of the members in the
|
||||
// structure. Instead, apply this attribute only to structure members that need
|
||||
// it.
|
||||
//
|
||||
// When applying ABSL_ATTRIBUTE_PACKED only to specific structure members the
|
||||
// natural alignment of structure members not annotated is preserved. Aligned
|
||||
@ -595,31 +620,24 @@
|
||||
// case 42:
|
||||
// ...
|
||||
//
|
||||
// Notes: when compiled with clang in C++11 mode, the ABSL_FALLTHROUGH_INTENDED
|
||||
// macro is expanded to the [[clang::fallthrough]] attribute, which is analysed
|
||||
// when performing switch labels fall-through diagnostic
|
||||
// (`-Wimplicit-fallthrough`). See clang documentation on language extensions
|
||||
// for details:
|
||||
// Notes: When supported, GCC and Clang can issue a warning on switch labels
|
||||
// with unannotated fallthrough using the warning `-Wimplicit-fallthrough`. See
|
||||
// clang documentation on language extensions for details:
|
||||
// https://clang.llvm.org/docs/AttributeReference.html#fallthrough-clang-fallthrough
|
||||
//
|
||||
// When used with unsupported compilers, the ABSL_FALLTHROUGH_INTENDED macro
|
||||
// has no effect on diagnostics. In any case this macro has no effect on runtime
|
||||
// When used with unsupported compilers, the ABSL_FALLTHROUGH_INTENDED macro has
|
||||
// no effect on diagnostics. In any case this macro has no effect on runtime
|
||||
// behavior and performance of code.
|
||||
|
||||
#ifdef ABSL_FALLTHROUGH_INTENDED
|
||||
#error "ABSL_FALLTHROUGH_INTENDED should not be defined."
|
||||
#endif
|
||||
|
||||
// TODO(zhangxy): Use c++17 standard [[fallthrough]] macro, when supported.
|
||||
#if defined(__clang__) && defined(__has_warning)
|
||||
#if __has_feature(cxx_attributes) && __has_warning("-Wimplicit-fallthrough")
|
||||
#elif ABSL_HAVE_CPP_ATTRIBUTE(fallthrough)
|
||||
#define ABSL_FALLTHROUGH_INTENDED [[fallthrough]]
|
||||
#elif ABSL_HAVE_CPP_ATTRIBUTE(clang::fallthrough)
|
||||
#define ABSL_FALLTHROUGH_INTENDED [[clang::fallthrough]]
|
||||
#endif
|
||||
#elif defined(__GNUC__) && __GNUC__ >= 7
|
||||
#elif ABSL_HAVE_CPP_ATTRIBUTE(gnu::fallthrough)
|
||||
#define ABSL_FALLTHROUGH_INTENDED [[gnu::fallthrough]]
|
||||
#endif
|
||||
|
||||
#ifndef ABSL_FALLTHROUGH_INTENDED
|
||||
#else
|
||||
#define ABSL_FALLTHROUGH_INTENDED \
|
||||
do { \
|
||||
} while (0)
|
||||
@ -631,6 +649,9 @@
|
||||
// declarations. The macro argument is used as a custom diagnostic message (e.g.
|
||||
// suggestion of a better alternative).
|
||||
//
|
||||
// For code or headers that are assured to only build with C++14 and up, prefer
|
||||
// just using the standard `[[deprecated("message")]]` directly over this macro.
|
||||
//
|
||||
// Examples:
|
||||
//
|
||||
// class ABSL_DEPRECATED("Use Bar instead") Foo {...};
|
||||
@ -641,14 +662,17 @@
|
||||
// ABSL_DEPRECATED("Use DoThat() instead")
|
||||
// void DoThis();
|
||||
//
|
||||
// enum FooEnum {
|
||||
// kBar ABSL_DEPRECATED("Use kBaz instead"),
|
||||
// };
|
||||
//
|
||||
// Every usage of a deprecated entity will trigger a warning when compiled with
|
||||
// clang's `-Wdeprecated-declarations` option. This option is turned off by
|
||||
// default, but the warnings will be reported by clang-tidy.
|
||||
#if defined(__clang__) && defined(__cplusplus) && __cplusplus >= 201103L
|
||||
// GCC/Clang's `-Wdeprecated-declarations` option. Google's production toolchain
|
||||
// turns this warning off by default, instead relying on clang-tidy to report
|
||||
// new uses of deprecated code.
|
||||
#if ABSL_HAVE_ATTRIBUTE(deprecated)
|
||||
#define ABSL_DEPRECATED(message) __attribute__((deprecated(message)))
|
||||
#endif
|
||||
|
||||
#ifndef ABSL_DEPRECATED
|
||||
#else
|
||||
#define ABSL_DEPRECATED(message)
|
||||
#endif
|
||||
|
||||
@ -658,9 +682,18 @@
|
||||
// not compile (on supported platforms) unless the variable has a constant
|
||||
// initializer. This is useful for variables with static and thread storage
|
||||
// duration, because it guarantees that they will not suffer from the so-called
|
||||
// "static init order fiasco". Prefer to put this attribute on the most visible
|
||||
// declaration of the variable, if there's more than one, because code that
|
||||
// accesses the variable can then use the attribute for optimization.
|
||||
// "static init order fiasco".
|
||||
//
|
||||
// This attribute must be placed on the initializing declaration of the
|
||||
// variable. Some compilers will give a -Wmissing-constinit warning when this
|
||||
// attribute is placed on some other declaration but missing from the
|
||||
// initializing declaration.
|
||||
//
|
||||
// In some cases (notably with thread_local variables), `ABSL_CONST_INIT` can
|
||||
// also be used in a non-initializing declaration to tell the compiler that a
|
||||
// variable is already initialized, reducing overhead that would otherwise be
|
||||
// incurred by a hidden guard variable. Thus annotating all declarations with
|
||||
// this attribute is recommended to potentially enhance optimization.
|
||||
//
|
||||
// Example:
|
||||
//
|
||||
@ -669,14 +702,19 @@
|
||||
// ABSL_CONST_INIT static MyType my_var;
|
||||
// };
|
||||
//
|
||||
// MyType MyClass::my_var = MakeMyType(...);
|
||||
// ABSL_CONST_INIT MyType MyClass::my_var = MakeMyType(...);
|
||||
//
|
||||
// For code or headers that are assured to only build with C++20 and up, prefer
|
||||
// just using the standard `constinit` keyword directly over this macro.
|
||||
//
|
||||
// Note that this attribute is redundant if the variable is declared constexpr.
|
||||
#if ABSL_HAVE_CPP_ATTRIBUTE(clang::require_constant_initialization)
|
||||
#if defined(__cpp_constinit) && __cpp_constinit >= 201907L
|
||||
#define ABSL_CONST_INIT constinit
|
||||
#elif ABSL_HAVE_CPP_ATTRIBUTE(clang::require_constant_initialization)
|
||||
#define ABSL_CONST_INIT [[clang::require_constant_initialization]]
|
||||
#else
|
||||
#define ABSL_CONST_INIT
|
||||
#endif // ABSL_HAVE_CPP_ATTRIBUTE(clang::require_constant_initialization)
|
||||
#endif
|
||||
|
||||
// ABSL_ATTRIBUTE_PURE_FUNCTION
|
||||
//
|
||||
@ -699,4 +737,26 @@
|
||||
#define ABSL_ATTRIBUTE_PURE_FUNCTION
|
||||
#endif
|
||||
|
||||
// ABSL_ATTRIBUTE_LIFETIME_BOUND indicates that a resource owned by a function
|
||||
// parameter or implicit object parameter is retained by the return value of the
|
||||
// annotated function (or, for a parameter of a constructor, in the value of the
|
||||
// constructed object). This attribute causes warnings to be produced if a
|
||||
// temporary object does not live long enough.
|
||||
//
|
||||
// When applied to a reference parameter, the referenced object is assumed to be
|
||||
// retained by the return value of the function. When applied to a non-reference
|
||||
// parameter (for example, a pointer or a class type), all temporaries
|
||||
// referenced by the parameter are assumed to be retained by the return value of
|
||||
// the function.
|
||||
//
|
||||
// See also the upstream documentation:
|
||||
// https://clang.llvm.org/docs/AttributeReference.html#lifetimebound
|
||||
#if ABSL_HAVE_CPP_ATTRIBUTE(clang::lifetimebound)
|
||||
#define ABSL_ATTRIBUTE_LIFETIME_BOUND [[clang::lifetimebound]]
|
||||
#elif ABSL_HAVE_ATTRIBUTE(lifetimebound)
|
||||
#define ABSL_ATTRIBUTE_LIFETIME_BOUND __attribute__((lifetimebound))
|
||||
#else
|
||||
#define ABSL_ATTRIBUTE_LIFETIME_BOUND
|
||||
#endif
|
||||
|
||||
#endif // ABSL_BASE_ATTRIBUTES_H_
|
@ -29,6 +29,10 @@
|
||||
#include <type_traits>
|
||||
#include <utility>
|
||||
|
||||
#if defined(__cpp_lib_bit_cast) && __cpp_lib_bit_cast >= 201806L
|
||||
#include <bit> // For std::bit_cast.
|
||||
#endif // defined(__cpp_lib_bit_cast) && __cpp_lib_bit_cast >= 201806L
|
||||
|
||||
#include "absl/base/internal/identity.h"
|
||||
#include "absl/base/macros.h"
|
||||
#include "absl/meta/type_traits.h"
|
||||
@ -36,19 +40,6 @@
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
|
||||
namespace internal_casts {
|
||||
|
||||
template <class Dest, class Source>
|
||||
struct is_bitcastable
|
||||
: std::integral_constant<
|
||||
bool,
|
||||
sizeof(Dest) == sizeof(Source) &&
|
||||
type_traits_internal::is_trivially_copyable<Source>::value &&
|
||||
type_traits_internal::is_trivially_copyable<Dest>::value &&
|
||||
std::is_default_constructible<Dest>::value> {};
|
||||
|
||||
} // namespace internal_casts
|
||||
|
||||
// implicit_cast()
|
||||
//
|
||||
// Performs an implicit conversion between types following the language
|
||||
@ -105,81 +96,83 @@ constexpr To implicit_cast(typename absl::internal::identity_t<To> to) {
|
||||
|
||||
// bit_cast()
|
||||
//
|
||||
// Performs a bitwise cast on a type without changing the underlying bit
|
||||
// representation of that type's value. The two types must be of the same size
|
||||
// and both types must be trivially copyable. As with most casts, use with
|
||||
// caution. A `bit_cast()` might be needed when you need to temporarily treat a
|
||||
// type as some other type, such as in the following cases:
|
||||
// Creates a value of the new type `Dest` whose representation is the same as
|
||||
// that of the argument, which is of (deduced) type `Source` (a "bitwise cast";
|
||||
// every bit in the value representation of the result is equal to the
|
||||
// corresponding bit in the object representation of the source). Source and
|
||||
// destination types must be of the same size, and both types must be trivially
|
||||
// copyable.
|
||||
//
|
||||
// * Serialization (casting temporarily to `char *` for those purposes is
|
||||
// always allowed by the C++ standard)
|
||||
// * Managing the individual bits of a type within mathematical operations
|
||||
// that are not normally accessible through that type
|
||||
// * Casting non-pointer types to pointer types (casting the other way is
|
||||
// allowed by `reinterpret_cast()` but round-trips cannot occur the other
|
||||
// way).
|
||||
//
|
||||
// Example:
|
||||
// As with most casts, use with caution. A `bit_cast()` might be needed when you
|
||||
// need to treat a value as the value of some other type, for example, to access
|
||||
// the individual bits of an object which are not normally accessible through
|
||||
// the object's type, such as for working with the binary representation of a
|
||||
// floating point value:
|
||||
//
|
||||
// float f = 3.14159265358979;
|
||||
// int i = bit_cast<int32_t>(f);
|
||||
// int i = bit_cast<int>(f);
|
||||
// // i = 0x40490fdb
|
||||
//
|
||||
// Casting non-pointer types to pointer types and then dereferencing them
|
||||
// traditionally produces undefined behavior.
|
||||
// Reinterpreting and accessing a value directly as a different type (as shown
|
||||
// below) usually results in undefined behavior.
|
||||
//
|
||||
// Example:
|
||||
//
|
||||
// // WRONG
|
||||
// float f = 3.14159265358979; // WRONG
|
||||
// int i = * reinterpret_cast<int*>(&f); // WRONG
|
||||
// float f = 3.14159265358979;
|
||||
// int i = reinterpret_cast<int&>(f); // Wrong
|
||||
// int j = *reinterpret_cast<int*>(&f); // Equally wrong
|
||||
// int k = *bit_cast<int*>(&f); // Equally wrong
|
||||
//
|
||||
// The address-casting method produces undefined behavior according to the ISO
|
||||
// C++ specification section [basic.lval]. Roughly, this section says: if an
|
||||
// object in memory has one type, and a program accesses it with a different
|
||||
// type, the result is undefined behavior for most values of "different type".
|
||||
// Reinterpret-casting results in undefined behavior according to the ISO C++
|
||||
// specification, section [basic.lval]. Roughly, this section says: if an object
|
||||
// in memory has one type, and a program accesses it with a different type, the
|
||||
// result is undefined behavior for most "different type".
|
||||
//
|
||||
// Using bit_cast on a pointer and then dereferencing it is no better than using
|
||||
// reinterpret_cast. You should only use bit_cast on the value itself.
|
||||
//
|
||||
// Such casting results in type punning: holding an object in memory of one type
|
||||
// and reading its bits back using a different type. A `bit_cast()` avoids this
|
||||
// issue by implementing its casts using `memcpy()`, which avoids introducing
|
||||
// this undefined behavior.
|
||||
// issue by copying the object representation to a new value, which avoids
|
||||
// introducing this undefined behavior (since the original value is never
|
||||
// accessed in the wrong way).
|
||||
//
|
||||
// NOTE: The requirements here are more strict than the bit_cast of standard
|
||||
// proposal p0476 due to the need for workarounds and lack of intrinsics.
|
||||
// Specifically, this implementation also requires `Dest` to be
|
||||
// default-constructible.
|
||||
template <
|
||||
typename Dest, typename Source,
|
||||
typename std::enable_if<internal_casts::is_bitcastable<Dest, Source>::value,
|
||||
// The requirements of `absl::bit_cast` are more strict than that of
|
||||
// `std::bit_cast` unless compiler support is available. Specifically, without
|
||||
// compiler support, this implementation also requires `Dest` to be
|
||||
// default-constructible. In C++20, `absl::bit_cast` is replaced by
|
||||
// `std::bit_cast`.
|
||||
#if defined(__cpp_lib_bit_cast) && __cpp_lib_bit_cast >= 201806L
|
||||
|
||||
using std::bit_cast;
|
||||
|
||||
#else // defined(__cpp_lib_bit_cast) && __cpp_lib_bit_cast >= 201806L
|
||||
|
||||
template <typename Dest, typename Source,
|
||||
typename std::enable_if<
|
||||
sizeof(Dest) == sizeof(Source) &&
|
||||
type_traits_internal::is_trivially_copyable<Source>::value &&
|
||||
type_traits_internal::is_trivially_copyable<Dest>::value
|
||||
#if !ABSL_HAVE_BUILTIN(__builtin_bit_cast)
|
||||
&& std::is_default_constructible<Dest>::value
|
||||
#endif // !ABSL_HAVE_BUILTIN(__builtin_bit_cast)
|
||||
,
|
||||
int>::type = 0>
|
||||
#if ABSL_HAVE_BUILTIN(__builtin_bit_cast)
|
||||
inline constexpr Dest bit_cast(const Source& source) {
|
||||
return __builtin_bit_cast(Dest, source);
|
||||
}
|
||||
#else // ABSL_HAVE_BUILTIN(__builtin_bit_cast)
|
||||
inline Dest bit_cast(const Source& source) {
|
||||
Dest dest;
|
||||
memcpy(static_cast<void*>(std::addressof(dest)),
|
||||
static_cast<const void*>(std::addressof(source)), sizeof(dest));
|
||||
return dest;
|
||||
}
|
||||
#endif // ABSL_HAVE_BUILTIN(__builtin_bit_cast)
|
||||
|
||||
// NOTE: This overload is only picked if the requirements of bit_cast are
|
||||
// not met. It is therefore UB, but is provided temporarily as previous
|
||||
// versions of this function template were unchecked. Do not use this in
|
||||
// new code.
|
||||
template <
|
||||
typename Dest, typename Source,
|
||||
typename std::enable_if<
|
||||
!internal_casts::is_bitcastable<Dest, Source>::value,
|
||||
int>::type = 0>
|
||||
ABSL_DEPRECATED(
|
||||
"absl::bit_cast type requirements were violated. Update the types "
|
||||
"being used such that they are the same size and are both "
|
||||
"TriviallyCopyable.")
|
||||
inline Dest bit_cast(const Source& source) {
|
||||
static_assert(sizeof(Dest) == sizeof(Source),
|
||||
"Source and destination types should have equal sizes.");
|
||||
|
||||
Dest dest;
|
||||
memcpy(&dest, &source, sizeof(dest));
|
||||
return dest;
|
||||
}
|
||||
#endif // defined(__cpp_lib_bit_cast) && __cpp_lib_bit_cast >= 201806L
|
||||
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
@ -56,6 +56,25 @@
|
||||
#include <cstddef>
|
||||
#endif // __cplusplus
|
||||
|
||||
// ABSL_INTERNAL_CPLUSPLUS_LANG
|
||||
//
|
||||
// MSVC does not set the value of __cplusplus correctly, but instead uses
|
||||
// _MSVC_LANG as a stand-in.
|
||||
// https://docs.microsoft.com/en-us/cpp/preprocessor/predefined-macros
|
||||
//
|
||||
// However, there are reports that MSVC even sets _MSVC_LANG incorrectly at
|
||||
// times, for example:
|
||||
// https://github.com/microsoft/vscode-cpptools/issues/1770
|
||||
// https://reviews.llvm.org/D70996
|
||||
//
|
||||
// For this reason, this symbol is considered INTERNAL and code outside of
|
||||
// Abseil must not use it.
|
||||
#if defined(_MSVC_LANG)
|
||||
#define ABSL_INTERNAL_CPLUSPLUS_LANG _MSVC_LANG
|
||||
#elif defined(__cplusplus)
|
||||
#define ABSL_INTERNAL_CPLUSPLUS_LANG __cplusplus
|
||||
#endif
|
||||
|
||||
#if defined(__APPLE__)
|
||||
// Included for TARGET_OS_IPHONE, __IPHONE_OS_VERSION_MIN_REQUIRED,
|
||||
// __IPHONE_8_0.
|
||||
@ -66,6 +85,35 @@
|
||||
#include "absl/base/options.h"
|
||||
#include "absl/base/policy_checks.h"
|
||||
|
||||
// Abseil long-term support (LTS) releases will define
|
||||
// `ABSL_LTS_RELEASE_VERSION` to the integer representing the date string of the
|
||||
// LTS release version, and will define `ABSL_LTS_RELEASE_PATCH_LEVEL` to the
|
||||
// integer representing the patch-level for that release.
|
||||
//
|
||||
// For example, for LTS release version "20300401.2", this would give us
|
||||
// ABSL_LTS_RELEASE_VERSION == 20300401 && ABSL_LTS_RELEASE_PATCH_LEVEL == 2
|
||||
//
|
||||
// These symbols will not be defined in non-LTS code.
|
||||
//
|
||||
// Abseil recommends that clients live-at-head. Therefore, if you are using
|
||||
// these symbols to assert a minimum version requirement, we recommend you do it
|
||||
// as
|
||||
//
|
||||
// #if defined(ABSL_LTS_RELEASE_VERSION) && ABSL_LTS_RELEASE_VERSION < 20300401
|
||||
// #error Project foo requires Abseil LTS version >= 20300401
|
||||
// #endif
|
||||
//
|
||||
// The `defined(ABSL_LTS_RELEASE_VERSION)` part of the check excludes
|
||||
// live-at-head clients from the minimum version assertion.
|
||||
//
|
||||
// See https://abseil.io/about/releases for more information on Abseil release
|
||||
// management.
|
||||
//
|
||||
// LTS releases can be obtained from
|
||||
// https://github.com/abseil/abseil-cpp/releases.
|
||||
#define ABSL_LTS_RELEASE_VERSION 20220623
|
||||
#define ABSL_LTS_RELEASE_PATCH_LEVEL 1
|
||||
|
||||
// Helper macro to convert a CPP variable to a string literal.
|
||||
#define ABSL_INTERNAL_DO_TOKEN_STR(x) #x
|
||||
#define ABSL_INTERNAL_TOKEN_STR(x) ABSL_INTERNAL_DO_TOKEN_STR(x)
|
||||
@ -154,24 +202,35 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
#define ABSL_HAVE_BUILTIN(x) 0
|
||||
#endif
|
||||
|
||||
#if defined(__is_identifier)
|
||||
#define ABSL_INTERNAL_HAS_KEYWORD(x) !(__is_identifier(x))
|
||||
#else
|
||||
#define ABSL_INTERNAL_HAS_KEYWORD(x) 0
|
||||
#endif
|
||||
|
||||
#ifdef __has_feature
|
||||
#define ABSL_HAVE_FEATURE(f) __has_feature(f)
|
||||
#else
|
||||
#define ABSL_HAVE_FEATURE(f) 0
|
||||
#endif
|
||||
|
||||
// Portable check for GCC minimum version:
|
||||
// https://gcc.gnu.org/onlinedocs/cpp/Common-Predefined-Macros.html
|
||||
#if defined(__GNUC__) && defined(__GNUC_MINOR__)
|
||||
#define ABSL_INTERNAL_HAVE_MIN_GNUC_VERSION(x, y) \
|
||||
(__GNUC__ > (x) || __GNUC__ == (x) && __GNUC_MINOR__ >= (y))
|
||||
#else
|
||||
#define ABSL_INTERNAL_HAVE_MIN_GNUC_VERSION(x, y) 0
|
||||
#endif
|
||||
|
||||
#if defined(__clang__) && defined(__clang_major__) && defined(__clang_minor__)
|
||||
#define ABSL_INTERNAL_HAVE_MIN_CLANG_VERSION(x, y) \
|
||||
(__clang_major__ > (x) || __clang_major__ == (x) && __clang_minor__ >= (y))
|
||||
#else
|
||||
#define ABSL_INTERNAL_HAVE_MIN_CLANG_VERSION(x, y) 0
|
||||
#endif
|
||||
|
||||
// ABSL_HAVE_TLS is defined to 1 when __thread should be supported.
|
||||
// We assume __thread is supported on Linux when compiled with Clang or compiled
|
||||
// against libstdc++ with _GLIBCXX_HAVE_TLS defined.
|
||||
// We assume __thread is supported on Linux or Asylo when compiled with Clang or
|
||||
// compiled against libstdc++ with _GLIBCXX_HAVE_TLS defined.
|
||||
#ifdef ABSL_HAVE_TLS
|
||||
#error ABSL_HAVE_TLS cannot be directly set
|
||||
#elif defined(__linux__) && (defined(__clang__) || defined(_GLIBCXX_HAVE_TLS))
|
||||
#elif (defined(__linux__) || defined(__ASYLO__)) && \
|
||||
(defined(__clang__) || defined(_GLIBCXX_HAVE_TLS))
|
||||
#define ABSL_HAVE_TLS 1
|
||||
#endif
|
||||
|
||||
@ -183,10 +242,9 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
// gcc >= 4.8.1 using libstdc++, and Visual Studio.
|
||||
#ifdef ABSL_HAVE_STD_IS_TRIVIALLY_DESTRUCTIBLE
|
||||
#error ABSL_HAVE_STD_IS_TRIVIALLY_DESTRUCTIBLE cannot be directly set
|
||||
#elif defined(_LIBCPP_VERSION) || \
|
||||
(!defined(__clang__) && defined(__GNUC__) && defined(__GLIBCXX__) && \
|
||||
(__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 8))) || \
|
||||
defined(_MSC_VER)
|
||||
#elif defined(_LIBCPP_VERSION) || defined(_MSC_VER) || \
|
||||
(!defined(__clang__) && defined(__GLIBCXX__) && \
|
||||
ABSL_INTERNAL_HAVE_MIN_GNUC_VERSION(4, 8))
|
||||
#define ABSL_HAVE_STD_IS_TRIVIALLY_DESTRUCTIBLE 1
|
||||
#endif
|
||||
|
||||
@ -199,34 +257,22 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
//
|
||||
// Checks whether `std::is_trivially_copy_assignable<T>` is supported.
|
||||
|
||||
// Notes: Clang with libc++ supports these features, as does gcc >= 5.1 with
|
||||
// either libc++ or libstdc++, and Visual Studio (but not NVCC).
|
||||
// Notes: Clang with libc++ supports these features, as does gcc >= 7.4 with
|
||||
// libstdc++, or gcc >= 8.2 with libc++, and Visual Studio (but not NVCC).
|
||||
#if defined(ABSL_HAVE_STD_IS_TRIVIALLY_CONSTRUCTIBLE)
|
||||
#error ABSL_HAVE_STD_IS_TRIVIALLY_CONSTRUCTIBLE cannot be directly set
|
||||
#elif defined(ABSL_HAVE_STD_IS_TRIVIALLY_ASSIGNABLE)
|
||||
#error ABSL_HAVE_STD_IS_TRIVIALLY_ASSIGNABLE cannot directly set
|
||||
#elif (defined(__clang__) && defined(_LIBCPP_VERSION)) || \
|
||||
(!defined(__clang__) && defined(__GNUC__) && \
|
||||
(__GNUC__ > 7 || (__GNUC__ == 7 && __GNUC_MINOR__ >= 4)) && \
|
||||
(defined(_LIBCPP_VERSION) || defined(__GLIBCXX__))) || \
|
||||
(!defined(__clang__) && \
|
||||
((ABSL_INTERNAL_HAVE_MIN_GNUC_VERSION(7, 4) && defined(__GLIBCXX__)) || \
|
||||
(ABSL_INTERNAL_HAVE_MIN_GNUC_VERSION(8, 2) && \
|
||||
defined(_LIBCPP_VERSION)))) || \
|
||||
(defined(_MSC_VER) && !defined(__NVCC__))
|
||||
#define ABSL_HAVE_STD_IS_TRIVIALLY_CONSTRUCTIBLE 1
|
||||
#define ABSL_HAVE_STD_IS_TRIVIALLY_ASSIGNABLE 1
|
||||
#endif
|
||||
|
||||
// ABSL_HAVE_SOURCE_LOCATION_CURRENT
|
||||
//
|
||||
// Indicates whether `absl::SourceLocation::current()` will return useful
|
||||
// information in some contexts.
|
||||
#ifndef ABSL_HAVE_SOURCE_LOCATION_CURRENT
|
||||
#if ABSL_INTERNAL_HAS_KEYWORD(__builtin_LINE) && \
|
||||
ABSL_INTERNAL_HAS_KEYWORD(__builtin_FILE)
|
||||
#define ABSL_HAVE_SOURCE_LOCATION_CURRENT 1
|
||||
#elif defined(__GNUC__) && __GNUC__ >= 5
|
||||
#define ABSL_HAVE_SOURCE_LOCATION_CURRENT 1
|
||||
#endif
|
||||
#endif
|
||||
|
||||
// ABSL_HAVE_THREAD_LOCAL
|
||||
//
|
||||
// Checks whether C++11's `thread_local` storage duration specifier is
|
||||
@ -319,25 +365,21 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
// For further details, consult the compiler's documentation.
|
||||
#ifdef ABSL_HAVE_EXCEPTIONS
|
||||
#error ABSL_HAVE_EXCEPTIONS cannot be directly set.
|
||||
|
||||
#elif defined(__clang__)
|
||||
|
||||
#if __clang_major__ > 3 || (__clang_major__ == 3 && __clang_minor__ >= 6)
|
||||
#elif ABSL_INTERNAL_HAVE_MIN_CLANG_VERSION(3, 6)
|
||||
// Clang >= 3.6
|
||||
#if ABSL_HAVE_FEATURE(cxx_exceptions)
|
||||
#define ABSL_HAVE_EXCEPTIONS 1
|
||||
#endif // ABSL_HAVE_FEATURE(cxx_exceptions)
|
||||
#else
|
||||
#elif defined(__clang__)
|
||||
// Clang < 3.6
|
||||
// http://releases.llvm.org/3.6.0/tools/clang/docs/ReleaseNotes.html#the-exceptions-macro
|
||||
#if defined(__EXCEPTIONS) && ABSL_HAVE_FEATURE(cxx_exceptions)
|
||||
#define ABSL_HAVE_EXCEPTIONS 1
|
||||
#endif // defined(__EXCEPTIONS) && ABSL_HAVE_FEATURE(cxx_exceptions)
|
||||
#endif // __clang_major__ > 3 || (__clang_major__ == 3 && __clang_minor__ >= 6)
|
||||
|
||||
// Handle remaining special cases and default to exceptions being supported.
|
||||
#elif !(defined(__GNUC__) && (__GNUC__ < 5) && !defined(__EXCEPTIONS)) && \
|
||||
!(defined(__GNUC__) && (__GNUC__ >= 5) && !defined(__cpp_exceptions)) && \
|
||||
!(ABSL_INTERNAL_HAVE_MIN_GNUC_VERSION(5, 0) && \
|
||||
!defined(__cpp_exceptions)) && \
|
||||
!(defined(_MSC_VER) && !defined(_CPPUNWIND))
|
||||
#define ABSL_HAVE_EXCEPTIONS 1
|
||||
#endif
|
||||
@ -370,9 +412,11 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
#ifdef ABSL_HAVE_MMAP
|
||||
#error ABSL_HAVE_MMAP cannot be directly set
|
||||
#elif defined(__linux__) || defined(__APPLE__) || defined(__FreeBSD__) || \
|
||||
defined(__ros__) || defined(__native_client__) || defined(__asmjs__) || \
|
||||
defined(__wasm__) || defined(__Fuchsia__) || defined(__sun) || \
|
||||
defined(__ASYLO__) || defined(__myriad2__)
|
||||
defined(_AIX) || defined(__ros__) || defined(__native_client__) || \
|
||||
defined(__asmjs__) || defined(__wasm__) || defined(__Fuchsia__) || \
|
||||
defined(__sun) || defined(__ASYLO__) || defined(__myriad2__) || \
|
||||
defined(__HAIKU__) || defined(__OpenBSD__) || defined(__NetBSD__) || \
|
||||
defined(__QNX__)
|
||||
#define ABSL_HAVE_MMAP 1
|
||||
#endif
|
||||
|
||||
@ -383,7 +427,8 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
#ifdef ABSL_HAVE_PTHREAD_GETSCHEDPARAM
|
||||
#error ABSL_HAVE_PTHREAD_GETSCHEDPARAM cannot be directly set
|
||||
#elif defined(__linux__) || defined(__APPLE__) || defined(__FreeBSD__) || \
|
||||
defined(__ros__)
|
||||
defined(_AIX) || defined(__ros__) || defined(__OpenBSD__) || \
|
||||
defined(__NetBSD__)
|
||||
#define ABSL_HAVE_PTHREAD_GETSCHEDPARAM 1
|
||||
#endif
|
||||
|
||||
@ -478,14 +523,33 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
#error "absl endian detection needs to be set up for your compiler"
|
||||
#endif
|
||||
|
||||
// macOS 10.13 and iOS 10.11 don't let you use <any>, <optional>, or <variant>
|
||||
// even though the headers exist and are publicly noted to work. See
|
||||
// https://github.com/abseil/abseil-cpp/issues/207 and
|
||||
// macOS < 10.13 and iOS < 11 don't let you use <any>, <optional>, or <variant>
|
||||
// even though the headers exist and are publicly noted to work, because the
|
||||
// libc++ shared library shipped on the system doesn't have the requisite
|
||||
// exported symbols. See https://github.com/abseil/abseil-cpp/issues/207 and
|
||||
// https://developer.apple.com/documentation/xcode_release_notes/xcode_10_release_notes
|
||||
//
|
||||
// libc++ spells out the availability requirements in the file
|
||||
// llvm-project/libcxx/include/__config via the #define
|
||||
// _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS.
|
||||
//
|
||||
// Unfortunately, Apple initially mis-stated the requirements as macOS < 10.14
|
||||
// and iOS < 12 in the libc++ headers. This was corrected by
|
||||
// https://github.com/llvm/llvm-project/commit/7fb40e1569dd66292b647f4501b85517e9247953
|
||||
// which subsequently made it into the XCode 12.5 release. We need to match the
|
||||
// old (incorrect) conditions when built with old XCode, but can use the
|
||||
// corrected earlier versions with new XCode.
|
||||
#if defined(__APPLE__) && defined(_LIBCPP_VERSION) && \
|
||||
((_LIBCPP_VERSION >= 11000 && /* XCode 12.5 or later: */ \
|
||||
((defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) && \
|
||||
__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ < 101300) || \
|
||||
(defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) && \
|
||||
__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ < 110000) || \
|
||||
(defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) && \
|
||||
__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ < 40000) || \
|
||||
(defined(__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__) && \
|
||||
__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ < 110000))) || \
|
||||
(_LIBCPP_VERSION < 11000 && /* Pre-XCode 12.5: */ \
|
||||
((defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) && \
|
||||
__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ < 101400) || \
|
||||
(defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) && \
|
||||
@ -493,7 +557,7 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
(defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) && \
|
||||
__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ < 50000) || \
|
||||
(defined(__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__) && \
|
||||
__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ < 120000))
|
||||
__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ < 120000))))
|
||||
#define ABSL_INTERNAL_APPLE_CXX17_TYPES_UNAVAILABLE 1
|
||||
#else
|
||||
#define ABSL_INTERNAL_APPLE_CXX17_TYPES_UNAVAILABLE 0
|
||||
@ -663,8 +727,6 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#undef ABSL_INTERNAL_HAS_KEYWORD
|
||||
|
||||
// ABSL_DLL
|
||||
//
|
||||
// When building Abseil as a DLL, this macro expands to `__declspec(dllexport)`
|
||||
@ -690,12 +752,6 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
// a compiler instrumentation module and a run-time library.
|
||||
#ifdef ABSL_HAVE_MEMORY_SANITIZER
|
||||
#error "ABSL_HAVE_MEMORY_SANITIZER cannot be directly set."
|
||||
#elif defined(MEMORY_SANITIZER)
|
||||
// The MEMORY_SANITIZER macro is deprecated but we will continue to honor it
|
||||
// for now.
|
||||
#define ABSL_HAVE_MEMORY_SANITIZER 1
|
||||
#elif defined(__SANITIZE_MEMORY__)
|
||||
#define ABSL_HAVE_MEMORY_SANITIZER 1
|
||||
#elif !defined(__native_client__) && ABSL_HAVE_FEATURE(memory_sanitizer)
|
||||
#define ABSL_HAVE_MEMORY_SANITIZER 1
|
||||
#endif
|
||||
@ -705,10 +761,6 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
// ThreadSanitizer (TSan) is a fast data race detector.
|
||||
#ifdef ABSL_HAVE_THREAD_SANITIZER
|
||||
#error "ABSL_HAVE_THREAD_SANITIZER cannot be directly set."
|
||||
#elif defined(THREAD_SANITIZER)
|
||||
// The THREAD_SANITIZER macro is deprecated but we will continue to honor it
|
||||
// for now.
|
||||
#define ABSL_HAVE_THREAD_SANITIZER 1
|
||||
#elif defined(__SANITIZE_THREAD__)
|
||||
#define ABSL_HAVE_THREAD_SANITIZER 1
|
||||
#elif ABSL_HAVE_FEATURE(thread_sanitizer)
|
||||
@ -720,16 +772,51 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
// AddressSanitizer (ASan) is a fast memory error detector.
|
||||
#ifdef ABSL_HAVE_ADDRESS_SANITIZER
|
||||
#error "ABSL_HAVE_ADDRESS_SANITIZER cannot be directly set."
|
||||
#elif defined(ADDRESS_SANITIZER)
|
||||
// The ADDRESS_SANITIZER macro is deprecated but we will continue to honor it
|
||||
// for now.
|
||||
#define ABSL_HAVE_ADDRESS_SANITIZER 1
|
||||
#elif defined(__SANITIZE_ADDRESS__)
|
||||
#define ABSL_HAVE_ADDRESS_SANITIZER 1
|
||||
#elif ABSL_HAVE_FEATURE(address_sanitizer)
|
||||
#define ABSL_HAVE_ADDRESS_SANITIZER 1
|
||||
#endif
|
||||
|
||||
// ABSL_HAVE_HWADDRESS_SANITIZER
|
||||
//
|
||||
// Hardware-Assisted AddressSanitizer (or HWASAN) is even faster than asan
|
||||
// memory error detector which can use CPU features like ARM TBI, Intel LAM or
|
||||
// AMD UAI.
|
||||
#ifdef ABSL_HAVE_HWADDRESS_SANITIZER
|
||||
#error "ABSL_HAVE_HWADDRESS_SANITIZER cannot be directly set."
|
||||
#elif defined(__SANITIZE_HWADDRESS__)
|
||||
#define ABSL_HAVE_HWADDRESS_SANITIZER 1
|
||||
#elif ABSL_HAVE_FEATURE(hwaddress_sanitizer)
|
||||
#define ABSL_HAVE_HWADDRESS_SANITIZER 1
|
||||
#endif
|
||||
|
||||
// ABSL_HAVE_LEAK_SANITIZER
|
||||
//
|
||||
// LeakSanitizer (or lsan) is a detector of memory leaks.
|
||||
// https://clang.llvm.org/docs/LeakSanitizer.html
|
||||
// https://github.com/google/sanitizers/wiki/AddressSanitizerLeakSanitizer
|
||||
//
|
||||
// The macro ABSL_HAVE_LEAK_SANITIZER can be used to detect at compile-time
|
||||
// whether the LeakSanitizer is potentially available. However, just because the
|
||||
// LeakSanitizer is available does not mean it is active. Use the
|
||||
// always-available run-time interface in //absl/debugging/leak_check.h for
|
||||
// interacting with LeakSanitizer.
|
||||
#ifdef ABSL_HAVE_LEAK_SANITIZER
|
||||
#error "ABSL_HAVE_LEAK_SANITIZER cannot be directly set."
|
||||
#elif defined(LEAK_SANITIZER)
|
||||
// GCC provides no method for detecting the presense of the standalone
|
||||
// LeakSanitizer (-fsanitize=leak), so GCC users of -fsanitize=leak should also
|
||||
// use -DLEAK_SANITIZER.
|
||||
#define ABSL_HAVE_LEAK_SANITIZER 1
|
||||
// Clang standalone LeakSanitizer (-fsanitize=leak)
|
||||
#elif ABSL_HAVE_FEATURE(leak_sanitizer)
|
||||
#define ABSL_HAVE_LEAK_SANITIZER 1
|
||||
#elif defined(ABSL_HAVE_ADDRESS_SANITIZER)
|
||||
// GCC or Clang using the LeakSanitizer integrated into AddressSanitizer.
|
||||
#define ABSL_HAVE_LEAK_SANITIZER 1
|
||||
#endif
|
||||
|
||||
// ABSL_HAVE_CLASS_TEMPLATE_ARGUMENT_DEDUCTION
|
||||
//
|
||||
// Class template argument deduction is a language feature added in C++17.
|
||||
@ -739,4 +826,88 @@ static_assert(ABSL_INTERNAL_INLINE_NAMESPACE_STR[0] != 'h' ||
|
||||
#define ABSL_HAVE_CLASS_TEMPLATE_ARGUMENT_DEDUCTION 1
|
||||
#endif
|
||||
|
||||
// ABSL_INTERNAL_NEED_REDUNDANT_CONSTEXPR_DECL
|
||||
//
|
||||
// Prior to C++17, static constexpr variables defined in classes required a
|
||||
// separate definition outside of the class body, for example:
|
||||
//
|
||||
// class Foo {
|
||||
// static constexpr int kBar = 0;
|
||||
// };
|
||||
// constexpr int Foo::kBar;
|
||||
//
|
||||
// In C++17, these variables defined in classes are considered inline variables,
|
||||
// and the extra declaration is redundant. Since some compilers warn on the
|
||||
// extra declarations, ABSL_INTERNAL_NEED_REDUNDANT_CONSTEXPR_DECL can be used
|
||||
// conditionally ignore them:
|
||||
//
|
||||
// #ifdef ABSL_INTERNAL_NEED_REDUNDANT_CONSTEXPR_DECL
|
||||
// constexpr int Foo::kBar;
|
||||
// #endif
|
||||
#if defined(ABSL_INTERNAL_CPLUSPLUS_LANG) && \
|
||||
ABSL_INTERNAL_CPLUSPLUS_LANG < 201703L
|
||||
#define ABSL_INTERNAL_NEED_REDUNDANT_CONSTEXPR_DECL 1
|
||||
#endif
|
||||
|
||||
// `ABSL_INTERNAL_HAS_RTTI` determines whether abseil is being compiled with
|
||||
// RTTI support.
|
||||
#ifdef ABSL_INTERNAL_HAS_RTTI
|
||||
#error ABSL_INTERNAL_HAS_RTTI cannot be directly set
|
||||
#elif !defined(__GNUC__) || defined(__GXX_RTTI)
|
||||
#define ABSL_INTERNAL_HAS_RTTI 1
|
||||
#endif // !defined(__GNUC__) || defined(__GXX_RTTI)
|
||||
|
||||
// ABSL_INTERNAL_HAVE_SSE is used for compile-time detection of SSE support.
|
||||
// See https://gcc.gnu.org/onlinedocs/gcc/x86-Options.html for an overview of
|
||||
// which architectures support the various x86 instruction sets.
|
||||
#ifdef ABSL_INTERNAL_HAVE_SSE
|
||||
#error ABSL_INTERNAL_HAVE_SSE cannot be directly set
|
||||
#elif defined(__SSE__)
|
||||
#define ABSL_INTERNAL_HAVE_SSE 1
|
||||
#elif defined(_M_X64) || (defined(_M_IX86_FP) && _M_IX86_FP >= 1)
|
||||
// MSVC only defines _M_IX86_FP for x86 32-bit code, and _M_IX86_FP >= 1
|
||||
// indicates that at least SSE was targeted with the /arch:SSE option.
|
||||
// All x86-64 processors support SSE, so support can be assumed.
|
||||
// https://docs.microsoft.com/en-us/cpp/preprocessor/predefined-macros
|
||||
#define ABSL_INTERNAL_HAVE_SSE 1
|
||||
#endif
|
||||
|
||||
// ABSL_INTERNAL_HAVE_SSE2 is used for compile-time detection of SSE2 support.
|
||||
// See https://gcc.gnu.org/onlinedocs/gcc/x86-Options.html for an overview of
|
||||
// which architectures support the various x86 instruction sets.
|
||||
#ifdef ABSL_INTERNAL_HAVE_SSE2
|
||||
#error ABSL_INTERNAL_HAVE_SSE2 cannot be directly set
|
||||
#elif defined(__SSE2__)
|
||||
#define ABSL_INTERNAL_HAVE_SSE2 1
|
||||
#elif defined(_M_X64) || (defined(_M_IX86_FP) && _M_IX86_FP >= 2)
|
||||
// MSVC only defines _M_IX86_FP for x86 32-bit code, and _M_IX86_FP >= 2
|
||||
// indicates that at least SSE2 was targeted with the /arch:SSE2 option.
|
||||
// All x86-64 processors support SSE2, so support can be assumed.
|
||||
// https://docs.microsoft.com/en-us/cpp/preprocessor/predefined-macros
|
||||
#define ABSL_INTERNAL_HAVE_SSE2 1
|
||||
#endif
|
||||
|
||||
// ABSL_INTERNAL_HAVE_SSSE3 is used for compile-time detection of SSSE3 support.
|
||||
// See https://gcc.gnu.org/onlinedocs/gcc/x86-Options.html for an overview of
|
||||
// which architectures support the various x86 instruction sets.
|
||||
//
|
||||
// MSVC does not have a mode that targets SSSE3 at compile-time. To use SSSE3
|
||||
// with MSVC requires either assuming that the code will only every run on CPUs
|
||||
// that support SSSE3, otherwise __cpuid() can be used to detect support at
|
||||
// runtime and fallback to a non-SSSE3 implementation when SSSE3 is unsupported
|
||||
// by the CPU.
|
||||
#ifdef ABSL_INTERNAL_HAVE_SSSE3
|
||||
#error ABSL_INTERNAL_HAVE_SSSE3 cannot be directly set
|
||||
#elif defined(__SSSE3__)
|
||||
#define ABSL_INTERNAL_HAVE_SSSE3 1
|
||||
#endif
|
||||
|
||||
// ABSL_INTERNAL_HAVE_ARM_NEON is used for compile-time detection of NEON (ARM
|
||||
// SIMD).
|
||||
#ifdef ABSL_INTERNAL_HAVE_ARM_NEON
|
||||
#error ABSL_INTERNAL_HAVE_ARM_NEON cannot be directly set
|
||||
#elif defined(__ARM_NEON)
|
||||
#define ABSL_INTERNAL_HAVE_ARM_NEON 1
|
||||
#endif
|
||||
|
||||
#endif // ABSL_BASE_CONFIG_H_
|
@ -433,31 +433,6 @@ ABSL_NAMESPACE_END
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef __cplusplus
|
||||
#ifdef ABSL_HAVE_THREAD_SANITIZER
|
||||
ABSL_INTERNAL_BEGIN_EXTERN_C
|
||||
int RunningOnValgrind();
|
||||
double ValgrindSlowdown();
|
||||
ABSL_INTERNAL_END_EXTERN_C
|
||||
#else
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
namespace base_internal {
|
||||
ABSL_DEPRECATED(
|
||||
"Don't use this interface. It is misleading and is being deleted.")
|
||||
ABSL_ATTRIBUTE_ALWAYS_INLINE inline int RunningOnValgrind() { return 0; }
|
||||
ABSL_DEPRECATED(
|
||||
"Don't use this interface. It is misleading and is being deleted.")
|
||||
ABSL_ATTRIBUTE_ALWAYS_INLINE inline double ValgrindSlowdown() { return 1.0; }
|
||||
} // namespace base_internal
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
|
||||
using absl::base_internal::RunningOnValgrind;
|
||||
using absl::base_internal::ValgrindSlowdown;
|
||||
#endif
|
||||
#endif
|
||||
|
||||
// -------------------------------------------------------------------------
|
||||
// Address sanitizer annotations
|
||||
|
||||
@ -471,7 +446,7 @@ using absl::base_internal::ValgrindSlowdown;
|
||||
__sanitizer_annotate_contiguous_container(beg, end, old_mid, new_mid)
|
||||
#define ABSL_ADDRESS_SANITIZER_REDZONE(name) \
|
||||
struct { \
|
||||
char x[8] __attribute__((aligned(8))); \
|
||||
alignas(8) char x[8]; \
|
||||
} name
|
||||
|
||||
#else
|
@ -701,7 +701,10 @@ struct BasicGuaranteeWithExtraContracts : public NonNegative {
|
||||
|
||||
static constexpr int kExceptionSentinel = 9999;
|
||||
};
|
||||
|
||||
#ifdef ABSL_INTERNAL_NEED_REDUNDANT_CONSTEXPR_DECL
|
||||
constexpr int BasicGuaranteeWithExtraContracts::kExceptionSentinel;
|
||||
#endif
|
||||
|
||||
TEST(ExceptionCheckTest, BasicGuaranteeWithExtraContracts) {
|
||||
auto tester_with_val =
|
@ -25,6 +25,8 @@
|
||||
#include <atomic>
|
||||
#include <chrono> // NOLINT(build/c++11)
|
||||
|
||||
#include "absl/base/attributes.h"
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/internal/unscaledcycleclock.h"
|
||||
|
||||
namespace absl {
|
||||
@ -33,44 +35,20 @@ namespace base_internal {
|
||||
|
||||
#if ABSL_USE_UNSCALED_CYCLECLOCK
|
||||
|
||||
namespace {
|
||||
|
||||
#ifdef NDEBUG
|
||||
#ifdef ABSL_INTERNAL_UNSCALED_CYCLECLOCK_FREQUENCY_IS_CPU_FREQUENCY
|
||||
// Not debug mode and the UnscaledCycleClock frequency is the CPU
|
||||
// frequency. Scale the CycleClock to prevent overflow if someone
|
||||
// tries to represent the time as cycles since the Unix epoch.
|
||||
static constexpr int32_t kShift = 1;
|
||||
#else
|
||||
// Not debug mode and the UnscaledCycleClock isn't operating at the
|
||||
// raw CPU frequency. There is no need to do any scaling, so don't
|
||||
// needlessly sacrifice precision.
|
||||
static constexpr int32_t kShift = 0;
|
||||
#endif
|
||||
#else
|
||||
// In debug mode use a different shift to discourage depending on a
|
||||
// particular shift value.
|
||||
static constexpr int32_t kShift = 2;
|
||||
#ifdef ABSL_INTERNAL_NEED_REDUNDANT_CONSTEXPR_DECL
|
||||
constexpr int32_t CycleClock::kShift;
|
||||
constexpr double CycleClock::kFrequencyScale;
|
||||
#endif
|
||||
|
||||
static constexpr double kFrequencyScale = 1.0 / (1 << kShift);
|
||||
static std::atomic<CycleClockSourceFunc> cycle_clock_source;
|
||||
ABSL_CONST_INIT std::atomic<CycleClockSourceFunc>
|
||||
CycleClock::cycle_clock_source_{nullptr};
|
||||
|
||||
CycleClockSourceFunc LoadCycleClockSource() {
|
||||
// Optimize for the common case (no callback) by first doing a relaxed load;
|
||||
// this is significantly faster on non-x86 platforms.
|
||||
if (cycle_clock_source.load(std::memory_order_relaxed) == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
// This corresponds to the store(std::memory_order_release) in
|
||||
// CycleClockSource::Register, and makes sure that any updates made prior to
|
||||
// registering the callback are visible to this thread before the callback is
|
||||
// invoked.
|
||||
return cycle_clock_source.load(std::memory_order_acquire);
|
||||
void CycleClockSource::Register(CycleClockSourceFunc source) {
|
||||
// Corresponds to the load(std::memory_order_acquire) in LoadCycleClockSource.
|
||||
CycleClock::cycle_clock_source_.store(source, std::memory_order_release);
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
#ifdef _WIN32
|
||||
int64_t CycleClock::Now() {
|
||||
auto fn = LoadCycleClockSource();
|
||||
if (fn == nullptr) {
|
||||
@ -78,15 +56,7 @@ int64_t CycleClock::Now() {
|
||||
}
|
||||
return fn() >> kShift;
|
||||
}
|
||||
|
||||
double CycleClock::Frequency() {
|
||||
return kFrequencyScale * base_internal::UnscaledCycleClock::Frequency();
|
||||
}
|
||||
|
||||
void CycleClockSource::Register(CycleClockSourceFunc source) {
|
||||
// Corresponds to the load(std::memory_order_acquire) in LoadCycleClockSource.
|
||||
cycle_clock_source.store(source, std::memory_order_release);
|
||||
}
|
||||
#endif
|
||||
|
||||
#else
|
||||
|
@ -42,14 +42,19 @@
|
||||
#ifndef ABSL_BASE_INTERNAL_CYCLECLOCK_H_
|
||||
#define ABSL_BASE_INTERNAL_CYCLECLOCK_H_
|
||||
|
||||
#include <atomic>
|
||||
#include <cstdint>
|
||||
|
||||
#include "absl/base/attributes.h"
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/internal/unscaledcycleclock.h"
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
namespace base_internal {
|
||||
|
||||
using CycleClockSourceFunc = int64_t (*)();
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
// CycleClock
|
||||
// -----------------------------------------------------------------------------
|
||||
@ -68,12 +73,37 @@ class CycleClock {
|
||||
static double Frequency();
|
||||
|
||||
private:
|
||||
#if ABSL_USE_UNSCALED_CYCLECLOCK
|
||||
static CycleClockSourceFunc LoadCycleClockSource();
|
||||
|
||||
#ifdef NDEBUG
|
||||
#ifdef ABSL_INTERNAL_UNSCALED_CYCLECLOCK_FREQUENCY_IS_CPU_FREQUENCY
|
||||
// Not debug mode and the UnscaledCycleClock frequency is the CPU
|
||||
// frequency. Scale the CycleClock to prevent overflow if someone
|
||||
// tries to represent the time as cycles since the Unix epoch.
|
||||
static constexpr int32_t kShift = 1;
|
||||
#else
|
||||
// Not debug mode and the UnscaledCycleClock isn't operating at the
|
||||
// raw CPU frequency. There is no need to do any scaling, so don't
|
||||
// needlessly sacrifice precision.
|
||||
static constexpr int32_t kShift = 0;
|
||||
#endif
|
||||
#else // NDEBUG
|
||||
// In debug mode use a different shift to discourage depending on a
|
||||
// particular shift value.
|
||||
static constexpr int32_t kShift = 2;
|
||||
#endif // NDEBUG
|
||||
|
||||
static constexpr double kFrequencyScale = 1.0 / (1 << kShift);
|
||||
ABSL_CONST_INIT static std::atomic<CycleClockSourceFunc> cycle_clock_source_;
|
||||
#endif // ABSL_USE_UNSCALED_CYCLECLOC
|
||||
|
||||
CycleClock() = delete; // no instances
|
||||
CycleClock(const CycleClock&) = delete;
|
||||
CycleClock& operator=(const CycleClock&) = delete;
|
||||
};
|
||||
|
||||
using CycleClockSourceFunc = int64_t (*)();
|
||||
friend class CycleClockSource;
|
||||
};
|
||||
|
||||
class CycleClockSource {
|
||||
private:
|
||||
@ -87,6 +117,41 @@ class CycleClockSource {
|
||||
static void Register(CycleClockSourceFunc source);
|
||||
};
|
||||
|
||||
#if ABSL_USE_UNSCALED_CYCLECLOCK
|
||||
|
||||
inline CycleClockSourceFunc CycleClock::LoadCycleClockSource() {
|
||||
#if !defined(__x86_64__)
|
||||
// Optimize for the common case (no callback) by first doing a relaxed load;
|
||||
// this is significantly faster on non-x86 platforms.
|
||||
if (cycle_clock_source_.load(std::memory_order_relaxed) == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
#endif // !defined(__x86_64__)
|
||||
|
||||
// This corresponds to the store(std::memory_order_release) in
|
||||
// CycleClockSource::Register, and makes sure that any updates made prior to
|
||||
// registering the callback are visible to this thread before the callback
|
||||
// is invoked.
|
||||
return cycle_clock_source_.load(std::memory_order_acquire);
|
||||
}
|
||||
|
||||
// Accessing globals in inlined code in Window DLLs is problematic.
|
||||
#ifndef _WIN32
|
||||
inline int64_t CycleClock::Now() {
|
||||
auto fn = LoadCycleClockSource();
|
||||
if (fn == nullptr) {
|
||||
return base_internal::UnscaledCycleClock::Now() >> kShift;
|
||||
}
|
||||
return fn() >> kShift;
|
||||
}
|
||||
#endif
|
||||
|
||||
inline double CycleClock::Frequency() {
|
||||
return kFrequencyScale * base_internal::UnscaledCycleClock::Frequency();
|
||||
}
|
||||
|
||||
#endif // ABSL_USE_UNSCALED_CYCLECLOCK
|
||||
|
||||
} // namespace base_internal
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
@ -20,7 +20,7 @@
|
||||
|
||||
#include "absl/base/config.h"
|
||||
|
||||
#if ABSL_HAVE_MMAP
|
||||
#ifdef ABSL_HAVE_MMAP
|
||||
|
||||
#include <sys/mman.h>
|
||||
|
||||
@ -41,13 +41,13 @@
|
||||
|
||||
#ifdef __mips__
|
||||
// Include definitions of the ABI currently in use.
|
||||
#ifdef __BIONIC__
|
||||
#if defined(__BIONIC__) || !defined(__GLIBC__)
|
||||
// Android doesn't have sgidefs.h, but does have asm/sgidefs.h, which has the
|
||||
// definitions we need.
|
||||
#include <asm/sgidefs.h>
|
||||
#else
|
||||
#include <sgidefs.h>
|
||||
#endif // __BIONIC__
|
||||
#endif // __BIONIC__ || !__GLIBC__
|
||||
#endif // __mips__
|
||||
|
||||
// SYS_mmap and SYS_munmap are not defined in Android.
|
@ -16,16 +16,9 @@
|
||||
#ifndef ABSL_BASE_INTERNAL_ENDIAN_H_
|
||||
#define ABSL_BASE_INTERNAL_ENDIAN_H_
|
||||
|
||||
// The following guarantees declaration of the byte swap functions
|
||||
#ifdef _MSC_VER
|
||||
#include <stdlib.h> // NOLINT(build/include)
|
||||
#elif defined(__FreeBSD__)
|
||||
#include <sys/endian.h>
|
||||
#elif defined(__GLIBC__)
|
||||
#include <byteswap.h> // IWYU pragma: export
|
||||
#endif
|
||||
|
||||
#include <cstdint>
|
||||
#include <cstdlib>
|
||||
|
||||
#include "absl/base/casts.h"
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/internal/unaligned_access.h"
|
||||
@ -34,47 +27,11 @@
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
|
||||
// Use compiler byte-swapping intrinsics if they are available. 32-bit
|
||||
// and 64-bit versions are available in Clang and GCC as of GCC 4.3.0.
|
||||
// The 16-bit version is available in Clang and GCC only as of GCC 4.8.0.
|
||||
// For simplicity, we enable them all only for GCC 4.8.0 or later.
|
||||
#if defined(__clang__) || \
|
||||
(defined(__GNUC__) && \
|
||||
((__GNUC__ == 4 && __GNUC_MINOR__ >= 8) || __GNUC__ >= 5))
|
||||
inline uint64_t gbswap_64(uint64_t host_int) {
|
||||
#if ABSL_HAVE_BUILTIN(__builtin_bswap64) || defined(__GNUC__)
|
||||
return __builtin_bswap64(host_int);
|
||||
}
|
||||
inline uint32_t gbswap_32(uint32_t host_int) {
|
||||
return __builtin_bswap32(host_int);
|
||||
}
|
||||
inline uint16_t gbswap_16(uint16_t host_int) {
|
||||
return __builtin_bswap16(host_int);
|
||||
}
|
||||
|
||||
#elif defined(_MSC_VER)
|
||||
inline uint64_t gbswap_64(uint64_t host_int) {
|
||||
return _byteswap_uint64(host_int);
|
||||
}
|
||||
inline uint32_t gbswap_32(uint32_t host_int) {
|
||||
return _byteswap_ulong(host_int);
|
||||
}
|
||||
inline uint16_t gbswap_16(uint16_t host_int) {
|
||||
return _byteswap_ushort(host_int);
|
||||
}
|
||||
|
||||
#else
|
||||
inline uint64_t gbswap_64(uint64_t host_int) {
|
||||
#if defined(__GNUC__) && defined(__x86_64__) && !defined(__APPLE__)
|
||||
// Adapted from /usr/include/byteswap.h. Not available on Mac.
|
||||
if (__builtin_constant_p(host_int)) {
|
||||
return __bswap_constant_64(host_int);
|
||||
} else {
|
||||
uint64_t result;
|
||||
__asm__("bswap %0" : "=r"(result) : "0"(host_int));
|
||||
return result;
|
||||
}
|
||||
#elif defined(__GLIBC__)
|
||||
return bswap_64(host_int);
|
||||
#else
|
||||
return (((host_int & uint64_t{0xFF}) << 56) |
|
||||
((host_int & uint64_t{0xFF00}) << 40) |
|
||||
@ -84,12 +41,14 @@ inline uint64_t gbswap_64(uint64_t host_int) {
|
||||
((host_int & uint64_t{0xFF0000000000}) >> 24) |
|
||||
((host_int & uint64_t{0xFF000000000000}) >> 40) |
|
||||
((host_int & uint64_t{0xFF00000000000000}) >> 56));
|
||||
#endif // bswap_64
|
||||
#endif
|
||||
}
|
||||
|
||||
inline uint32_t gbswap_32(uint32_t host_int) {
|
||||
#if defined(__GLIBC__)
|
||||
return bswap_32(host_int);
|
||||
#if ABSL_HAVE_BUILTIN(__builtin_bswap32) || defined(__GNUC__)
|
||||
return __builtin_bswap32(host_int);
|
||||
#elif defined(_MSC_VER)
|
||||
return _byteswap_ulong(host_int);
|
||||
#else
|
||||
return (((host_int & uint32_t{0xFF}) << 24) |
|
||||
((host_int & uint32_t{0xFF00}) << 8) |
|
||||
@ -99,33 +58,29 @@ inline uint32_t gbswap_32(uint32_t host_int) {
|
||||
}
|
||||
|
||||
inline uint16_t gbswap_16(uint16_t host_int) {
|
||||
#if defined(__GLIBC__)
|
||||
return bswap_16(host_int);
|
||||
#if ABSL_HAVE_BUILTIN(__builtin_bswap16) || defined(__GNUC__)
|
||||
return __builtin_bswap16(host_int);
|
||||
#elif defined(_MSC_VER)
|
||||
return _byteswap_ushort(host_int);
|
||||
#else
|
||||
return (((host_int & uint16_t{0xFF}) << 8) |
|
||||
((host_int & uint16_t{0xFF00}) >> 8));
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif // intrinsics available
|
||||
|
||||
#ifdef ABSL_IS_LITTLE_ENDIAN
|
||||
|
||||
// Definitions for ntohl etc. that don't require us to include
|
||||
// netinet/in.h. We wrap gbswap_32 and gbswap_16 in functions rather
|
||||
// than just #defining them because in debug mode, gcc doesn't
|
||||
// correctly handle the (rather involved) definitions of bswap_32.
|
||||
// gcc guarantees that inline functions are as fast as macros, so
|
||||
// this isn't a performance hit.
|
||||
// Portable definitions for htonl (host-to-network) and friends on little-endian
|
||||
// architectures.
|
||||
inline uint16_t ghtons(uint16_t x) { return gbswap_16(x); }
|
||||
inline uint32_t ghtonl(uint32_t x) { return gbswap_32(x); }
|
||||
inline uint64_t ghtonll(uint64_t x) { return gbswap_64(x); }
|
||||
|
||||
#elif defined ABSL_IS_BIG_ENDIAN
|
||||
|
||||
// These definitions are simpler on big-endian machines
|
||||
// These are functions instead of macros to avoid self-assignment warnings
|
||||
// on calls such as "i = ghtnol(i);". This also provides type checking.
|
||||
// Portable definitions for htonl (host-to-network) etc on big-endian
|
||||
// architectures. These definitions are simpler since the host byte order is the
|
||||
// same as network byte order.
|
||||
inline uint16_t ghtons(uint16_t x) { return x; }
|
||||
inline uint32_t ghtonl(uint32_t x) { return x; }
|
||||
inline uint64_t ghtonll(uint64_t x) { return x; }
|
@ -536,7 +536,22 @@ class ThrowingValue : private exceptions_internal::TrackedObject {
|
||||
}
|
||||
|
||||
// Memory management operators
|
||||
// Args.. allows us to overload regular and placement new in one shot
|
||||
static void* operator new(size_t s) noexcept(
|
||||
IsSpecified(TypeSpec::kNoThrowNew)) {
|
||||
if (!IsSpecified(TypeSpec::kNoThrowNew)) {
|
||||
exceptions_internal::MaybeThrow(ABSL_PRETTY_FUNCTION, true);
|
||||
}
|
||||
return ::operator new(s);
|
||||
}
|
||||
|
||||
static void* operator new[](size_t s) noexcept(
|
||||
IsSpecified(TypeSpec::kNoThrowNew)) {
|
||||
if (!IsSpecified(TypeSpec::kNoThrowNew)) {
|
||||
exceptions_internal::MaybeThrow(ABSL_PRETTY_FUNCTION, true);
|
||||
}
|
||||
return ::operator new[](s);
|
||||
}
|
||||
|
||||
template <typename... Args>
|
||||
static void* operator new(size_t s, Args&&... args) noexcept(
|
||||
IsSpecified(TypeSpec::kNoThrowNew)) {
|
||||
@ -557,12 +572,6 @@ class ThrowingValue : private exceptions_internal::TrackedObject {
|
||||
|
||||
// Abseil doesn't support throwing overloaded operator delete. These are
|
||||
// provided so a throwing operator-new can clean up after itself.
|
||||
//
|
||||
// We provide both regular and templated operator delete because if only the
|
||||
// templated version is provided as we did with operator new, the compiler has
|
||||
// no way of knowing which overload of operator delete to call. See
|
||||
// https://en.cppreference.com/w/cpp/memory/new/operator_delete and
|
||||
// https://en.cppreference.com/w/cpp/language/delete for the gory details.
|
||||
void operator delete(void* p) noexcept { ::operator delete(p); }
|
||||
|
||||
template <typename... Args>
|
||||
@ -726,9 +735,8 @@ class ThrowingAllocator : private exceptions_internal::TrackedObject {
|
||||
|
||||
ThrowingAllocator select_on_container_copy_construction() noexcept(
|
||||
IsSpecified(AllocSpec::kNoThrowAllocate)) {
|
||||
auto& out = *this;
|
||||
ReadStateAndMaybeThrow(ABSL_PRETTY_FUNCTION);
|
||||
return out;
|
||||
return *this;
|
||||
}
|
||||
|
||||
template <typename U>
|
@ -28,8 +28,10 @@ struct FastTypeTag {
|
||||
constexpr static char dummy_var = 0;
|
||||
};
|
||||
|
||||
#ifdef ABSL_INTERNAL_NEED_REDUNDANT_CONSTEXPR_DECL
|
||||
template <typename Type>
|
||||
constexpr char FastTypeTag<Type>::dummy_var;
|
||||
#endif
|
||||
|
||||
// FastTypeId<Type>() evaluates at compile/link-time to a unique pointer for the
|
||||
// passed-in type. These are meant to be good match for keys into maps or
|
@ -14,6 +14,8 @@
|
||||
//
|
||||
// absl::base_internal::invoke(f, args...) is an implementation of
|
||||
// INVOKE(f, args...) from section [func.require] of the C++ standard.
|
||||
// When compiled as C++17 and later versions, it is implemented as an alias of
|
||||
// std::invoke.
|
||||
//
|
||||
// [func.require]
|
||||
// Define INVOKE (f, t1, t2, ..., tN) as follows:
|
||||
@ -35,6 +37,26 @@
|
||||
#ifndef ABSL_BASE_INTERNAL_INVOKE_H_
|
||||
#define ABSL_BASE_INTERNAL_INVOKE_H_
|
||||
|
||||
#include "absl/base/config.h"
|
||||
|
||||
#if ABSL_INTERNAL_CPLUSPLUS_LANG >= 201703L
|
||||
|
||||
#include <functional>
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
namespace base_internal {
|
||||
|
||||
using std::invoke;
|
||||
using std::invoke_result_t;
|
||||
using std::is_invocable_r;
|
||||
|
||||
} // namespace base_internal
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
|
||||
#else // ABSL_INTERNAL_CPLUSPLUS_LANG >= 201703L
|
||||
|
||||
#include <algorithm>
|
||||
#include <type_traits>
|
||||
#include <utility>
|
||||
@ -80,8 +102,18 @@ struct MemFunAndRef : StrippedAccept<MemFunAndRef> {
|
||||
static decltype((std::declval<Obj>().*
|
||||
std::declval<MemFun>())(std::declval<Args>()...))
|
||||
Invoke(MemFun&& mem_fun, Obj&& obj, Args&&... args) {
|
||||
// Ignore bogus GCC warnings on this line.
|
||||
// See https://gcc.gnu.org/bugzilla/show_bug.cgi?id=101436 for similar example.
|
||||
#if ABSL_INTERNAL_HAVE_MIN_GNUC_VERSION(11, 0)
|
||||
#pragma GCC diagnostic push
|
||||
#pragma GCC diagnostic ignored "-Warray-bounds"
|
||||
#pragma GCC diagnostic ignored "-Wmaybe-uninitialized"
|
||||
#endif
|
||||
return (std::forward<Obj>(obj).*
|
||||
std::forward<MemFun>(mem_fun))(std::forward<Args>(args)...);
|
||||
#if ABSL_INTERNAL_HAVE_MIN_GNUC_VERSION(11, 0)
|
||||
#pragma GCC diagnostic pop
|
||||
#endif
|
||||
}
|
||||
};
|
||||
|
||||
@ -180,8 +212,30 @@ invoke_result_t<F, Args...> invoke(F&& f, Args&&... args) {
|
||||
return Invoker<F, Args...>::type::Invoke(std::forward<F>(f),
|
||||
std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template <typename AlwaysVoid, typename, typename, typename...>
|
||||
struct IsInvocableRImpl : std::false_type {};
|
||||
|
||||
template <typename R, typename F, typename... Args>
|
||||
struct IsInvocableRImpl<
|
||||
absl::void_t<absl::base_internal::invoke_result_t<F, Args...> >, R, F,
|
||||
Args...>
|
||||
: std::integral_constant<
|
||||
bool,
|
||||
std::is_convertible<absl::base_internal::invoke_result_t<F, Args...>,
|
||||
R>::value ||
|
||||
std::is_void<R>::value> {};
|
||||
|
||||
// Type trait whose member `value` is true if invoking `F` with `Args` is valid,
|
||||
// and either the return type is convertible to `R`, or `R` is void.
|
||||
// C++11-compatible version of `std::is_invocable_r`.
|
||||
template <typename R, typename F, typename... Args>
|
||||
using is_invocable_r = IsInvocableRImpl<void, R, F, Args...>;
|
||||
|
||||
} // namespace base_internal
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
|
||||
#endif // ABSL_INTERNAL_CPLUSPLUS_LANG >= 201703L
|
||||
|
||||
#endif // ABSL_BASE_INTERNAL_INVOKE_H_
|
@ -86,7 +86,7 @@ static void Test(bool use_new_arena, bool call_malloc_hook, int n) {
|
||||
AllocMap::iterator it;
|
||||
BlockDesc block_desc;
|
||||
int rnd;
|
||||
LowLevelAlloc::Arena *arena = 0;
|
||||
LowLevelAlloc::Arena *arena = nullptr;
|
||||
if (use_new_arena) {
|
||||
int32_t flags = call_malloc_hook ? LowLevelAlloc::kCallMallocHook : 0;
|
||||
arena = LowLevelAlloc::NewArena(flags);
|
||||
@ -101,9 +101,8 @@ static void Test(bool use_new_arena, bool call_malloc_hook, int n) {
|
||||
case 0: // coin came up heads: add a block
|
||||
using_low_level_alloc = true;
|
||||
block_desc.len = rand() & 0x3fff;
|
||||
block_desc.ptr =
|
||||
reinterpret_cast<char *>(
|
||||
arena == 0
|
||||
block_desc.ptr = reinterpret_cast<char *>(
|
||||
arena == nullptr
|
||||
? LowLevelAlloc::Alloc(block_desc.len)
|
||||
: LowLevelAlloc::AllocWithArena(block_desc.len, arena));
|
||||
using_low_level_alloc = false;
|
138
ThirdParty/abseil-cpp-20220623.1/absl/base/internal/prefetch.h
vendored
Normal file
138
ThirdParty/abseil-cpp-20220623.1/absl/base/internal/prefetch.h
vendored
Normal file
@ -0,0 +1,138 @@
|
||||
// Copyright 2022 The Abseil Authors.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// https://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#ifndef ABSL_BASE_INTERNAL_PREFETCH_H_
|
||||
#define ABSL_BASE_INTERNAL_PREFETCH_H_
|
||||
|
||||
#include "absl/base/config.h"
|
||||
|
||||
#ifdef __SSE__
|
||||
#include <xmmintrin.h>
|
||||
#endif
|
||||
|
||||
#if defined(_MSC_VER) && defined(ABSL_INTERNAL_HAVE_SSE)
|
||||
#include <intrin.h>
|
||||
#pragma intrinsic(_mm_prefetch)
|
||||
#endif
|
||||
|
||||
// Compatibility wrappers around __builtin_prefetch, to prefetch data
|
||||
// for read if supported by the toolchain.
|
||||
|
||||
// Move data into the cache before it is read, or "prefetch" it.
|
||||
//
|
||||
// The value of `addr` is the address of the memory to prefetch. If
|
||||
// the target and compiler support it, data prefetch instructions are
|
||||
// generated. If the prefetch is done some time before the memory is
|
||||
// read, it may be in the cache by the time the read occurs.
|
||||
//
|
||||
// The function names specify the temporal locality heuristic applied,
|
||||
// using the names of Intel prefetch instructions:
|
||||
//
|
||||
// T0 - high degree of temporal locality; data should be left in as
|
||||
// many levels of the cache possible
|
||||
// T1 - moderate degree of temporal locality
|
||||
// T2 - low degree of temporal locality
|
||||
// Nta - no temporal locality, data need not be left in the cache
|
||||
// after the read
|
||||
//
|
||||
// Incorrect or gratuitous use of these functions can degrade
|
||||
// performance, so use them only when representative benchmarks show
|
||||
// an improvement.
|
||||
//
|
||||
// Example usage:
|
||||
//
|
||||
// absl::base_internal::PrefetchT0(addr);
|
||||
//
|
||||
// Currently, the different prefetch calls behave on some Intel
|
||||
// architectures as follows:
|
||||
//
|
||||
// SNB..SKL SKX
|
||||
// PrefetchT0() L1/L2/L3 L1/L2
|
||||
// PrefetchT1() L2/L3 L2
|
||||
// PrefetchT2() L2/L3 L2
|
||||
// PrefetchNta() L1/--/L3 L1*
|
||||
//
|
||||
// * On SKX PrefetchNta() will bring the line into L1 but will evict
|
||||
// from L3 cache. This might result in surprising behavior.
|
||||
//
|
||||
// SNB = Sandy Bridge, SKL = Skylake, SKX = Skylake Xeon.
|
||||
//
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
namespace base_internal {
|
||||
|
||||
void PrefetchT0(const void* addr);
|
||||
void PrefetchT1(const void* addr);
|
||||
void PrefetchT2(const void* addr);
|
||||
void PrefetchNta(const void* addr);
|
||||
|
||||
// Implementation details follow.
|
||||
|
||||
#if ABSL_HAVE_BUILTIN(__builtin_prefetch) || defined(__GNUC__)
|
||||
|
||||
#define ABSL_INTERNAL_HAVE_PREFETCH 1
|
||||
|
||||
// See __builtin_prefetch:
|
||||
// https://gcc.gnu.org/onlinedocs/gcc/Other-Builtins.html.
|
||||
//
|
||||
// These functions speculatively load for read only. This is
|
||||
// safe for all currently supported platforms. However, prefetch for
|
||||
// store may have problems depending on the target platform.
|
||||
//
|
||||
inline void PrefetchT0(const void* addr) {
|
||||
// Note: this uses prefetcht0 on Intel.
|
||||
__builtin_prefetch(addr, 0, 3);
|
||||
}
|
||||
inline void PrefetchT1(const void* addr) {
|
||||
// Note: this uses prefetcht1 on Intel.
|
||||
__builtin_prefetch(addr, 0, 2);
|
||||
}
|
||||
inline void PrefetchT2(const void* addr) {
|
||||
// Note: this uses prefetcht2 on Intel.
|
||||
__builtin_prefetch(addr, 0, 1);
|
||||
}
|
||||
inline void PrefetchNta(const void* addr) {
|
||||
// Note: this uses prefetchtnta on Intel.
|
||||
__builtin_prefetch(addr, 0, 0);
|
||||
}
|
||||
|
||||
#elif defined(ABSL_INTERNAL_HAVE_SSE)
|
||||
|
||||
#define ABSL_INTERNAL_HAVE_PREFETCH 1
|
||||
|
||||
inline void PrefetchT0(const void* addr) {
|
||||
_mm_prefetch(reinterpret_cast<const char*>(addr), _MM_HINT_T0);
|
||||
}
|
||||
inline void PrefetchT1(const void* addr) {
|
||||
_mm_prefetch(reinterpret_cast<const char*>(addr), _MM_HINT_T1);
|
||||
}
|
||||
inline void PrefetchT2(const void* addr) {
|
||||
_mm_prefetch(reinterpret_cast<const char*>(addr), _MM_HINT_T2);
|
||||
}
|
||||
inline void PrefetchNta(const void* addr) {
|
||||
_mm_prefetch(reinterpret_cast<const char*>(addr), _MM_HINT_NTA);
|
||||
}
|
||||
|
||||
#else
|
||||
inline void PrefetchT0(const void*) {}
|
||||
inline void PrefetchT1(const void*) {}
|
||||
inline void PrefetchT2(const void*) {}
|
||||
inline void PrefetchNta(const void*) {}
|
||||
#endif
|
||||
|
||||
} // namespace base_internal
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
|
||||
#endif // ABSL_BASE_INTERNAL_PREFETCH_H_
|
43
ThirdParty/abseil-cpp-20220623.1/absl/base/internal/prefetch_test.cc
vendored
Normal file
43
ThirdParty/abseil-cpp-20220623.1/absl/base/internal/prefetch_test.cc
vendored
Normal file
@ -0,0 +1,43 @@
|
||||
// Copyright 2022 The Abseil Authors.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// https://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include "absl/base/internal/prefetch.h"
|
||||
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
namespace {
|
||||
|
||||
int number = 42;
|
||||
|
||||
TEST(Prefetch, TemporalLocalityNone) {
|
||||
absl::base_internal::PrefetchNta(&number);
|
||||
EXPECT_EQ(number, 42);
|
||||
}
|
||||
|
||||
TEST(Prefetch, TemporalLocalityLow) {
|
||||
absl::base_internal::PrefetchT2(&number);
|
||||
EXPECT_EQ(number, 42);
|
||||
}
|
||||
|
||||
TEST(Prefetch, TemporalLocalityMedium) {
|
||||
absl::base_internal::PrefetchT1(&number);
|
||||
EXPECT_EQ(number, 42);
|
||||
}
|
||||
|
||||
TEST(Prefetch, TemporalLocalityHigh) {
|
||||
absl::base_internal::PrefetchT0(&number);
|
||||
EXPECT_EQ(number, 42);
|
||||
}
|
||||
|
||||
} // namespace
|
@ -14,15 +14,17 @@
|
||||
|
||||
#include "absl/base/internal/raw_logging.h"
|
||||
|
||||
#include <stddef.h>
|
||||
#include <cstdarg>
|
||||
#include <cstddef>
|
||||
#include <cstdio>
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <string>
|
||||
|
||||
#include "absl/base/attributes.h"
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/internal/atomic_hook.h"
|
||||
#include "absl/base/internal/errno_saver.h"
|
||||
#include "absl/base/log_severity.h"
|
||||
|
||||
// We know how to perform low-level writes to stderr in POSIX and Windows. For
|
||||
@ -37,7 +39,7 @@
|
||||
// this, consider moving both to config.h instead.
|
||||
#if defined(__linux__) || defined(__APPLE__) || defined(__FreeBSD__) || \
|
||||
defined(__Fuchsia__) || defined(__native_client__) || \
|
||||
defined(__EMSCRIPTEN__) || defined(__ASYLO__)
|
||||
defined(__OpenBSD__) || defined(__EMSCRIPTEN__) || defined(__ASYLO__)
|
||||
|
||||
#include <unistd.h>
|
||||
|
||||
@ -50,7 +52,8 @@
|
||||
// ABSL_HAVE_SYSCALL_WRITE is defined when the platform provides the syscall
|
||||
// syscall(SYS_write, /*int*/ fd, /*char* */ buf, /*size_t*/ len);
|
||||
// for low level operations that want to avoid libc.
|
||||
#if (defined(__linux__) || defined(__FreeBSD__)) && !defined(__ANDROID__)
|
||||
#if (defined(__linux__) || defined(__FreeBSD__) || defined(__OpenBSD__)) && \
|
||||
!defined(__ANDROID__)
|
||||
#include <sys/syscall.h>
|
||||
#define ABSL_HAVE_SYSCALL_WRITE 1
|
||||
#define ABSL_LOW_LEVEL_WRITE_SUPPORTED 1
|
||||
@ -76,13 +79,6 @@ namespace {
|
||||
// Explicitly `#error` out when not `ABSL_LOW_LEVEL_WRITE_SUPPORTED`, except for
|
||||
// a selected set of platforms for which we expect not to be able to raw log.
|
||||
|
||||
ABSL_INTERNAL_ATOMIC_HOOK_ATTRIBUTES
|
||||
absl::base_internal::AtomicHook<LogPrefixHook>
|
||||
log_prefix_hook;
|
||||
ABSL_INTERNAL_ATOMIC_HOOK_ATTRIBUTES
|
||||
absl::base_internal::AtomicHook<AbortHook>
|
||||
abort_hook;
|
||||
|
||||
#ifdef ABSL_LOW_LEVEL_WRITE_SUPPORTED
|
||||
constexpr char kTruncated[] = " ... (message truncated)\n";
|
||||
|
||||
@ -130,6 +126,18 @@ bool DoRawLog(char** buf, int* size, const char* format, ...) {
|
||||
return true;
|
||||
}
|
||||
|
||||
bool DefaultLogFilterAndPrefix(absl::LogSeverity, const char* file, int line,
|
||||
char** buf, int* buf_size) {
|
||||
DoRawLog(buf, buf_size, "[%s : %d] RAW: ", file, line);
|
||||
return true;
|
||||
}
|
||||
|
||||
ABSL_INTERNAL_ATOMIC_HOOK_ATTRIBUTES
|
||||
absl::base_internal::AtomicHook<LogFilterAndPrefixHook>
|
||||
log_filter_and_prefix_hook(DefaultLogFilterAndPrefix);
|
||||
ABSL_INTERNAL_ATOMIC_HOOK_ATTRIBUTES
|
||||
absl::base_internal::AtomicHook<AbortHook> abort_hook;
|
||||
|
||||
void RawLogVA(absl::LogSeverity severity, const char* file, int line,
|
||||
const char* format, va_list ap) ABSL_PRINTF_ATTRIBUTE(4, 0);
|
||||
void RawLogVA(absl::LogSeverity severity, const char* file, int line,
|
||||
@ -150,14 +158,7 @@ void RawLogVA(absl::LogSeverity severity, const char* file, int line,
|
||||
}
|
||||
#endif
|
||||
|
||||
auto log_prefix_hook_ptr = log_prefix_hook.Load();
|
||||
if (log_prefix_hook_ptr) {
|
||||
enabled = log_prefix_hook_ptr(severity, file, line, &buf, &size);
|
||||
} else {
|
||||
if (enabled) {
|
||||
DoRawLog(&buf, &size, "[%s : %d] RAW: ", file, line);
|
||||
}
|
||||
}
|
||||
enabled = log_filter_and_prefix_hook(severity, file, line, &buf, &size);
|
||||
const char* const prefix_end = buf;
|
||||
|
||||
#ifdef ABSL_LOW_LEVEL_WRITE_SUPPORTED
|
||||
@ -168,11 +169,12 @@ void RawLogVA(absl::LogSeverity severity, const char* file, int line,
|
||||
} else {
|
||||
DoRawLog(&buf, &size, "%s", kTruncated);
|
||||
}
|
||||
SafeWriteToStderr(buffer, strlen(buffer));
|
||||
AsyncSignalSafeWriteToStderr(buffer, strlen(buffer));
|
||||
}
|
||||
#else
|
||||
static_cast<void>(format);
|
||||
static_cast<void>(ap);
|
||||
static_cast<void>(enabled);
|
||||
#endif
|
||||
|
||||
// Abort the process after logging a FATAL message, even if the output itself
|
||||
@ -195,8 +197,11 @@ void DefaultInternalLog(absl::LogSeverity severity, const char* file, int line,
|
||||
|
||||
} // namespace
|
||||
|
||||
void SafeWriteToStderr(const char *s, size_t len) {
|
||||
void AsyncSignalSafeWriteToStderr(const char* s, size_t len) {
|
||||
absl::base_internal::ErrnoSaver errno_saver;
|
||||
#if defined(ABSL_HAVE_SYSCALL_WRITE)
|
||||
// We prefer calling write via `syscall` to minimize the risk of libc doing
|
||||
// something "helpful".
|
||||
syscall(SYS_write, STDERR_FILENO, s, len);
|
||||
#elif defined(ABSL_HAVE_POSIX_WRITE)
|
||||
write(STDERR_FILENO, s, len);
|
||||
@ -229,7 +234,9 @@ ABSL_INTERNAL_ATOMIC_HOOK_ATTRIBUTES ABSL_DLL
|
||||
absl::base_internal::AtomicHook<InternalLogFunction>
|
||||
internal_log_function(DefaultInternalLog);
|
||||
|
||||
void RegisterLogPrefixHook(LogPrefixHook func) { log_prefix_hook.Store(func); }
|
||||
void RegisterLogFilterAndPrefixHook(LogFilterAndPrefixHook func) {
|
||||
log_filter_and_prefix_hook.Store(func);
|
||||
}
|
||||
|
||||
void RegisterAbortHook(AbortHook func) { abort_hook.Store(func); }
|
||||
|
@ -109,12 +109,9 @@ namespace raw_logging_internal {
|
||||
void RawLog(absl::LogSeverity severity, const char* file, int line,
|
||||
const char* format, ...) ABSL_PRINTF_ATTRIBUTE(4, 5);
|
||||
|
||||
// Writes the provided buffer directly to stderr, in a safe, low-level manner.
|
||||
//
|
||||
// In POSIX this means calling write(), which is async-signal safe and does
|
||||
// not malloc. If the platform supports the SYS_write syscall, we invoke that
|
||||
// directly to side-step any libc interception.
|
||||
void SafeWriteToStderr(const char *s, size_t len);
|
||||
// Writes the provided buffer directly to stderr, in a signal-safe, low-level
|
||||
// manner.
|
||||
void AsyncSignalSafeWriteToStderr(const char* s, size_t len);
|
||||
|
||||
// compile-time function to get the "base" filename, that is, the part of
|
||||
// a filename after the last "/" or "\" path separator. The search starts at
|
||||
@ -148,11 +145,12 @@ bool RawLoggingFullySupported();
|
||||
// 'severity' is the severity level of the message being written.
|
||||
// 'file' and 'line' are the file and line number where the ABSL_RAW_LOG macro
|
||||
// was located.
|
||||
// 'buffer' and 'buf_size' are pointers to the buffer and buffer size. If the
|
||||
// hook writes a prefix, it must increment *buffer and decrement *buf_size
|
||||
// 'buf' and 'buf_size' are pointers to the buffer and buffer size. If the
|
||||
// hook writes a prefix, it must increment *buf and decrement *buf_size
|
||||
// accordingly.
|
||||
using LogPrefixHook = bool (*)(absl::LogSeverity severity, const char* file,
|
||||
int line, char** buffer, int* buf_size);
|
||||
using LogFilterAndPrefixHook = bool (*)(absl::LogSeverity severity,
|
||||
const char* file, int line, char** buf,
|
||||
int* buf_size);
|
||||
|
||||
// Function type for a raw_logging customization hook called to abort a process
|
||||
// when a FATAL message is logged. If the provided AbortHook() returns, the
|
||||
@ -162,7 +160,10 @@ using LogPrefixHook = bool (*)(absl::LogSeverity severity, const char* file,
|
||||
// was located.
|
||||
// The NUL-terminated logged message lives in the buffer between 'buf_start'
|
||||
// and 'buf_end'. 'prefix_end' points to the first non-prefix character of the
|
||||
// buffer (as written by the LogPrefixHook.)
|
||||
// buffer (as written by the LogFilterAndPrefixHook.)
|
||||
//
|
||||
// The lifetime of the filename and message buffers will not end while the
|
||||
// process remains alive.
|
||||
using AbortHook = void (*)(const char* file, int line, const char* buf_start,
|
||||
const char* prefix_end, const char* buf_end);
|
||||
|
||||
@ -184,7 +185,7 @@ ABSL_INTERNAL_ATOMIC_HOOK_ATTRIBUTES ABSL_DLL extern base_internal::AtomicHook<
|
||||
//
|
||||
// These functions are safe to call at any point during initialization; they do
|
||||
// not block or malloc, and are async-signal safe.
|
||||
void RegisterLogPrefixHook(LogPrefixHook func);
|
||||
void RegisterLogFilterAndPrefixHook(LogFilterAndPrefixHook func);
|
||||
void RegisterAbortHook(AbortHook func);
|
||||
void RegisterInternalLogFunction(InternalLogFunction func);
|
||||
|
@ -19,6 +19,7 @@
|
||||
#include <limits>
|
||||
|
||||
#include "absl/base/attributes.h"
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/internal/atomic_hook.h"
|
||||
#include "absl/base/internal/cycleclock.h"
|
||||
#include "absl/base/internal/spinlock_wait.h"
|
||||
@ -66,12 +67,14 @@ void RegisterSpinLockProfiler(void (*fn)(const void *contendedlock,
|
||||
submit_profile_data.Store(fn);
|
||||
}
|
||||
|
||||
#ifdef ABSL_INTERNAL_NEED_REDUNDANT_CONSTEXPR_DECL
|
||||
// Static member variable definitions.
|
||||
constexpr uint32_t SpinLock::kSpinLockHeld;
|
||||
constexpr uint32_t SpinLock::kSpinLockCooperative;
|
||||
constexpr uint32_t SpinLock::kSpinLockDisabledScheduling;
|
||||
constexpr uint32_t SpinLock::kSpinLockSleeper;
|
||||
constexpr uint32_t SpinLock::kWaitTimeMask;
|
||||
#endif
|
||||
|
||||
// Uncommon constructors.
|
||||
SpinLock::SpinLock(base_internal::SchedulingMode mode)
|
@ -16,13 +16,15 @@
|
||||
|
||||
// Most users requiring mutual exclusion should use Mutex.
|
||||
// SpinLock is provided for use in two situations:
|
||||
// - for use in code that Mutex itself depends on
|
||||
// - for use by Abseil internal code that Mutex itself depends on
|
||||
// - for async signal safety (see below)
|
||||
|
||||
// SpinLock is async signal safe. If a spinlock is used within a signal
|
||||
// handler, all code that acquires the lock must ensure that the signal cannot
|
||||
// arrive while they are holding the lock. Typically, this is done by blocking
|
||||
// the signal.
|
||||
//
|
||||
// Threads waiting on a SpinLock may be woken in an arbitrary order.
|
||||
|
||||
#ifndef ABSL_BASE_INTERNAL_SPINLOCK_H_
|
||||
#define ABSL_BASE_INTERNAL_SPINLOCK_H_
|
||||
@ -118,6 +120,14 @@ class ABSL_LOCKABLE SpinLock {
|
||||
return (lockword_.load(std::memory_order_relaxed) & kSpinLockHeld) != 0;
|
||||
}
|
||||
|
||||
// Return immediately if this thread holds the SpinLock exclusively.
|
||||
// Otherwise, report an error by crashing with a diagnostic.
|
||||
inline void AssertHeld() const ABSL_ASSERT_EXCLUSIVE_LOCK() {
|
||||
if (!IsHeld()) {
|
||||
ABSL_RAW_LOG(FATAL, "thread should hold the lock on SpinLock");
|
||||
}
|
||||
}
|
||||
|
||||
protected:
|
||||
// These should not be exported except for testing.
|
||||
|
@ -57,13 +57,10 @@ static_assert(sizeof(std::atomic<uint32_t>) == sizeof(int),
|
||||
extern "C" {
|
||||
|
||||
ABSL_ATTRIBUTE_WEAK void ABSL_INTERNAL_C_SYMBOL(AbslInternalSpinLockDelay)(
|
||||
std::atomic<uint32_t> *w, uint32_t value, int loop,
|
||||
std::atomic<uint32_t> *w, uint32_t value, int,
|
||||
absl::base_internal::SchedulingMode) {
|
||||
absl::base_internal::ErrnoSaver errno_saver;
|
||||
struct timespec tm;
|
||||
tm.tv_sec = 0;
|
||||
tm.tv_nsec = absl::base_internal::SpinLockSuggestedDelayNS(loop);
|
||||
syscall(SYS_futex, w, FUTEX_WAIT | FUTEX_PRIVATE_FLAG, value, &tm);
|
||||
syscall(SYS_futex, w, FUTEX_WAIT | FUTEX_PRIVATE_FLAG, value, nullptr);
|
||||
}
|
||||
|
||||
ABSL_ATTRIBUTE_WEAK void ABSL_INTERNAL_C_SYMBOL(AbslInternalSpinLockWake)(
|
@ -39,6 +39,8 @@ struct SpinLockWaitTransition {
|
||||
// satisfying 0<=i<n && trans[i].done, atomically make the transition,
|
||||
// then return the old value of *w. Make any other atomic transitions
|
||||
// where !trans[i].done, but continue waiting.
|
||||
//
|
||||
// Wakeups for threads blocked on SpinLockWait do not respect priorities.
|
||||
uint32_t SpinLockWait(std::atomic<uint32_t> *w, int n,
|
||||
const SpinLockWaitTransition trans[],
|
||||
SchedulingMode scheduling_mode);
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user