mirror of
https://github.com/boostorg/log.git
synced 2026-01-26 06:32:24 +00:00
Merge branch 'develop'
This commit is contained in:
@@ -19,9 +19,8 @@ local here = [ modules.binding $(__name__) ] ;
|
||||
|
||||
project.push-current [ project.current ] ;
|
||||
project.load [ path.join [ path.make $(here:D) ] ../config/message-compiler ] ;
|
||||
project.pop-current ;
|
||||
project.push-current [ project.current ] ;
|
||||
project.load [ path.join [ path.make $(here:D) ] ../config/x86-ext ] ;
|
||||
project.load [ path.join [ path.make $(here:D) ] ../config/visibility ] ;
|
||||
project.pop-current ;
|
||||
|
||||
# Windows libs
|
||||
@@ -66,7 +65,7 @@ rule select-log-api ( properties * )
|
||||
# We have to verify if message compiler is available
|
||||
if ! ( <define>BOOST_LOG_WITHOUT_EVENT_LOG in $(properties) || <define>BOOST_LOG_WITHOUT_EVENT_LOG=1 in $(properties) )
|
||||
{
|
||||
local has_mc = [ configure.builds /boost/message-compiler//test-availability : $(properties) : message-compiler ] ;
|
||||
local has_mc = [ configure.builds /boost/log/message-compiler//test-availability : $(properties) : message-compiler ] ;
|
||||
if $(has_mc)
|
||||
{
|
||||
result = <log-api>winnt ;
|
||||
@@ -113,12 +112,27 @@ rule select-regex-backend ( properties * )
|
||||
return $(result) ;
|
||||
}
|
||||
|
||||
rule check-visibility ( properties * )
|
||||
{
|
||||
local result = ;
|
||||
|
||||
local has_visibility = [ configure.builds /boost/log/visibility//visibility : $(properties) : compiler-supports-visibility ] ;
|
||||
if $(has_visibility)
|
||||
{
|
||||
result = <cxxflags>"-fvisibility=hidden" ;
|
||||
}
|
||||
|
||||
return $(result) ;
|
||||
}
|
||||
|
||||
project boost/log
|
||||
: source-location ../src
|
||||
: requirements
|
||||
<conditional>@select-log-api
|
||||
<conditional>@check-instruction-set
|
||||
<conditional>@select-regex-backend
|
||||
<conditional>@check-visibility
|
||||
|
||||
<define>BOOST_SPIRIT_USE_PHOENIX_V3=1
|
||||
<define>BOOST_THREAD_DONT_USE_CHRONO=1 # Don't introduce false dependency on Boost.Chrono
|
||||
|
||||
@@ -136,6 +150,7 @@ project boost/log
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
|
||||
# Disable Intel warnings:
|
||||
# warning #177: function "X" was declared but never referenced
|
||||
@@ -243,7 +258,7 @@ rule ssse3-targets-cond ( properties * )
|
||||
|
||||
if <log-architecture>x86 in [ log-architecture.deduce-architecture $(properties) ]
|
||||
{
|
||||
local has_ssse3 = [ configure.builds /boost/x86-extensions//ssse3 : $(properties) : compiler-supports-ssse3 ] ;
|
||||
local has_ssse3 = [ configure.builds /boost/log/x86-extensions//ssse3 : $(properties) : compiler-supports-ssse3 ] ;
|
||||
if $(has_ssse3)
|
||||
{
|
||||
result = ;
|
||||
@@ -305,7 +320,7 @@ rule avx2-targets-cond ( properties * )
|
||||
|
||||
if <log-architecture>x86 in [ log-architecture.deduce-architecture $(properties) ]
|
||||
{
|
||||
local has_ssse3 = [ configure.builds /boost/x86-extensions//avx2 : $(properties) : compiler-supports-avx2 ] ;
|
||||
local has_ssse3 = [ configure.builds /boost/log/x86-extensions//avx2 : $(properties) : compiler-supports-avx2 ] ;
|
||||
if $(has_ssse3)
|
||||
{
|
||||
result = ;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
#
|
||||
# Copyright Andrey Semashev 2007 - 2014.
|
||||
# Copyright Andrey Semashev 2007 - 2015.
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# (See accompanying file LICENSE_1_0.txt or copy at
|
||||
# http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -8,7 +8,7 @@
|
||||
import project ;
|
||||
using mc ;
|
||||
|
||||
project /boost/message-compiler
|
||||
project /boost/log/message-compiler
|
||||
: source-location ../../src
|
||||
: requirements
|
||||
<pch>off
|
||||
|
||||
22
config/visibility/Jamfile.jam
Normal file
22
config/visibility/Jamfile.jam
Normal file
@@ -0,0 +1,22 @@
|
||||
#
|
||||
# Copyright Andrey Semashev 2007 - 2015.
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# (See accompanying file LICENSE_1_0.txt or copy at
|
||||
# http://www.boost.org/LICENSE_1_0.txt)
|
||||
#
|
||||
|
||||
import project ;
|
||||
|
||||
project /boost/log/visibility
|
||||
: source-location .
|
||||
: requirements
|
||||
<pch>off
|
||||
;
|
||||
|
||||
obj visibility : visibility.cpp
|
||||
:
|
||||
<cxxflags>"-fvisibility=hidden"
|
||||
# Some compilers may not support visibility but just ignore the option with a warning
|
||||
<warnings>all
|
||||
<warnings-as-errors>on
|
||||
;
|
||||
16
config/visibility/visibility.cpp
Normal file
16
config/visibility/visibility.cpp
Normal file
@@ -0,0 +1,16 @@
|
||||
/*
|
||||
* Copyright Andrey Semashev 2007 - 2015.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
|
||||
// Guess what, MSVC doesn't ever fail on unknown options, even with /WX. Hence this additional check.
|
||||
#if !defined(__GNUC__)
|
||||
#error Visibility option is only supported by gcc and compatible compilers
|
||||
#endif
|
||||
|
||||
int main(int, char*[])
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
@@ -1,5 +1,5 @@
|
||||
#
|
||||
# Copyright Andrey Semashev 2007 - 2014.
|
||||
# Copyright Andrey Semashev 2007 - 2015.
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# (See accompanying file LICENSE_1_0.txt or copy at
|
||||
# http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -7,7 +7,7 @@
|
||||
|
||||
import project ;
|
||||
|
||||
project /boost/x86-extensions
|
||||
project /boost/log/x86-extensions
|
||||
: source-location .
|
||||
: requirements
|
||||
<pch>off
|
||||
|
||||
@@ -9,6 +9,24 @@
|
||||
|
||||
[section:changelog Changelog]
|
||||
|
||||
[heading 2.6, Boost 1.59]
|
||||
|
||||
[*General changes:]
|
||||
|
||||
* On systems with [@https://gcc.gnu.org/wiki/Visibility symbol visibility] support (e.g. Linux) the library is now built with all internal symbols hidden. API symbols still have default visibility, so this shouldn't affect linking with the library.
|
||||
* *Breaking change:* The library has been ported to __boost_type_index__ for its underlying type info management tool. This improved library compatibility with hidden symbol visibility mode on some compilers. This affected the following public interfaces:
|
||||
* `invalid_type` exceptions thrown by the library now have `typeindex::type_index` attached as the description of the offending type. The type was previously identified by `type_info_wrapper`.
|
||||
* __boost_exception__ `type_info_info` error information now contains `typeindex::type_index` instead of `type_info_wrapper`. This is the error info that can be used to obtain the type info from `invalid_type` exceptions.
|
||||
* `attribute_value::get_type()` now returns `typeindex::type_index` instead of `type_info_wrapper`. If the `attribute_value` object is empty, the returned `type_index` is default-constructed (i.e. refers to the `void` type). User-defined attribute value implementations should be similatly changed (the `attribute_value::impl::get_type()` virtual method now also returns `typeindex::type_index`).
|
||||
* `type_info_wrapper` component has been deprecated and will be removed in future releases. __boost_type_index__ is recommended as a replacement.
|
||||
* Removed the previously deprecated headers: `boost/log/utility/intrusive_ref_counter.hpp`, `boost/log/utility/explicit_operator_bool.hpp`, `boost/log/utility/empty_deleter.hpp`.
|
||||
* Added support for building the library for OpenBSD. ([ticket 11446])
|
||||
* Improved internal implementation of the event synchronization primitive used for asynchronous logging. The updated implementation relies on __boost_atomic__ for atomic operations which provides better portability. On Linux the implementation uses futexes directly. ([ticket 11398])
|
||||
|
||||
[*Bug fixes:]
|
||||
|
||||
* Fixed incorrect behavior of `attribute_value_set::insert()` and `attribute_value_set` constructor in some cases. The inserted elements could have made some previously inserted elements not findable. The constructor from `attribute_set`s could leave some of the attribute values acquired from attributes not findable. ([ticket 11190])
|
||||
|
||||
[heading 2.5, Boost 1.58]
|
||||
|
||||
[*Bug fixes:]
|
||||
|
||||
@@ -17,6 +17,7 @@
|
||||
|
||||
[/ Links to external resources /]
|
||||
[def __boost_config__ [@http://www.boost.org/doc/libs/release/libs/config/doc/html/index.html Boost.Config]]
|
||||
[def __boost_atomic__ [@http://www.boost.org/doc/libs/release/doc/html/atomic.html Boost.Atomic]]
|
||||
[def __boost_smart_ptr__ [@http://www.boost.org/doc/libs/release/libs/smart_ptr/smart_ptr.htm Boost.SmartPtr]]
|
||||
[def __boost_function__ [@http://www.boost.org/doc/libs/release/doc/html/function.html Boost.Function]]
|
||||
[def __boost_filesystem__ [@http://www.boost.org/doc/libs/release/libs/filesystem/doc/index.htm Boost.Filesystem]]
|
||||
@@ -46,6 +47,7 @@
|
||||
[def __boost_asio__ [@http://www.boost.org/doc/libs/release/doc/html/boost_asio.html Boost.ASIO]]
|
||||
[def __boost_move__ [@http://www.boost.org/doc/libs/release/doc/html/move.html Boost.Move]]
|
||||
[def __boost_locale__ [@http://www.boost.org/doc/libs/release/libs/locale/doc/html/index.html Boost.Locale]]
|
||||
[def __boost_type_index__ [@http://www.boost.org/doc/libs/release/doc/html/boost_typeindex.html Boost.TypeIndex]]
|
||||
[def __boost_utility__ [@http://www.boost.org/doc/libs/release/libs/utility/utility.htm Boost.Utility]]
|
||||
[def __boost_quickbook__ [@http://www.boost.org/doc/libs/release/doc/html/quickbook.html Boost.Quickbook]]
|
||||
|
||||
@@ -245,6 +247,8 @@ The library provides the `BOOST_LOG_USE_COMPILER_TLS` configuration macro that a
|
||||
* The application executable must be linked with the Boost.Log library. It should not be loaded dynamically during run time.
|
||||
* The application must not use logging in global constructors or destructors.
|
||||
|
||||
Note that the `BOOST_LOG_USE_COMPILER_TLS` macro only controls use of TLS in Boost.Log but not in other libraries used by Boost.Log. For example, __boost_asio__ uses compiler-supplied TLS by default. In order to build Boost.Log binaries completely free from use of compiler-supplied TLS, this feature has to be disabled in those other libraries as well (in case of __boost_asio__ this can be achieved by defining `BOOST_ASIO_DISABLE_THREAD_KEYWORD_EXTENSION` when building and using Boost).
|
||||
|
||||
[endsect]
|
||||
|
||||
[endsect]
|
||||
|
||||
@@ -23,6 +23,8 @@ String literals support interface similar to STL strings, except for string modi
|
||||
|
||||
[section:type_info_wrapper Type information wrapper]
|
||||
|
||||
[note This component is deprecated and will be removed in future releases. __boost_type_index__ is recommended as a replacement.]
|
||||
|
||||
#include <``[boost_log_utility_type_info_wrapper_hpp]``>
|
||||
|
||||
The language support for run time type information is essential for the library. But partially because of limitations that the C++ Standard imposes on this feature, partially because of differences of implementation of different compilers, there was a need for a lightweight wrapper around the `std::type_info` class to fill the gaps. The table below briefly shows the differences between the `std::type_info` and [class_log_type_info_wrapper] classes.
|
||||
|
||||
@@ -16,6 +16,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -16,6 +16,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -16,6 +16,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -16,6 +16,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -19,6 +19,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -18,6 +18,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -16,6 +16,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -16,6 +16,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -16,6 +16,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -17,6 +17,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -16,6 +16,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -16,6 +16,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -16,6 +16,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -17,6 +17,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -16,6 +16,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -16,6 +16,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_WARNINGS
|
||||
<toolset>intel-win:<define>_SCL_SECURE_NO_DEPRECATE
|
||||
<toolset>intel-win:<define>_CRT_SECURE_NO_WARNINGS
|
||||
|
||||
@@ -15,11 +15,11 @@
|
||||
#ifndef BOOST_LOG_ATTRIBUTE_VALUE_HPP_INCLUDED_
|
||||
#define BOOST_LOG_ATTRIBUTE_VALUE_HPP_INCLUDED_
|
||||
|
||||
#include <boost/type_index.hpp>
|
||||
#include <boost/move/core.hpp>
|
||||
#include <boost/smart_ptr/intrusive_ptr.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
#include <boost/utility/explicit_operator_bool.hpp>
|
||||
#include <boost/log/utility/type_info_wrapper.hpp>
|
||||
#include <boost/log/utility/type_dispatch/type_dispatcher.hpp>
|
||||
#include <boost/log/attributes/attribute.hpp>
|
||||
#include <boost/log/attributes/value_extraction_fwd.hpp>
|
||||
@@ -103,7 +103,7 @@ public:
|
||||
/*!
|
||||
* \return The attribute value type
|
||||
*/
|
||||
virtual type_info_wrapper get_type() const { return type_info_wrapper(); }
|
||||
virtual typeindex::type_index get_type() const { return typeindex::type_index(); }
|
||||
};
|
||||
|
||||
private:
|
||||
@@ -166,12 +166,12 @@ public:
|
||||
* the information cannot be provided. If the returned value is not empty, the type
|
||||
* can be used for value extraction.
|
||||
*/
|
||||
type_info_wrapper get_type() const
|
||||
typeindex::type_index get_type() const
|
||||
{
|
||||
if (m_pImpl.get())
|
||||
return m_pImpl->get_type();
|
||||
else
|
||||
return type_info_wrapper();
|
||||
return typeindex::type_index();
|
||||
}
|
||||
|
||||
/*!
|
||||
|
||||
@@ -15,6 +15,7 @@
|
||||
#ifndef BOOST_LOG_ATTRIBUTES_ATTRIBUTE_VALUE_IMPL_HPP_INCLUDED_
|
||||
#define BOOST_LOG_ATTRIBUTES_ATTRIBUTE_VALUE_IMPL_HPP_INCLUDED_
|
||||
|
||||
#include <boost/type_index.hpp>
|
||||
#include <boost/move/core.hpp>
|
||||
#include <boost/move/utility.hpp>
|
||||
#include <boost/type_traits/remove_cv.hpp>
|
||||
@@ -87,7 +88,7 @@ public:
|
||||
/*!
|
||||
* \return The attribute value type
|
||||
*/
|
||||
type_info_wrapper get_type() const { return type_info_wrapper(typeid(value_type)); }
|
||||
typeindex::type_index get_type() const { return typeindex::type_id< value_type >(); }
|
||||
|
||||
/*!
|
||||
* \return Reference to the contained value.
|
||||
|
||||
@@ -79,7 +79,7 @@ protected:
|
||||
return new detached_value(boost::log::aux::this_thread::get_id());
|
||||
}
|
||||
|
||||
type_info_wrapper get_type() const { return type_info_wrapper(typeid(value_type)); }
|
||||
typeindex::type_index get_type() const { return typeindex::type_id< value_type >(); }
|
||||
};
|
||||
|
||||
public:
|
||||
|
||||
@@ -15,11 +15,11 @@
|
||||
#ifndef BOOST_LOG_ATTRIBUTES_FALLBACK_POLICY_HPP_INCLUDED_
|
||||
#define BOOST_LOG_ATTRIBUTES_FALLBACK_POLICY_HPP_INCLUDED_
|
||||
|
||||
#include <boost/type_index.hpp>
|
||||
#include <boost/type_traits/remove_cv.hpp>
|
||||
#include <boost/type_traits/remove_reference.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
#include <boost/log/exceptions.hpp>
|
||||
#include <boost/log/utility/type_info_wrapper.hpp>
|
||||
#include <boost/log/attributes/fallback_policy_fwd.hpp>
|
||||
#include <boost/log/detail/header.hpp>
|
||||
|
||||
@@ -59,7 +59,7 @@ struct fallback_to_none
|
||||
/*!
|
||||
* The method is called when value extraction failed because the attribute value has different type than requested.
|
||||
*/
|
||||
static void on_invalid_type(type_info_wrapper const&)
|
||||
static void on_invalid_type(typeindex::type_index const&)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -99,7 +99,7 @@ struct fallback_to_throw
|
||||
/*!
|
||||
* The method is called when value extraction failed because the attribute value has different type than requested.
|
||||
*/
|
||||
static void on_invalid_type(type_info_wrapper const& t)
|
||||
static void on_invalid_type(typeindex::type_index const& t)
|
||||
{
|
||||
BOOST_LOG_THROW_DESCR_PARAMS(invalid_type, "Attribute value has incompatible type", (t));
|
||||
}
|
||||
@@ -161,7 +161,7 @@ struct fallback_to_default
|
||||
/*!
|
||||
* The method is called when value extraction failed because the attribute value has different type than requested.
|
||||
*/
|
||||
static void on_invalid_type(type_info_wrapper const&)
|
||||
static void on_invalid_type(typeindex::type_index const&)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
@@ -88,8 +88,8 @@ private:
|
||||
BOOST_DELETED_FUNCTION(public_data(public_data const&))
|
||||
BOOST_DELETED_FUNCTION(public_data& operator= (public_data const&))
|
||||
|
||||
friend void intrusive_ptr_add_ref(const public_data* p) { ++p->m_ref_counter; }
|
||||
friend void intrusive_ptr_release(const public_data* p) { if (--p->m_ref_counter == 0) public_data::destroy(p); }
|
||||
friend void intrusive_ptr_add_ref(const public_data* p) BOOST_NOEXCEPT { ++p->m_ref_counter; }
|
||||
friend void intrusive_ptr_release(const public_data* p) BOOST_NOEXCEPT { if (--p->m_ref_counter == 0) public_data::destroy(p); }
|
||||
};
|
||||
|
||||
private:
|
||||
|
||||
@@ -22,12 +22,15 @@
|
||||
#ifndef BOOST_LOG_NO_THREADS
|
||||
|
||||
#if defined(BOOST_THREAD_PLATFORM_PTHREAD)
|
||||
# if defined(_POSIX_SEMAPHORES) && (_POSIX_SEMAPHORES + 0) > 0
|
||||
# if defined(__GNUC__) && defined(__GCC_HAVE_SYNC_COMPARE_AND_SWAP_4)
|
||||
# include <semaphore.h>
|
||||
# include <boost/cstdint.hpp>
|
||||
# define BOOST_LOG_EVENT_USE_POSIX_SEMAPHORE
|
||||
# endif
|
||||
# include <boost/atomic/capabilities.hpp>
|
||||
# if (defined(linux) || defined(__linux) || defined(__linux__)) && BOOST_ATOMIC_INT_LOCK_FREE == 2
|
||||
# include <boost/atomic/atomic.hpp>
|
||||
# define BOOST_LOG_EVENT_USE_FUTEX
|
||||
# elif defined(_POSIX_SEMAPHORES) && (_POSIX_SEMAPHORES + 0) > 0 && BOOST_ATOMIC_FLAG_LOCK_FREE == 2
|
||||
# include <semaphore.h>
|
||||
# include <boost/cstdint.hpp>
|
||||
# include <boost/atomic/atomic_flag.hpp>
|
||||
# define BOOST_LOG_EVENT_USE_POSIX_SEMAPHORE
|
||||
# endif
|
||||
#elif defined(BOOST_THREAD_PLATFORM_WIN32)
|
||||
# include <boost/cstdint.hpp>
|
||||
@@ -48,12 +51,37 @@ BOOST_LOG_OPEN_NAMESPACE
|
||||
|
||||
namespace aux {
|
||||
|
||||
#if defined(BOOST_LOG_EVENT_USE_POSIX_SEMAPHORE)
|
||||
#if defined(BOOST_LOG_EVENT_USE_FUTEX)
|
||||
|
||||
class futex_based_event
|
||||
{
|
||||
private:
|
||||
boost::atomic< int > m_state;
|
||||
|
||||
public:
|
||||
//! Default constructor
|
||||
BOOST_LOG_API futex_based_event();
|
||||
//! Destructor
|
||||
BOOST_LOG_API ~futex_based_event();
|
||||
|
||||
//! Waits for the object to become signalled
|
||||
BOOST_LOG_API void wait();
|
||||
//! Sets the object to a signalled state
|
||||
BOOST_LOG_API void set_signalled();
|
||||
|
||||
// Copying prohibited
|
||||
BOOST_DELETED_FUNCTION(futex_based_event(futex_based_event const&))
|
||||
BOOST_DELETED_FUNCTION(futex_based_event& operator= (futex_based_event const&))
|
||||
};
|
||||
|
||||
typedef futex_based_event event;
|
||||
|
||||
#elif defined(BOOST_LOG_EVENT_USE_POSIX_SEMAPHORE)
|
||||
|
||||
class sem_based_event
|
||||
{
|
||||
private:
|
||||
boost::uint32_t m_state;
|
||||
boost::atomic_flag m_state;
|
||||
sem_t m_semaphore;
|
||||
|
||||
public:
|
||||
|
||||
@@ -5,19 +5,23 @@
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
/*!
|
||||
* \file visible_type.hpp
|
||||
* \file is_ostream.hpp
|
||||
* \author Andrey Semashev
|
||||
* \date 08.03.2007
|
||||
* \date 05.07.2015
|
||||
*
|
||||
* \brief This header is the Boost.Log library implementation, see the library documentation
|
||||
* at http://www.boost.org/doc/libs/release/libs/log/doc/html/index.html. In this file
|
||||
* internal configuration macros are defined.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_LOG_DETAIL_VISIBLE_TYPE_HPP_INCLUDED_
|
||||
#define BOOST_LOG_DETAIL_VISIBLE_TYPE_HPP_INCLUDED_
|
||||
#ifndef BOOST_LOG_DETAIL_IS_OSTREAM_HPP_INCLUDED_
|
||||
#define BOOST_LOG_DETAIL_IS_OSTREAM_HPP_INCLUDED_
|
||||
|
||||
#include <iosfwd>
|
||||
#include <boost/type_traits/is_base_of.hpp>
|
||||
#include <boost/type_traits/has_left_shift.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
#include <boost/log/utility/formatting_ostream_fwd.hpp>
|
||||
#include <boost/log/detail/header.hpp>
|
||||
|
||||
#ifdef BOOST_HAS_PRAGMA_ONCE
|
||||
@@ -30,11 +34,16 @@ BOOST_LOG_OPEN_NAMESPACE
|
||||
|
||||
namespace aux {
|
||||
|
||||
//! The wrapper type whose type_info is always visible
|
||||
template< typename T >
|
||||
struct BOOST_SYMBOL_VISIBLE visible_type
|
||||
struct is_ostream
|
||||
{
|
||||
typedef T wrapped_type;
|
||||
static BOOST_CONSTEXPR_OR_CONST bool value = is_base_of< std::ios_base, T >::value && has_left_shift< T, int >::value;
|
||||
};
|
||||
|
||||
template< typename CharT, typename TraitsT, typename AllocatorT >
|
||||
struct is_ostream< basic_formatting_ostream< CharT, TraitsT, AllocatorT > >
|
||||
{
|
||||
static BOOST_CONSTEXPR_OR_CONST bool value = true;
|
||||
};
|
||||
|
||||
} // namespace aux
|
||||
@@ -45,4 +54,4 @@ BOOST_LOG_CLOSE_NAMESPACE // namespace log
|
||||
|
||||
#include <boost/log/detail/footer.hpp>
|
||||
|
||||
#endif // BOOST_LOG_DETAIL_VISIBLE_TYPE_HPP_INCLUDED_
|
||||
#endif // BOOST_LOG_DETAIL_IS_OSTREAM_HPP_INCLUDED_
|
||||
@@ -18,10 +18,10 @@
|
||||
#include <cstddef>
|
||||
#include <string>
|
||||
#include <stdexcept>
|
||||
#include <boost/type_index.hpp>
|
||||
#include <boost/preprocessor/seq/enum.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
#include <boost/log/attributes/attribute_name.hpp>
|
||||
#include <boost/log/utility/type_info_wrapper.hpp>
|
||||
#include <boost/log/detail/header.hpp>
|
||||
|
||||
#ifdef BOOST_HAS_PRAGMA_ONCE
|
||||
@@ -130,8 +130,8 @@ public:
|
||||
static BOOST_LOG_NORETURN void throw_(const char* file, std::size_t line);
|
||||
static BOOST_LOG_NORETURN void throw_(const char* file, std::size_t line, std::string const& descr);
|
||||
static BOOST_LOG_NORETURN void throw_(const char* file, std::size_t line, std::string const& descr, attribute_name const& name);
|
||||
static BOOST_LOG_NORETURN void throw_(const char* file, std::size_t line, std::string const& descr, type_info_wrapper const& type);
|
||||
static BOOST_LOG_NORETURN void throw_(const char* file, std::size_t line, std::string const& descr, attribute_name const& name, type_info_wrapper const& type);
|
||||
static BOOST_LOG_NORETURN void throw_(const char* file, std::size_t line, std::string const& descr, typeindex::type_index const& type);
|
||||
static BOOST_LOG_NORETURN void throw_(const char* file, std::size_t line, std::string const& descr, attribute_name const& name, typeindex::type_index const& type);
|
||||
#endif
|
||||
};
|
||||
|
||||
|
||||
@@ -15,14 +15,13 @@
|
||||
#ifndef BOOST_LOG_SOURCES_GLOBAL_LOGGER_STORAGE_HPP_INCLUDED_
|
||||
#define BOOST_LOG_SOURCES_GLOBAL_LOGGER_STORAGE_HPP_INCLUDED_
|
||||
|
||||
#include <typeinfo>
|
||||
#include <stdexcept>
|
||||
#include <boost/type_index.hpp>
|
||||
#include <boost/smart_ptr/shared_ptr.hpp>
|
||||
#include <boost/smart_ptr/make_shared_object.hpp>
|
||||
#include <boost/preprocessor/seq/enum.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
#include <boost/log/detail/singleton.hpp>
|
||||
#include <boost/log/detail/visible_type.hpp>
|
||||
#include <boost/log/detail/header.hpp>
|
||||
|
||||
#ifdef BOOST_HAS_PRAGMA_ONCE
|
||||
@@ -41,17 +40,19 @@ namespace aux {
|
||||
struct BOOST_LOG_NO_VTABLE BOOST_SYMBOL_VISIBLE logger_holder_base
|
||||
{
|
||||
//! The source file name where the logger was registered
|
||||
const char* m_RegistrationFile;
|
||||
const char* const m_RegistrationFile;
|
||||
//! The line number where the logger was registered
|
||||
unsigned int m_RegistrationLine;
|
||||
const unsigned int m_RegistrationLine;
|
||||
//! Stored logger type
|
||||
const typeindex::type_index m_LoggerType;
|
||||
|
||||
logger_holder_base(const char* file, unsigned int line) :
|
||||
logger_holder_base(const char* file, unsigned int line, typeindex::type_index logger_type) BOOST_NOEXCEPT :
|
||||
m_RegistrationFile(file),
|
||||
m_RegistrationLine(line)
|
||||
m_RegistrationLine(line),
|
||||
m_LoggerType(logger_type)
|
||||
{
|
||||
}
|
||||
virtual ~logger_holder_base() {}
|
||||
virtual std::type_info const& logger_type() const = 0;
|
||||
};
|
||||
|
||||
//! The actual logger holder class
|
||||
@@ -63,11 +64,10 @@ struct BOOST_SYMBOL_VISIBLE logger_holder :
|
||||
LoggerT m_Logger;
|
||||
|
||||
logger_holder(const char* file, unsigned int line, LoggerT const& logger) :
|
||||
logger_holder_base(file, line),
|
||||
logger_holder_base(file, line, typeindex::type_id< LoggerT >()),
|
||||
m_Logger(logger)
|
||||
{
|
||||
}
|
||||
std::type_info const& logger_type() const { return typeid(LoggerT); }
|
||||
};
|
||||
|
||||
//! The class implements a global repository of tagged loggers
|
||||
@@ -76,7 +76,7 @@ struct global_storage
|
||||
typedef shared_ptr< logger_holder_base >(*initializer_t)();
|
||||
|
||||
//! Finds or creates the logger and returns its holder
|
||||
BOOST_LOG_API static shared_ptr< logger_holder_base > get_or_init(std::type_info const& key, initializer_t initializer);
|
||||
BOOST_LOG_API static shared_ptr< logger_holder_base > get_or_init(typeindex::type_index key, initializer_t initializer);
|
||||
|
||||
// Non-constructible, non-copyable, non-assignable
|
||||
BOOST_DELETED_FUNCTION(global_storage())
|
||||
@@ -86,8 +86,8 @@ struct global_storage
|
||||
|
||||
//! Throws the \c odr_violation exception
|
||||
BOOST_LOG_API BOOST_LOG_NORETURN void throw_odr_violation(
|
||||
std::type_info const& tag_type,
|
||||
std::type_info const& logger_type,
|
||||
typeindex::type_index tag_type,
|
||||
typeindex::type_index logger_type,
|
||||
logger_holder_base const& registered);
|
||||
|
||||
//! The class implements a logger singleton
|
||||
@@ -116,18 +116,24 @@ struct logger_singleton :
|
||||
static void init_instance()
|
||||
{
|
||||
shared_ptr< logger_holder< logger_type > >& instance = base_type::get_instance();
|
||||
shared_ptr< logger_holder_base > holder = global_storage::get_or_init(
|
||||
typeid(boost::log::aux::visible_type< TagT >),
|
||||
&logger_singleton::construct_logger);
|
||||
instance = boost::dynamic_pointer_cast< logger_holder< logger_type > >(holder);
|
||||
if (!instance)
|
||||
const typeindex::type_index tag_type_index = typeindex::type_id< TagT >();
|
||||
shared_ptr< logger_holder_base > holder = global_storage::get_or_init(tag_type_index, &logger_singleton::construct_logger);
|
||||
const typeindex::type_index logger_type_index = typeindex::type_id< logger_type >();
|
||||
if (holder->m_LoggerType == logger_type_index)
|
||||
{
|
||||
// Note: dynamic_cast may fail here if logger_type is not visible (for example, with Clang on Linux, if the original logger
|
||||
// instance was initialized in a different DSO than where it's being queried). logger_holder default visibility doesn't
|
||||
// help since it is inhibited by the template parameter visibility.
|
||||
instance = boost::static_pointer_cast< logger_holder< logger_type > >(holder);
|
||||
}
|
||||
else
|
||||
{
|
||||
// In pure C++ this should never happen, since there cannot be two
|
||||
// different tag types that have equal type_infos. In real life it can
|
||||
// happen if the same-named tag is defined differently in two or more
|
||||
// dlls. This check is intended to detect such ODR violations. However, there
|
||||
// is no protection against different definitions of the logger type itself.
|
||||
throw_odr_violation(typeid(TagT), typeid(logger_type), *holder);
|
||||
throw_odr_violation(tag_type_index, logger_type_index, *holder);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -15,11 +15,11 @@
|
||||
#ifndef BOOST_LOG_SUPPORT_EXCEPTION_HPP_INCLUDED_
|
||||
#define BOOST_LOG_SUPPORT_EXCEPTION_HPP_INCLUDED_
|
||||
|
||||
#include <boost/type_index.hpp>
|
||||
#include <boost/exception/info.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
#include <boost/log/attributes/attribute_name.hpp>
|
||||
#include <boost/log/attributes/named_scope.hpp>
|
||||
#include <boost/log/utility/type_info_wrapper.hpp>
|
||||
#include <boost/log/detail/header.hpp>
|
||||
|
||||
#ifdef BOOST_HAS_PRAGMA_ONCE
|
||||
@@ -38,7 +38,7 @@ typedef error_info< struct attribute_name_info_tag, attribute_name > attribute_n
|
||||
/*!
|
||||
* Type info exception information
|
||||
*/
|
||||
typedef error_info< struct type_info_info_tag, type_info_wrapper > type_info_info;
|
||||
typedef error_info< struct type_info_info_tag, typeindex::type_index > type_info_info;
|
||||
|
||||
/*!
|
||||
* Parse position exception information
|
||||
|
||||
@@ -1,42 +0,0 @@
|
||||
/*
|
||||
* Copyright Andrey Semashev 2007 - 2015.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
/*!
|
||||
* \file empty_deleter.hpp
|
||||
* \author Andrey Semashev
|
||||
* \date 22.04.2007
|
||||
*
|
||||
* This header is deprecated, use boost/utility/empty_deleter.hpp instead. The header is left for
|
||||
* backward compatibility and will be removed in future versions.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_LOG_UTILITY_EMPTY_DELETER_HPP_INCLUDED_
|
||||
#define BOOST_LOG_UTILITY_EMPTY_DELETER_HPP_INCLUDED_
|
||||
|
||||
#include <boost/core/null_deleter.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
|
||||
#ifdef BOOST_HAS_PRAGMA_ONCE
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#if defined(__GNUC__)
|
||||
#pragma message "Boost.Log: This header is deprecated, use boost/core/null_deleter.hpp instead."
|
||||
#elif defined(_MSC_VER)
|
||||
#pragma message("Boost.Log: This header is deprecated, use boost/core/null_deleter.hpp instead.")
|
||||
#endif
|
||||
|
||||
namespace boost {
|
||||
|
||||
BOOST_LOG_OPEN_NAMESPACE
|
||||
|
||||
typedef boost::null_deleter empty_deleter;
|
||||
|
||||
BOOST_LOG_CLOSE_NAMESPACE // namespace log
|
||||
|
||||
} // namespace boost
|
||||
|
||||
#endif // BOOST_LOG_UTILITY_EMPTY_DELETER_HPP_INCLUDED_
|
||||
@@ -1,42 +0,0 @@
|
||||
/*
|
||||
* Copyright Andrey Semashev 2007 - 2015.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
/*!
|
||||
* \file explicit_operator_bool.hpp
|
||||
* \author Andrey Semashev
|
||||
* \date 08.03.2009
|
||||
*
|
||||
* This header is deprecated, use boost/utility/explicit_operator_bool.hpp instead. The header is left for
|
||||
* backward compatibility and will be removed in future versions.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_LOG_UTILITY_EXPLICIT_OPERATOR_BOOL_HPP_INCLUDED_
|
||||
#define BOOST_LOG_UTILITY_EXPLICIT_OPERATOR_BOOL_HPP_INCLUDED_
|
||||
|
||||
#include <boost/utility/explicit_operator_bool.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
|
||||
#ifdef BOOST_HAS_PRAGMA_ONCE
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#if defined(__GNUC__)
|
||||
#pragma message "Boost.Log: This header is deprecated, use boost/utility/explicit_operator_bool.hpp instead."
|
||||
#elif defined(_MSC_VER)
|
||||
#pragma message("Boost.Log: This header is deprecated, use boost/utility/explicit_operator_bool.hpp instead.")
|
||||
#endif
|
||||
|
||||
/*!
|
||||
* \brief The macro defines an explicit operator of conversion to \c bool
|
||||
*
|
||||
* The macro should be used inside the definition of a class that has to
|
||||
* support the conversion. The class should also implement <tt>operator!</tt>,
|
||||
* in terms of which the conversion operator will be implemented.
|
||||
*/
|
||||
#define BOOST_LOG_EXPLICIT_OPERATOR_BOOL()\
|
||||
BOOST_EXPLICIT_OPERATOR_BOOL()
|
||||
|
||||
#endif // BOOST_LOG_UTILITY_EXPLICIT_OPERATOR_BOOL_HPP_INCLUDED_
|
||||
@@ -54,6 +54,11 @@ template< typename R >
|
||||
struct enable_if_char_type< char32_t, R > { typedef R type; };
|
||||
#endif
|
||||
|
||||
template< typename StreamT, typename R >
|
||||
struct enable_if_formatting_ostream {};
|
||||
template< typename CharT, typename TraitsT, typename AllocatorT, typename R >
|
||||
struct enable_if_formatting_ostream< basic_formatting_ostream< CharT, TraitsT, AllocatorT >, R > { typedef R type; };
|
||||
|
||||
} // namespace aux
|
||||
|
||||
/*!
|
||||
@@ -768,17 +773,19 @@ void basic_formatting_ostream< CharT, TraitsT, AllocatorT >::aligned_write(const
|
||||
}
|
||||
}
|
||||
|
||||
template< typename CharT, typename TraitsT, typename AllocatorT, typename T >
|
||||
inline basic_formatting_ostream< CharT, TraitsT, AllocatorT >&
|
||||
operator<< (basic_formatting_ostream< CharT, TraitsT, AllocatorT >& strm, T const& value)
|
||||
// Implementation note: these operators below should be the least attractive for the compiler
|
||||
// so that user's overloads are chosen, when present. We use function template partial ordering for this purpose.
|
||||
template< typename StreamT, typename T >
|
||||
inline typename boost::log::aux::enable_if_formatting_ostream< StreamT, StreamT& >::type
|
||||
operator<< (StreamT& strm, T const& value)
|
||||
{
|
||||
strm.stream() << value;
|
||||
return strm;
|
||||
}
|
||||
|
||||
template< typename CharT, typename TraitsT, typename AllocatorT, typename T >
|
||||
inline basic_formatting_ostream< CharT, TraitsT, AllocatorT >&
|
||||
operator<< (basic_formatting_ostream< CharT, TraitsT, AllocatorT >& strm, T& value)
|
||||
template< typename StreamT, typename T >
|
||||
inline typename boost::log::aux::enable_if_formatting_ostream< StreamT, StreamT& >::type
|
||||
operator<< (StreamT& strm, T& value)
|
||||
{
|
||||
strm.stream() << value;
|
||||
return strm;
|
||||
@@ -786,19 +793,19 @@ operator<< (basic_formatting_ostream< CharT, TraitsT, AllocatorT >& strm, T& val
|
||||
|
||||
#if !defined(BOOST_NO_CXX11_RVALUE_REFERENCES)
|
||||
|
||||
template< typename CharT, typename TraitsT, typename AllocatorT, typename T >
|
||||
inline basic_formatting_ostream< CharT, TraitsT, AllocatorT >&
|
||||
operator<< (basic_formatting_ostream< CharT, TraitsT, AllocatorT >&& strm, T const& value)
|
||||
template< typename StreamT, typename T >
|
||||
inline typename boost::log::aux::enable_if_formatting_ostream< StreamT, StreamT& >::type
|
||||
operator<< (StreamT&& strm, T const& value)
|
||||
{
|
||||
static_cast< basic_formatting_ostream< CharT, TraitsT, AllocatorT >& >(strm) << value;
|
||||
strm.stream() << value;
|
||||
return strm;
|
||||
}
|
||||
|
||||
template< typename CharT, typename TraitsT, typename AllocatorT, typename T >
|
||||
inline basic_formatting_ostream< CharT, TraitsT, AllocatorT >&
|
||||
operator<< (basic_formatting_ostream< CharT, TraitsT, AllocatorT >&& strm, T& value)
|
||||
template< typename StreamT, typename T >
|
||||
inline typename boost::log::aux::enable_if_formatting_ostream< StreamT, StreamT& >::type
|
||||
operator<< (StreamT&& strm, T& value)
|
||||
{
|
||||
static_cast< basic_formatting_ostream< CharT, TraitsT, AllocatorT >& >(strm) << value;
|
||||
strm.stream() << value;
|
||||
return strm;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,55 +0,0 @@
|
||||
/*
|
||||
* Copyright Andrey Semashev 2007 - 2015.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
/*!
|
||||
* \file intrusive_ref_counter.hpp
|
||||
* \author Andrey Semashev
|
||||
* \date 12.03.2009
|
||||
*
|
||||
* This header is deprecated, use boost/smart_ptr/intrusive_ref_counter.hpp instead. The header is left for
|
||||
* backward compatibility and will be removed in future versions.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_LOG_UTILITY_INTRUSIVE_REF_COUNTER_HPP_INCLUDED_
|
||||
#define BOOST_LOG_UTILITY_INTRUSIVE_REF_COUNTER_HPP_INCLUDED_
|
||||
|
||||
#include <boost/smart_ptr/intrusive_ptr.hpp>
|
||||
#include <boost/smart_ptr/intrusive_ref_counter.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
#include <boost/log/detail/header.hpp>
|
||||
|
||||
#ifdef BOOST_HAS_PRAGMA_ONCE
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#if defined(__GNUC__)
|
||||
#pragma message "Boost.Log: This header is deprecated, use boost/smart_ptr/intrusive_ref_counter.hpp instead."
|
||||
#elif defined(_MSC_VER)
|
||||
#pragma message("Boost.Log: This header is deprecated, use boost/smart_ptr/intrusive_ref_counter.hpp instead.")
|
||||
#endif
|
||||
|
||||
namespace boost {
|
||||
|
||||
BOOST_LOG_OPEN_NAMESPACE
|
||||
|
||||
namespace aux {
|
||||
|
||||
struct legacy_intrusive_ref_counter_root
|
||||
{
|
||||
virtual ~legacy_intrusive_ref_counter_root() {}
|
||||
};
|
||||
|
||||
} // namespace aux
|
||||
|
||||
typedef boost::intrusive_ref_counter< aux::legacy_intrusive_ref_counter_root > intrusive_ref_counter;
|
||||
|
||||
BOOST_LOG_CLOSE_NAMESPACE // namespace log
|
||||
|
||||
} // namespace boost
|
||||
|
||||
#include <boost/log/detail/footer.hpp>
|
||||
|
||||
#endif // BOOST_LOG_UTILITY_INTRUSIVE_REF_COUNTER_HPP_INCLUDED_
|
||||
@@ -16,8 +16,9 @@
|
||||
#define BOOST_LOG_UTILITY_MANIPULATORS_TO_LOG_HPP_INCLUDED_
|
||||
|
||||
#include <iosfwd>
|
||||
#include <boost/mpl/bool.hpp>
|
||||
#include <boost/core/enable_if.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
#include <boost/log/detail/is_ostream.hpp>
|
||||
#include <boost/log/utility/formatting_ostream_fwd.hpp>
|
||||
#include <boost/log/detail/header.hpp>
|
||||
|
||||
@@ -46,34 +47,27 @@ private:
|
||||
value_type const& m_value;
|
||||
|
||||
public:
|
||||
explicit to_log_manip(value_type const& value) : m_value(value) {}
|
||||
to_log_manip(to_log_manip const& that) : m_value(that.m_value) {}
|
||||
explicit to_log_manip(value_type const& value) BOOST_NOEXCEPT : m_value(value) {}
|
||||
to_log_manip(to_log_manip const& that) BOOST_NOEXCEPT : m_value(that.m_value) {}
|
||||
|
||||
value_type const& get() const { return m_value; }
|
||||
value_type const& get() const BOOST_NOEXCEPT { return m_value; }
|
||||
};
|
||||
|
||||
template< typename CharT, typename TraitsT, typename T, typename TagT >
|
||||
inline std::basic_ostream< CharT, TraitsT >& operator<< (std::basic_ostream< CharT, TraitsT >& strm, to_log_manip< T, TagT > manip)
|
||||
{
|
||||
strm << manip.get();
|
||||
return strm;
|
||||
}
|
||||
|
||||
template< typename CharT, typename TraitsT, typename AllocatorT, typename T, typename TagT >
|
||||
inline basic_formatting_ostream< CharT, TraitsT, AllocatorT >& operator<< (basic_formatting_ostream< CharT, TraitsT, AllocatorT >& strm, to_log_manip< T, TagT > manip)
|
||||
template< typename StreamT, typename T, typename TagT >
|
||||
inline typename enable_if_c< log::aux::is_ostream< StreamT >::value, StreamT& >::type operator<< (StreamT& strm, to_log_manip< T, TagT > manip)
|
||||
{
|
||||
strm << manip.get();
|
||||
return strm;
|
||||
}
|
||||
|
||||
template< typename T >
|
||||
inline to_log_manip< T > to_log(T const& value)
|
||||
inline to_log_manip< T > to_log(T const& value) BOOST_NOEXCEPT
|
||||
{
|
||||
return to_log_manip< T >(value);
|
||||
}
|
||||
|
||||
template< typename TagT, typename T >
|
||||
inline to_log_manip< T, TagT > to_log(T const& value)
|
||||
inline to_log_manip< T, TagT > to_log(T const& value) BOOST_NOEXCEPT
|
||||
{
|
||||
return to_log_manip< T, TagT >(value);
|
||||
}
|
||||
|
||||
@@ -19,11 +19,10 @@
|
||||
#include <memory>
|
||||
#include <map>
|
||||
#include <boost/ref.hpp>
|
||||
#include <boost/type_index.hpp>
|
||||
#include <boost/smart_ptr/shared_ptr.hpp>
|
||||
#include <boost/smart_ptr/make_shared_object.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
#include <boost/log/detail/visible_type.hpp>
|
||||
#include <boost/log/utility/type_info_wrapper.hpp>
|
||||
#include <boost/log/utility/type_dispatch/type_dispatcher.hpp>
|
||||
#include <boost/log/detail/header.hpp>
|
||||
|
||||
@@ -78,7 +77,7 @@ private:
|
||||
#endif // BOOST_LOG_DOXYGEN_PASS
|
||||
|
||||
//! The dispatching map
|
||||
typedef std::map< type_info_wrapper, shared_ptr< callback_base > > dispatching_map;
|
||||
typedef std::map< typeindex::type_index, shared_ptr< callback_base > > dispatching_map;
|
||||
dispatching_map m_DispatchingMap;
|
||||
|
||||
public:
|
||||
@@ -118,7 +117,7 @@ public:
|
||||
boost::shared_ptr< callback_base > p(
|
||||
boost::make_shared< callback_impl< T, VisitorT > >(boost::cref(visitor)));
|
||||
|
||||
type_info_wrapper wrapper(typeid(aux::visible_type< T >));
|
||||
typeindex::type_index wrapper(typeindex::type_id< T >());
|
||||
m_DispatchingMap[wrapper].swap(p);
|
||||
}
|
||||
|
||||
@@ -132,11 +131,10 @@ public:
|
||||
|
||||
private:
|
||||
#ifndef BOOST_LOG_DOXYGEN_PASS
|
||||
static callback_base get_callback(type_dispatcher* p, std::type_info const& type)
|
||||
static callback_base get_callback(type_dispatcher* p, typeindex::type_index type)
|
||||
{
|
||||
dynamic_type_dispatcher* const self = static_cast< dynamic_type_dispatcher* >(p);
|
||||
type_info_wrapper wrapper(type);
|
||||
dispatching_map::iterator it = self->m_DispatchingMap.find(wrapper);
|
||||
dispatching_map::iterator it = self->m_DispatchingMap.find(type);
|
||||
if (it != self->m_DispatchingMap.end())
|
||||
return *it->second;
|
||||
else
|
||||
|
||||
@@ -21,6 +21,7 @@
|
||||
#include <algorithm>
|
||||
#include <boost/array.hpp>
|
||||
#include <boost/static_assert.hpp>
|
||||
#include <boost/type_index.hpp>
|
||||
#include <boost/mpl/if.hpp>
|
||||
#include <boost/mpl/size.hpp>
|
||||
#include <boost/mpl/begin.hpp>
|
||||
@@ -30,9 +31,7 @@
|
||||
#include <boost/mpl/is_sequence.hpp>
|
||||
#include <boost/utility/addressof.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
#include <boost/log/detail/visible_type.hpp>
|
||||
#include <boost/log/utility/once_block.hpp>
|
||||
#include <boost/log/utility/type_info_wrapper.hpp>
|
||||
#include <boost/log/utility/type_dispatch/type_dispatcher.hpp>
|
||||
#include <boost/log/detail/header.hpp>
|
||||
|
||||
@@ -50,7 +49,7 @@ namespace aux {
|
||||
struct dispatching_map_order
|
||||
{
|
||||
typedef bool result_type;
|
||||
typedef std::pair< type_info_wrapper, void* > first_argument_type, second_argument_type;
|
||||
typedef std::pair< typeindex::type_index, void* > first_argument_type, second_argument_type;
|
||||
result_type operator() (first_argument_type const& left, second_argument_type const& right) const
|
||||
{
|
||||
return (left.first < right.first);
|
||||
@@ -62,15 +61,15 @@ template< typename VisitorT >
|
||||
struct dispatching_map_initializer
|
||||
{
|
||||
template< typename IteratorT >
|
||||
static BOOST_FORCEINLINE void init(IteratorT*, IteratorT*, std::pair< type_info_wrapper, void* >*)
|
||||
static BOOST_FORCEINLINE void init(IteratorT*, IteratorT*, std::pair< typeindex::type_index, void* >*)
|
||||
{
|
||||
}
|
||||
|
||||
template< typename BeginIteratorT, typename EndIteratorT >
|
||||
static BOOST_FORCEINLINE void init(BeginIteratorT*, EndIteratorT* end, std::pair< type_info_wrapper, void* >* p)
|
||||
static BOOST_FORCEINLINE void init(BeginIteratorT*, EndIteratorT* end, std::pair< typeindex::type_index, void* >* p)
|
||||
{
|
||||
typedef typename mpl::deref< BeginIteratorT >::type type;
|
||||
do_init(static_cast< visible_type< type >* >(0), p);
|
||||
do_init(static_cast< type* >(0), p);
|
||||
|
||||
typedef typename mpl::next< BeginIteratorT >::type next_iterator_type;
|
||||
init(static_cast< next_iterator_type* >(0), end, p + 1);
|
||||
@@ -78,9 +77,9 @@ struct dispatching_map_initializer
|
||||
|
||||
private:
|
||||
template< typename T >
|
||||
static BOOST_FORCEINLINE void do_init(visible_type< T >*, std::pair< type_info_wrapper, void* >* p)
|
||||
static BOOST_FORCEINLINE void do_init(T*, std::pair< typeindex::type_index, void* >* p)
|
||||
{
|
||||
p->first = typeid(visible_type< T >);
|
||||
p->first = typeindex::type_id< T >();
|
||||
|
||||
typedef void (*trampoline_t)(void*, T const&);
|
||||
BOOST_STATIC_ASSERT_MSG(sizeof(trampoline_t) == sizeof(void*), "Boost.Log: Unsupported platform, the size of a function pointer differs from the size of a pointer");
|
||||
@@ -101,7 +100,7 @@ class type_sequence_dispatcher_base :
|
||||
{
|
||||
private:
|
||||
//! Dispatching map element type
|
||||
typedef std::pair< type_info_wrapper, void* > dispatching_map_element_type;
|
||||
typedef std::pair< typeindex::type_index, void* > dispatching_map_element_type;
|
||||
|
||||
private:
|
||||
//! Dispatching map
|
||||
@@ -123,21 +122,20 @@ protected:
|
||||
|
||||
private:
|
||||
//! The get_callback method implementation
|
||||
static callback_base get_callback(type_dispatcher* p, std::type_info const& type)
|
||||
static callback_base get_callback(type_dispatcher* p, typeindex::type_index type)
|
||||
{
|
||||
type_sequence_dispatcher_base* const self = static_cast< type_sequence_dispatcher_base* >(p);
|
||||
type_info_wrapper wrapper(type);
|
||||
const dispatching_map_element_type* begin = self->m_dispatching_map_begin;
|
||||
const dispatching_map_element_type* end = begin + self->m_dispatching_map_size;
|
||||
const dispatching_map_element_type* it = std::lower_bound
|
||||
(
|
||||
begin,
|
||||
end,
|
||||
dispatching_map_element_type(wrapper, (void*)0),
|
||||
dispatching_map_element_type(type, (void*)0),
|
||||
dispatching_map_order()
|
||||
);
|
||||
|
||||
if (it != end && it->first == wrapper)
|
||||
if (it != end && it->first == type)
|
||||
return callback_base(self->m_visitor, it->second);
|
||||
else
|
||||
return callback_base();
|
||||
@@ -160,7 +158,7 @@ public:
|
||||
private:
|
||||
//! The dispatching map
|
||||
typedef array<
|
||||
std::pair< type_info_wrapper, void* >,
|
||||
std::pair< typeindex::type_index, void* >,
|
||||
mpl::size< supported_types >::value
|
||||
> dispatching_map;
|
||||
|
||||
@@ -210,13 +208,13 @@ class single_type_dispatcher_base :
|
||||
{
|
||||
private:
|
||||
//! The type to match against
|
||||
std::type_info const& m_type;
|
||||
typeindex::type_index m_type;
|
||||
//! A callback for the supported type
|
||||
callback_base m_callback;
|
||||
|
||||
protected:
|
||||
//! Initializing constructor
|
||||
single_type_dispatcher_base(std::type_info const& type, callback_base const& callback) BOOST_NOEXCEPT :
|
||||
single_type_dispatcher_base(typeindex::type_index type, callback_base const& callback) BOOST_NOEXCEPT :
|
||||
type_dispatcher(&single_type_dispatcher_base::get_callback),
|
||||
m_type(type),
|
||||
m_callback(callback)
|
||||
@@ -225,7 +223,7 @@ protected:
|
||||
|
||||
private:
|
||||
//! The get_callback method implementation
|
||||
static callback_base get_callback(type_dispatcher* p, std::type_info const& type)
|
||||
static callback_base get_callback(type_dispatcher* p, typeindex::type_index type)
|
||||
{
|
||||
single_type_dispatcher_base* const self = static_cast< single_type_dispatcher_base* >(p);
|
||||
if (type == self->m_type)
|
||||
@@ -248,7 +246,7 @@ public:
|
||||
//! Constructor
|
||||
template< typename VisitorT >
|
||||
explicit single_type_dispatcher(VisitorT& visitor) BOOST_NOEXCEPT :
|
||||
single_type_dispatcher_base(typeid(visible_type< T >), callback_base((void*)boost::addressof(visitor), &callback_base::trampoline< VisitorT, T >))
|
||||
single_type_dispatcher_base(typeindex::type_id< T >(), callback_base((void*)boost::addressof(visitor), &callback_base::trampoline< VisitorT, T >))
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
@@ -15,10 +15,9 @@
|
||||
#ifndef BOOST_LOG_TYPE_DISPATCHER_HPP_INCLUDED_
|
||||
#define BOOST_LOG_TYPE_DISPATCHER_HPP_INCLUDED_
|
||||
|
||||
#include <typeinfo>
|
||||
#include <boost/type_index.hpp>
|
||||
#include <boost/static_assert.hpp>
|
||||
#include <boost/log/detail/config.hpp>
|
||||
#include <boost/log/detail/visible_type.hpp>
|
||||
#include <boost/utility/explicit_operator_bool.hpp>
|
||||
#include <boost/log/detail/header.hpp>
|
||||
|
||||
@@ -148,7 +147,7 @@ public:
|
||||
|
||||
protected:
|
||||
//! Pointer to the callback acquisition method
|
||||
typedef callback_base (*get_callback_impl_type)(type_dispatcher*, std::type_info const&);
|
||||
typedef callback_base (*get_callback_impl_type)(type_dispatcher*, typeindex::type_index);
|
||||
|
||||
private:
|
||||
//! Pointer to the callback acquisition method
|
||||
@@ -176,7 +175,7 @@ public:
|
||||
template< typename T >
|
||||
callback< T > get_callback()
|
||||
{
|
||||
return callback< T >((this->m_get_callback_impl)(this, typeid(boost::log::aux::visible_type< T >)));
|
||||
return callback< T >((this->m_get_callback_impl)(this, typeindex::type_id< T >()));
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -26,6 +26,12 @@
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#if defined(__GNUC__)
|
||||
#pragma message "Boost.Log: This header is deprecated, use Boost.TypeIndex instead."
|
||||
#elif defined(_MSC_VER)
|
||||
#pragma message("Boost.Log: This header is deprecated, use Boost.TypeIndex instead.")
|
||||
#endif
|
||||
|
||||
namespace boost {
|
||||
|
||||
BOOST_LOG_OPEN_NAMESPACE
|
||||
|
||||
@@ -119,8 +119,6 @@ private:
|
||||
|
||||
//! The container with elements
|
||||
node_list m_Nodes;
|
||||
//! The pointer to the beginning of the storage of the elements
|
||||
node* m_pStorage;
|
||||
//! The pointer to the end of the allocated elements within the storage
|
||||
node* m_pEnd;
|
||||
//! The pointer to the end of storage
|
||||
@@ -141,7 +139,6 @@ private:
|
||||
m_pSourceAttributes(source_attrs),
|
||||
m_pThreadAttributes(thread_attrs),
|
||||
m_pGlobalAttributes(global_attrs),
|
||||
m_pStorage(storage),
|
||||
m_pEnd(storage),
|
||||
m_pEOS(eos)
|
||||
{
|
||||
|
||||
47
src/core.cpp
47
src/core.cpp
@@ -20,11 +20,14 @@
|
||||
#include <algorithm>
|
||||
#include <boost/cstdint.hpp>
|
||||
#include <boost/assert.hpp>
|
||||
#include <boost/core/swap.hpp>
|
||||
#include <boost/filesystem/path.hpp>
|
||||
#include <boost/smart_ptr/weak_ptr.hpp>
|
||||
#include <boost/smart_ptr/shared_ptr.hpp>
|
||||
#include <boost/smart_ptr/make_shared_object.hpp>
|
||||
#include <boost/range/iterator_range_core.hpp>
|
||||
#include <boost/date_time/posix_time/posix_time_types.hpp>
|
||||
#include <boost/random/taus88.hpp>
|
||||
#include <boost/move/core.hpp>
|
||||
#include <boost/move/utility.hpp>
|
||||
#include <boost/log/core/core.hpp>
|
||||
@@ -38,6 +41,7 @@
|
||||
#include <boost/thread/exceptions.hpp>
|
||||
#include <boost/log/detail/locks.hpp>
|
||||
#include <boost/log/detail/light_rw_mutex.hpp>
|
||||
#include <boost/log/detail/thread_id.hpp>
|
||||
#endif
|
||||
#include "default_sink.hpp"
|
||||
#include "stateless_allocator.hpp"
|
||||
@@ -48,6 +52,29 @@ namespace boost {
|
||||
|
||||
BOOST_LOG_OPEN_NAMESPACE
|
||||
|
||||
namespace aux {
|
||||
|
||||
BOOST_LOG_ANONYMOUS_NAMESPACE {
|
||||
|
||||
//! Sequence shuffling algorithm. Very similar to std::random_shuffle, used for forward portability with compilers that removed it from STL.
|
||||
template< typename Iterator, typename RandomNumberGenerator >
|
||||
void random_shuffle(Iterator begin, Iterator end, RandomNumberGenerator& rng)
|
||||
{
|
||||
Iterator it = begin;
|
||||
++it;
|
||||
while (it != end)
|
||||
{
|
||||
Iterator where = begin + rng() % (it - begin + 1u);
|
||||
if (where != it)
|
||||
boost::swap(*where, *it);
|
||||
++it;
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
} // namespace aux
|
||||
|
||||
//! Private record data information, with core-specific structures
|
||||
struct record_view::private_data :
|
||||
public public_data
|
||||
@@ -209,6 +236,23 @@ public:
|
||||
{
|
||||
//! Thread-specific attribute set
|
||||
attribute_set m_thread_attributes;
|
||||
//! Random number generator for shuffling
|
||||
random::taus88 m_rng;
|
||||
|
||||
thread_data() : m_rng(get_random_seed())
|
||||
{
|
||||
}
|
||||
|
||||
private:
|
||||
//! Creates a seed for RNG
|
||||
static uint32_t get_random_seed()
|
||||
{
|
||||
uint32_t seed = static_cast< uint32_t >(posix_time::microsec_clock::universal_time().time_of_day().ticks());
|
||||
#if !defined(BOOST_LOG_NO_THREADS)
|
||||
seed += static_cast< uint32_t >(log::aux::this_thread::get_id().native_id());
|
||||
#endif
|
||||
return seed;
|
||||
}
|
||||
};
|
||||
|
||||
public:
|
||||
@@ -643,7 +687,8 @@ BOOST_LOG_API void core::push_record_move(record& rec)
|
||||
// If all sinks are busy then block on any
|
||||
if (!shuffled)
|
||||
{
|
||||
std::random_shuffle(begin, end);
|
||||
implementation::thread_data* tsd = m_impl->get_thread_data();
|
||||
log::aux::random_shuffle(begin, end, tsd->m_rng);
|
||||
shuffled = true;
|
||||
}
|
||||
|
||||
|
||||
@@ -24,16 +24,32 @@
|
||||
#include <boost/system/system_error.hpp>
|
||||
#include <boost/log/detail/event.hpp>
|
||||
|
||||
#if defined(BOOST_LOG_EVENT_USE_POSIX_SEMAPHORE)
|
||||
#if defined(BOOST_LOG_EVENT_USE_FUTEX)
|
||||
|
||||
#if defined(__GNUC__) && defined(__GCC_HAVE_SYNC_COMPARE_AND_SWAP_4)
|
||||
#define BOOST_LOG_EVENT_TRY_SET(ref) (__sync_lock_test_and_set(&ref, 1U) == 0U)
|
||||
#define BOOST_LOG_EVENT_RESET(ref) __sync_lock_release(&ref)
|
||||
#include <stddef.h>
|
||||
#include <errno.h>
|
||||
#include <sys/syscall.h>
|
||||
#include <linux/futex.h>
|
||||
#include <boost/memory_order.hpp>
|
||||
|
||||
#if defined(FUTEX_WAIT_PRIVATE)
|
||||
#define BOOST_LOG_FUTEX_WAIT FUTEX_WAIT_PRIVATE
|
||||
#else
|
||||
#error Boost.Log internal error: BOOST_LOG_EVENT_USE_POSIX_SEMAPHORE must only be defined when atomic ops are available
|
||||
#define BOOST_LOG_FUTEX_WAIT FUTEX_WAIT
|
||||
#endif
|
||||
|
||||
#if defined(FUTEX_WAKE_PRIVATE)
|
||||
#define BOOST_LOG_FUTEX_WAKE FUTEX_WAKE_PRIVATE
|
||||
#else
|
||||
#define BOOST_LOG_FUTEX_WAKE FUTEX_WAKE
|
||||
#endif
|
||||
|
||||
#elif defined(BOOST_LOG_EVENT_USE_POSIX_SEMAPHORE)
|
||||
|
||||
#include <errno.h>
|
||||
#include <semaphore.h>
|
||||
#include <boost/memory_order.hpp>
|
||||
#include <boost/atomic/fences.hpp>
|
||||
|
||||
#elif defined(BOOST_LOG_EVENT_USE_WINAPI)
|
||||
|
||||
@@ -55,10 +71,66 @@ BOOST_LOG_OPEN_NAMESPACE
|
||||
|
||||
namespace aux {
|
||||
|
||||
#if defined(BOOST_LOG_EVENT_USE_POSIX_SEMAPHORE)
|
||||
#if defined(BOOST_LOG_EVENT_USE_FUTEX)
|
||||
|
||||
//! Default constructor
|
||||
BOOST_LOG_API sem_based_event::sem_based_event() : m_state(0U)
|
||||
BOOST_LOG_API futex_based_event::futex_based_event() : m_state(0)
|
||||
{
|
||||
}
|
||||
|
||||
//! Destructor
|
||||
BOOST_LOG_API futex_based_event::~futex_based_event()
|
||||
{
|
||||
}
|
||||
|
||||
//! Waits for the object to become signalled
|
||||
BOOST_LOG_API void futex_based_event::wait()
|
||||
{
|
||||
if (m_state.exchange(0, boost::memory_order_acq_rel) == 0)
|
||||
{
|
||||
while (true)
|
||||
{
|
||||
if (::syscall(SYS_futex, &m_state.storage(), BOOST_LOG_FUTEX_WAIT, 0, NULL, NULL, 0) == 0)
|
||||
{
|
||||
// Another thread has set the event while sleeping
|
||||
break;
|
||||
}
|
||||
|
||||
const int err = errno;
|
||||
if (err == EWOULDBLOCK)
|
||||
{
|
||||
// Another thread has set the event before sleeping
|
||||
break;
|
||||
}
|
||||
else if (err != EINTR)
|
||||
{
|
||||
BOOST_THROW_EXCEPTION(system::system_error(
|
||||
err, system::system_category(), "Failed to block on the futex"));
|
||||
}
|
||||
}
|
||||
|
||||
m_state.store(0, boost::memory_order_relaxed);
|
||||
}
|
||||
}
|
||||
|
||||
//! Sets the object to a signalled state
|
||||
BOOST_LOG_API void futex_based_event::set_signalled()
|
||||
{
|
||||
if (m_state.exchange(1, boost::memory_order_release) == 0)
|
||||
{
|
||||
if (BOOST_UNLIKELY(::syscall(SYS_futex, &m_state.storage(), BOOST_LOG_FUTEX_WAKE, 1, NULL, NULL, 0) < 0))
|
||||
{
|
||||
const int err = errno;
|
||||
BOOST_THROW_EXCEPTION(system::system_error(
|
||||
err, system::system_category(), "Failed to wake threads blocked on the futex"));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#elif defined(BOOST_LOG_EVENT_USE_POSIX_SEMAPHORE)
|
||||
|
||||
//! Default constructor
|
||||
BOOST_LOG_API sem_based_event::sem_based_event() : m_state()
|
||||
{
|
||||
if (sem_init(&m_semaphore, 0, 0) != 0)
|
||||
{
|
||||
@@ -77,6 +149,7 @@ BOOST_LOG_API sem_based_event::~sem_based_event()
|
||||
//! Waits for the object to become signalled
|
||||
BOOST_LOG_API void sem_based_event::wait()
|
||||
{
|
||||
boost::atomic_thread_fence(boost::memory_order_acq_rel);
|
||||
while (true)
|
||||
{
|
||||
if (sem_wait(&m_semaphore) != 0)
|
||||
@@ -91,18 +164,17 @@ BOOST_LOG_API void sem_based_event::wait()
|
||||
else
|
||||
break;
|
||||
}
|
||||
BOOST_LOG_EVENT_RESET(m_state);
|
||||
m_state.clear(boost::memory_order_relaxed);
|
||||
}
|
||||
|
||||
//! Sets the object to a signalled state
|
||||
BOOST_LOG_API void sem_based_event::set_signalled()
|
||||
{
|
||||
if (BOOST_LOG_EVENT_TRY_SET(m_state))
|
||||
if (!m_state.test_and_set(boost::memory_order_release))
|
||||
{
|
||||
if (sem_post(&m_semaphore) != 0)
|
||||
{
|
||||
const int err = errno;
|
||||
BOOST_LOG_EVENT_RESET(m_state);
|
||||
BOOST_THROW_EXCEPTION(system::system_error(
|
||||
err, system::system_category(), "Failed to wake the blocked thread"));
|
||||
}
|
||||
|
||||
@@ -129,7 +129,7 @@ void invalid_type::throw_(const char* file, std::size_t line, std::string const&
|
||||
);
|
||||
}
|
||||
|
||||
void invalid_type::throw_(const char* file, std::size_t line, std::string const& descr, type_info_wrapper const& type)
|
||||
void invalid_type::throw_(const char* file, std::size_t line, std::string const& descr, typeindex::type_index const& type)
|
||||
{
|
||||
boost::throw_exception(boost::enable_error_info(invalid_type(descr))
|
||||
<< boost::throw_file(file)
|
||||
@@ -138,7 +138,7 @@ void invalid_type::throw_(const char* file, std::size_t line, std::string const&
|
||||
);
|
||||
}
|
||||
|
||||
void invalid_type::throw_(const char* file, std::size_t line, std::string const& descr, attribute_name const& name, type_info_wrapper const& type)
|
||||
void invalid_type::throw_(const char* file, std::size_t line, std::string const& descr, attribute_name const& name, typeindex::type_index const& type)
|
||||
{
|
||||
boost::throw_exception(boost::enable_error_info(invalid_type(descr))
|
||||
<< boost::throw_file(file)
|
||||
|
||||
@@ -16,10 +16,10 @@
|
||||
#include <map>
|
||||
#include <string>
|
||||
#include <boost/limits.hpp>
|
||||
#include <boost/type_index.hpp>
|
||||
#include <boost/log/exceptions.hpp>
|
||||
#include <boost/log/detail/snprintf.hpp>
|
||||
#include <boost/log/detail/singleton.hpp>
|
||||
#include <boost/log/utility/type_info_wrapper.hpp>
|
||||
#include <boost/log/sources/global_logger_storage.hpp>
|
||||
#if !defined(BOOST_LOG_NO_THREADS)
|
||||
#include <boost/thread/mutex.hpp>
|
||||
@@ -42,7 +42,7 @@ struct loggers_repository :
|
||||
public log::aux::lazy_singleton< loggers_repository >
|
||||
{
|
||||
//! Repository map type
|
||||
typedef std::map< type_info_wrapper, shared_ptr< logger_holder_base > > loggers_map_t;
|
||||
typedef std::map< typeindex::type_index, shared_ptr< logger_holder_base > > loggers_map_t;
|
||||
|
||||
#if !defined(BOOST_LOG_NO_THREADS)
|
||||
//! Synchronization primitive
|
||||
@@ -55,14 +55,13 @@ struct loggers_repository :
|
||||
} // namespace
|
||||
|
||||
//! Finds or creates the logger and returns its holder
|
||||
BOOST_LOG_API shared_ptr< logger_holder_base > global_storage::get_or_init(std::type_info const& key, initializer_t initializer)
|
||||
BOOST_LOG_API shared_ptr< logger_holder_base > global_storage::get_or_init(typeindex::type_index key, initializer_t initializer)
|
||||
{
|
||||
typedef loggers_repository::loggers_map_t loggers_map_t;
|
||||
loggers_repository& repo = loggers_repository::get();
|
||||
type_info_wrapper wrapped_key = key;
|
||||
|
||||
BOOST_LOG_EXPR_IF_MT(log::aux::exclusive_lock_guard< mutex > lock(repo.m_Mutex);)
|
||||
loggers_map_t::iterator it = repo.m_Loggers.find(wrapped_key);
|
||||
loggers_map_t::iterator it = repo.m_Loggers.find(key);
|
||||
if (it != repo.m_Loggers.end())
|
||||
{
|
||||
// There is an instance
|
||||
@@ -72,15 +71,15 @@ BOOST_LOG_API shared_ptr< logger_holder_base > global_storage::get_or_init(std::
|
||||
{
|
||||
// We have to create a logger instance
|
||||
shared_ptr< logger_holder_base > inst = initializer();
|
||||
repo.m_Loggers[wrapped_key] = inst;
|
||||
repo.m_Loggers[key] = inst;
|
||||
return inst;
|
||||
}
|
||||
}
|
||||
|
||||
//! Throws the \c odr_violation exception
|
||||
BOOST_LOG_API BOOST_LOG_NORETURN void throw_odr_violation(
|
||||
std::type_info const& tag_type,
|
||||
std::type_info const& logger_type,
|
||||
typeindex::type_index tag_type,
|
||||
typeindex::type_index logger_type,
|
||||
logger_holder_base const& registered)
|
||||
{
|
||||
char buf[std::numeric_limits< unsigned int >::digits10 + 3];
|
||||
@@ -88,11 +87,11 @@ BOOST_LOG_API BOOST_LOG_NORETURN void throw_odr_violation(
|
||||
buf[0] = '\0';
|
||||
std::string str =
|
||||
std::string("Could not initialize global logger with tag \"") +
|
||||
type_info_wrapper(tag_type).pretty_name() +
|
||||
tag_type.pretty_name() +
|
||||
"\" and type \"" +
|
||||
type_info_wrapper(logger_type).pretty_name() +
|
||||
logger_type.pretty_name() +
|
||||
"\". A logger of type \"" +
|
||||
type_info_wrapper(registered.logger_type()).pretty_name() +
|
||||
registered.m_LoggerType.pretty_name() +
|
||||
"\" with the same tag has already been registered at " +
|
||||
registered.m_RegistrationFile + ":" + buf + ".";
|
||||
|
||||
|
||||
@@ -16,6 +16,7 @@
|
||||
#include <memory>
|
||||
#include <utility>
|
||||
#include <algorithm>
|
||||
#include <boost/type_index.hpp>
|
||||
#include <boost/optional/optional.hpp>
|
||||
#include <boost/log/attributes/attribute.hpp>
|
||||
#include <boost/log/attributes/attribute_value.hpp>
|
||||
@@ -105,7 +106,7 @@ BOOST_LOG_ANONYMOUS_NAMESPACE {
|
||||
/*!
|
||||
* \return The attribute value type
|
||||
*/
|
||||
type_info_wrapper get_type() const { return type_info_wrapper(typeid(scope_stack)); }
|
||||
typeindex::type_index get_type() const { return typeindex::type_id< scope_stack >(); }
|
||||
|
||||
//! The method is called when the attribute value is passed to another thread (e.g.
|
||||
//! in case of asynchronous logging). The value should ensure it properly owns all thread-specific data.
|
||||
|
||||
@@ -203,7 +203,7 @@ BOOST_LOG_API get_tick_count_t get_tick_count = &get_tick_count_init;
|
||||
#endif // _WIN32_WINNT >= 0x0600
|
||||
|
||||
#elif (defined(_POSIX_TIMERS) && _POSIX_TIMERS > 0) /* POSIX timers supported */ \
|
||||
|| defined(__GNU__) /* GNU Hurd does not support POSIX timers fully but does provide clock_gettime() */
|
||||
|| defined(__GNU__) || defined(__OpenBSD__) /* GNU Hurd and OpenBSD don't support POSIX timers fully but do provide clock_gettime() */
|
||||
|
||||
BOOST_LOG_API int64_t duration::milliseconds() const
|
||||
{
|
||||
|
||||
@@ -28,6 +28,7 @@ project
|
||||
<toolset>msvc:<cxxflags>/wd4503 # decorated name length exceeded, name was truncated
|
||||
<toolset>msvc:<cxxflags>/wd4456 # declaration of 'A' hides previous local declaration
|
||||
<toolset>msvc:<cxxflags>/wd4459 # declaration of 'A' hides global declaration
|
||||
<toolset>msvc:<cxxflags>/wd4003 # not enough actual parameters for macro 'X' - caused by BOOST_PP_IS_EMPTY and BOOST_PP_IS_BEGIN_PARENS which are used by Fusion
|
||||
|
||||
# Disable Intel warnings:
|
||||
# warning #177: function "X" was declared but never referenced
|
||||
|
||||
@@ -41,7 +41,7 @@
|
||||
enum config
|
||||
{
|
||||
RECORD_COUNT = 50000000,
|
||||
THREAD_COUNT = 3,
|
||||
THREAD_COUNT = 8,
|
||||
SINK_COUNT = 3
|
||||
};
|
||||
|
||||
@@ -104,7 +104,7 @@ int main(int argc, char* argv[])
|
||||
// logging::core::get()->set_filter(severity > normal); // all records pass the filter
|
||||
// logging::core::get()->set_filter(severity > error); // all records don't pass the filter
|
||||
|
||||
logging::core::get()->set_filter(severity > error); // all records don't pass the filter
|
||||
// logging::core::get()->set_filter(severity > error); // all records don't pass the filter
|
||||
|
||||
const unsigned int record_count = RECORD_COUNT / THREAD_COUNT;
|
||||
boost::barrier bar(THREAD_COUNT);
|
||||
|
||||
98
test/run/form_to_log_manip.cpp
Normal file
98
test/run/form_to_log_manip.cpp
Normal file
@@ -0,0 +1,98 @@
|
||||
/*
|
||||
* Copyright Andrey Semashev 2007 - 2015.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
/*!
|
||||
* \file form_to_log_manip.cpp
|
||||
* \author Andrey Semashev
|
||||
* \date 05.07.2015
|
||||
*
|
||||
* \brief This header contains tests for support for the \c to_log_manip customization point.
|
||||
*/
|
||||
|
||||
#define BOOST_TEST_MODULE form_to_log_manip
|
||||
|
||||
#include <string>
|
||||
#include <ostream>
|
||||
#include <algorithm>
|
||||
#include <boost/test/unit_test.hpp>
|
||||
#include <boost/log/attributes/constant.hpp>
|
||||
#include <boost/log/attributes/attribute_set.hpp>
|
||||
#include <boost/log/utility/formatting_ostream.hpp>
|
||||
#include <boost/log/utility/manipulators/to_log.hpp>
|
||||
#include <boost/log/expressions.hpp>
|
||||
#include <boost/log/core/record.hpp>
|
||||
#include "char_definitions.hpp"
|
||||
#include "make_record.hpp"
|
||||
|
||||
namespace logging = boost::log;
|
||||
namespace attrs = logging::attributes;
|
||||
namespace expr = logging::expressions;
|
||||
|
||||
namespace {
|
||||
|
||||
struct my_class
|
||||
{
|
||||
int m_Data;
|
||||
|
||||
explicit my_class(int data) : m_Data(data) {}
|
||||
};
|
||||
|
||||
} // namespace
|
||||
|
||||
BOOST_LOG_ATTRIBUTE_KEYWORD(a_my_class, "MyClass", my_class)
|
||||
BOOST_LOG_ATTRIBUTE_KEYWORD(a_string, "String", std::string)
|
||||
|
||||
namespace {
|
||||
|
||||
template< typename CharT, typename TraitsT, typename AllocatorT >
|
||||
inline logging::basic_formatting_ostream< CharT, TraitsT, AllocatorT >&
|
||||
operator<< (logging::basic_formatting_ostream< CharT, TraitsT, AllocatorT >& strm, logging::to_log_manip< my_class, tag::a_my_class > const& obj)
|
||||
{
|
||||
strm << "a_my_class: [data: " << obj.get().m_Data << "]";
|
||||
return strm;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
namespace std {
|
||||
|
||||
template< typename CharT, typename TraitsT, typename AllocatorT >
|
||||
inline logging::basic_formatting_ostream< CharT, TraitsT, AllocatorT >&
|
||||
operator<< (logging::basic_formatting_ostream< CharT, TraitsT, AllocatorT >& strm, logging::to_log_manip< std::string, tag::a_string > const& obj)
|
||||
{
|
||||
strm << "a_string: [" << obj.get() << "]";
|
||||
return strm;
|
||||
}
|
||||
|
||||
} // namespace std
|
||||
|
||||
BOOST_AUTO_TEST_CASE_TEMPLATE(operator_overrides, CharT, char_types)
|
||||
{
|
||||
typedef logging::record_view record_view;
|
||||
typedef logging::attribute_set attr_set;
|
||||
typedef std::basic_string< CharT > string;
|
||||
typedef logging::basic_formatting_ostream< CharT > osstream;
|
||||
typedef logging::basic_formatter< CharT > formatter;
|
||||
|
||||
attrs::constant< my_class > attr1(my_class(77));
|
||||
attrs::constant< std::string > attr2("Hello");
|
||||
|
||||
attr_set set1;
|
||||
set1[a_my_class.get_name()] = attr1;
|
||||
set1[a_string.get_name()] = attr2;
|
||||
|
||||
record_view rec = make_record_view(set1);
|
||||
|
||||
// Check that out custom operators are called
|
||||
{
|
||||
string str1, str2;
|
||||
osstream strm1(str1), strm2(str2);
|
||||
formatter f = expr::stream << a_my_class << ", " << a_string;
|
||||
f(rec, strm1);
|
||||
strm2 << "a_my_class: [data: " << 77 << "], a_string: [" << "Hello" << "]";
|
||||
BOOST_CHECK(equal_strings(strm1.str(), strm2.str()));
|
||||
}
|
||||
}
|
||||
134
test/run/util_manip_to_log.cpp
Normal file
134
test/run/util_manip_to_log.cpp
Normal file
@@ -0,0 +1,134 @@
|
||||
/*
|
||||
* Copyright Andrey Semashev 2007 - 2015.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
/*!
|
||||
* \file util_manip_to_log.cpp
|
||||
* \author Andrey Semashev
|
||||
* \date 05.07.2015
|
||||
*
|
||||
* \brief This header contains tests for the \c to_log stream manipulator.
|
||||
*/
|
||||
|
||||
#define BOOST_TEST_MODULE util_manip_to_log
|
||||
|
||||
#include <string>
|
||||
#include <sstream>
|
||||
#include <algorithm>
|
||||
#include <boost/test/unit_test.hpp>
|
||||
#include <boost/log/utility/formatting_ostream.hpp>
|
||||
#include <boost/log/utility/manipulators/to_log.hpp>
|
||||
#include "char_definitions.hpp"
|
||||
|
||||
namespace logging = boost::log;
|
||||
|
||||
namespace tag {
|
||||
|
||||
struct a_my_class;
|
||||
|
||||
} // namespace tag
|
||||
|
||||
namespace {
|
||||
|
||||
struct my_class
|
||||
{
|
||||
int m_Data;
|
||||
|
||||
explicit my_class(int data) : m_Data(data) {}
|
||||
};
|
||||
|
||||
template< typename CharT, typename TraitsT >
|
||||
inline std::basic_ostream< CharT, TraitsT >&
|
||||
operator<< (std::basic_ostream< CharT, TraitsT >& strm, my_class const& obj)
|
||||
{
|
||||
strm << "my_class: [data: " << obj.m_Data << "]";
|
||||
return strm;
|
||||
}
|
||||
|
||||
template< typename StreamT >
|
||||
inline StreamT&
|
||||
operator<< (StreamT& strm, logging::to_log_manip< my_class > const& obj)
|
||||
{
|
||||
strm << "to_log(my_class: [data: " << obj.get().m_Data << "])";
|
||||
return strm;
|
||||
}
|
||||
|
||||
template< typename StreamT >
|
||||
inline StreamT&
|
||||
operator<< (StreamT& strm, logging::to_log_manip< my_class, tag::a_my_class > const& obj)
|
||||
{
|
||||
strm << "to_log<a_my_class>(my_class: [data: " << obj.get().m_Data << "])";
|
||||
return strm;
|
||||
}
|
||||
|
||||
template< typename CharT, typename StreamT >
|
||||
struct tests
|
||||
{
|
||||
typedef CharT char_type;
|
||||
typedef StreamT stream_type;
|
||||
typedef std::basic_string< char_type > string;
|
||||
typedef std::basic_ostringstream< char_type > std_stream;
|
||||
|
||||
//! The test verifies that the default behavior of the manipulator is equivalent to the standard operator<<
|
||||
static void default_operator()
|
||||
{
|
||||
string str;
|
||||
stream_type strm1(str);
|
||||
strm1 << logging::to_log(10);
|
||||
|
||||
std_stream strm2;
|
||||
strm2 << 10;
|
||||
BOOST_CHECK(equal_strings(strm1.str(), strm2.str()));
|
||||
}
|
||||
|
||||
//! The test verifies that operator overrides work
|
||||
static void operator_overrides()
|
||||
{
|
||||
{
|
||||
string str;
|
||||
stream_type strm1(str);
|
||||
strm1 << my_class(10);
|
||||
|
||||
std_stream strm2;
|
||||
strm2 << "my_class: [data: " << 10 << "]";
|
||||
BOOST_CHECK(equal_strings(strm1.str(), strm2.str()));
|
||||
}
|
||||
{
|
||||
string str;
|
||||
stream_type strm1(str);
|
||||
strm1 << logging::to_log(my_class(10));
|
||||
|
||||
std_stream strm2;
|
||||
strm2 << "to_log(my_class: [data: " << 10 << "])";
|
||||
BOOST_CHECK(equal_strings(strm1.str(), strm2.str()));
|
||||
}
|
||||
{
|
||||
string str;
|
||||
stream_type strm1(str);
|
||||
strm1 << logging::to_log< tag::a_my_class >(my_class(10));
|
||||
|
||||
std_stream strm2;
|
||||
strm2 << "to_log<a_my_class>(my_class: [data: " << 10 << "])";
|
||||
BOOST_CHECK(equal_strings(strm1.str(), strm2.str()));
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace
|
||||
|
||||
|
||||
//! The test verifies that the default behavior of the manipulator is equivalent to the standard operator<<
|
||||
BOOST_AUTO_TEST_CASE_TEMPLATE(default_operator, CharT, char_types)
|
||||
{
|
||||
tests< CharT, std::basic_ostringstream< CharT > >::default_operator();
|
||||
tests< CharT, logging::basic_formatting_ostream< CharT > >::default_operator();
|
||||
}
|
||||
|
||||
//! The test verifies that operator overrides work
|
||||
BOOST_AUTO_TEST_CASE_TEMPLATE(operator_overrides, CharT, char_types)
|
||||
{
|
||||
tests< CharT, std::basic_ostringstream< CharT > >::operator_overrides();
|
||||
tests< CharT, logging::basic_formatting_ostream< CharT > >::operator_overrides();
|
||||
}
|
||||
Reference in New Issue
Block a user