From d966de437e385f456c000695a6cbe028c7f0f243 Mon Sep 17 00:00:00 2001 From: Peter Dimov Date: Fri, 21 Sep 2018 20:51:24 +0300 Subject: [PATCH 1/9] Update and collapse Appveyor configurations --- appveyor.yml | 39 +++++++++++---------------------------- 1 file changed, 11 insertions(+), 28 deletions(-) diff --git a/appveyor.yml b/appveyor.yml index d350318..2e8c6dd 100644 --- a/appveyor.yml +++ b/appveyor.yml @@ -1,4 +1,4 @@ -# Copyright 2016, 2017 Peter Dimov +# Copyright 2016-2018 Peter Dimov # Distributed under the Boost Software License, Version 1.0. # (See accompanying file LICENSE_1_0.txt or copy at http://boost.org/LICENSE_1_0.txt) @@ -15,48 +15,30 @@ branches: environment: matrix: - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2013 - TOOLSET: msvc-9.0 - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2013 - TOOLSET: msvc-10.0 - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2013 - TOOLSET: msvc-11.0 - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2013 - TOOLSET: msvc-12.0 + TOOLSET: msvc-9.0,msvc-10.0,msvc-11.0,msvc-12.0 - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2015 TOOLSET: msvc-14.0 + ADDRMD: 32,64 - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2017 TOOLSET: msvc-14.1 - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2017 - TOOLSET: msvc-14.1 - CXXSTD: 17 + CXXSTD: 14,17 + ADDRMD: 32,64 - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2013 ADDPATH: C:\cygwin\bin; TOOLSET: gcc - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2013 - ADDPATH: C:\cygwin\bin; - TOOLSET: gcc - CXXSTD: 03,11 + CXXSTD: 03,11,14,1z - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2013 ADDPATH: C:\cygwin64\bin; TOOLSET: gcc - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2013 - ADDPATH: C:\cygwin64\bin; - TOOLSET: gcc - CXXSTD: 03,11 + CXXSTD: 03,11,14,1z - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2013 ADDPATH: C:\mingw\bin; TOOLSET: gcc - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2013 - ADDPATH: C:\mingw\bin; - TOOLSET: gcc - CXXSTD: 03,11 + CXXSTD: 03,11,14,1z - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2013 ADDPATH: C:\mingw-w64\x86_64-6.3.0-posix-seh-rt_v5-rev1\mingw64\bin; TOOLSET: gcc - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2013 - ADDPATH: C:\mingw-w64\x86_64-6.3.0-posix-seh-rt_v5-rev1\mingw64\bin; - TOOLSET: gcc - CXXSTD: 03,11 + CXXSTD: 03,11,14,1z install: - set BOOST_BRANCH=develop @@ -77,4 +59,5 @@ build: off test_script: - PATH=%ADDPATH%%PATH% - if not "%CXXSTD%" == "" set CXXSTD=cxxstd=%CXXSTD% - - b2 -j3 libs/system/test toolset=%TOOLSET% variant=debug,release %CXXSTD% + - if not "%ADDRMD%" == "" set ADDRMD=address-model=%ADDRMD% + - b2 -j3 libs/system/test toolset=%TOOLSET% %CXXSTD% %ADDRMD% variant=debug,release From a627662e6358d5acbf3fece16d350dec5a5e55dc Mon Sep 17 00:00:00 2001 From: Peter Dimov Date: Sat, 22 Sep 2018 15:17:47 +0300 Subject: [PATCH 2/9] Add after_main_test --- test/Jamfile.v2 | 1 + test/after_main_test.cpp | 26 ++++++++++++++++++++++++++ test/after_main_test_1.cpp | 9 +++++++++ test/after_main_test_2.cpp | 10 ++++++++++ 4 files changed, 46 insertions(+) create mode 100644 test/after_main_test.cpp create mode 100644 test/after_main_test_1.cpp create mode 100644 test/after_main_test_2.cpp diff --git a/test/Jamfile.v2 b/test/Jamfile.v2 index 7fbff70..7e5bddd 100644 --- a/test/Jamfile.v2 +++ b/test/Jamfile.v2 @@ -126,6 +126,7 @@ system-run win32_hresult_test.cpp ; system-run error_category_test.cpp ; system-run generic_category_test.cpp ; system-run system_category_test.cpp ; +system-run after_main_test.cpp after_main_test_1.cpp after_main_test_2.cpp ; # Quick (CI) test run quick.cpp ; diff --git a/test/after_main_test.cpp b/test/after_main_test.cpp new file mode 100644 index 0000000..79fc5b4 --- /dev/null +++ b/test/after_main_test.cpp @@ -0,0 +1,26 @@ + +// Copyright 2018 Peter Dimov. +// Distributed under the Boost Software License, Version 1.0. + +#include +#include +#include + +using namespace boost::system; + +struct Z +{ + ~Z() + { + BOOST_TEST_CSTR_EQ( generic_category().name(), "generic" ); + BOOST_TEST_CSTR_EQ( system_category().name(), "system" ); + + boost::quick_exit( boost::report_errors() ); + } +}; + +static Z z; + +int main() +{ +} diff --git a/test/after_main_test_1.cpp b/test/after_main_test_1.cpp new file mode 100644 index 0000000..5b9f728 --- /dev/null +++ b/test/after_main_test_1.cpp @@ -0,0 +1,9 @@ + +// Copyright 2018 Peter Dimov. +// Distributed under the Boost Software License, Version 1.0. + +#include + +using namespace boost::system; + +static error_code e1( 1, system_category() ); diff --git a/test/after_main_test_2.cpp b/test/after_main_test_2.cpp new file mode 100644 index 0000000..7da78e6 --- /dev/null +++ b/test/after_main_test_2.cpp @@ -0,0 +1,10 @@ + +// Copyright 2018 Peter Dimov. +// Distributed under the Boost Software License, Version 1.0. + +#include +#include + +using namespace boost::system; + +static error_code e2( ENOENT, generic_category() ); From 08dc402e77e32f7b69debd31949a72bc864e96e6 Mon Sep 17 00:00:00 2001 From: Peter Dimov Date: Sat, 22 Sep 2018 15:40:19 +0300 Subject: [PATCH 3/9] Simplify after_main_test --- test/Jamfile.v2 | 2 +- test/after_main_test.cpp | 4 ++++ test/after_main_test_1.cpp | 9 --------- test/after_main_test_2.cpp | 10 ---------- 4 files changed, 5 insertions(+), 20 deletions(-) delete mode 100644 test/after_main_test_1.cpp delete mode 100644 test/after_main_test_2.cpp diff --git a/test/Jamfile.v2 b/test/Jamfile.v2 index 7e5bddd..03ef7c4 100644 --- a/test/Jamfile.v2 +++ b/test/Jamfile.v2 @@ -126,7 +126,7 @@ system-run win32_hresult_test.cpp ; system-run error_category_test.cpp ; system-run generic_category_test.cpp ; system-run system_category_test.cpp ; -system-run after_main_test.cpp after_main_test_1.cpp after_main_test_2.cpp ; +system-run after_main_test.cpp ; # Quick (CI) test run quick.cpp ; diff --git a/test/after_main_test.cpp b/test/after_main_test.cpp index 79fc5b4..520f807 100644 --- a/test/after_main_test.cpp +++ b/test/after_main_test.cpp @@ -5,6 +5,7 @@ #include #include #include +#include using namespace boost::system; @@ -21,6 +22,9 @@ struct Z static Z z; +static error_code e1( 1, system_category() ); +static error_code e2( ENOENT, generic_category() ); + int main() { } diff --git a/test/after_main_test_1.cpp b/test/after_main_test_1.cpp deleted file mode 100644 index 5b9f728..0000000 --- a/test/after_main_test_1.cpp +++ /dev/null @@ -1,9 +0,0 @@ - -// Copyright 2018 Peter Dimov. -// Distributed under the Boost Software License, Version 1.0. - -#include - -using namespace boost::system; - -static error_code e1( 1, system_category() ); diff --git a/test/after_main_test_2.cpp b/test/after_main_test_2.cpp deleted file mode 100644 index 7da78e6..0000000 --- a/test/after_main_test_2.cpp +++ /dev/null @@ -1,10 +0,0 @@ - -// Copyright 2018 Peter Dimov. -// Distributed under the Boost Software License, Version 1.0. - -#include -#include - -using namespace boost::system; - -static error_code e2( ENOENT, generic_category() ); From 349fb30e8e3f381d4e79732f85095ea2bb8ba8db Mon Sep 17 00:00:00 2001 From: Peter Dimov Date: Sat, 22 Sep 2018 16:15:49 +0300 Subject: [PATCH 4/9] Remove the user-provided ~error_category in C++03 mode, to fix use after main --- include/boost/system/error_code.hpp | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/include/boost/system/error_code.hpp b/include/boost/system/error_code.hpp index a740dfd..7d68e11 100644 --- a/include/boost/system/error_code.hpp +++ b/include/boost/system/error_code.hpp @@ -196,9 +196,12 @@ protected: #else - ~error_category() - { - } + // We'd like to make the destructor protected, to make code that deletes + // an error_category* not compile; unfortunately, doing the below makes + // the destructor user-provided and hence breaks use after main, as the + // categories may get destroyed before code that uses them + + // ~error_category() {} #endif From f48cc5aec668ce716466f03baba9a39bc44956d3 Mon Sep 17 00:00:00 2001 From: Peter Dimov Date: Sat, 22 Sep 2018 17:34:40 +0300 Subject: [PATCH 5/9] Add failed() --- include/boost/system/error_code.hpp | 122 +++++++++++++------ test/Jamfile.v2 | 1 + test/failed_test.cpp | 179 ++++++++++++++++++++++++++++ 3 files changed, 267 insertions(+), 35 deletions(-) create mode 100644 test/failed_test.cpp diff --git a/include/boost/system/error_code.hpp b/include/boost/system/error_code.hpp index 7d68e11..99d23a1 100644 --- a/include/boost/system/error_code.hpp +++ b/include/boost/system/error_code.hpp @@ -224,6 +224,8 @@ public: virtual std::string message( int ev ) const = 0; virtual char const * message( int ev, char * buffer, std::size_t len ) const BOOST_NOEXCEPT; + virtual bool failed( int ev ) const BOOST_NOEXCEPT; + BOOST_SYSTEM_CONSTEXPR bool operator==( const error_category & rhs ) const BOOST_NOEXCEPT { return rhs.id_ == 0? this == &rhs: id_ == rhs.id_; @@ -381,6 +383,31 @@ template struct enable_if { }; +// failed_impl + +#if defined(BOOST_SYSTEM_HAS_CONSTEXPR) + +BOOST_SYSTEM_CONSTEXPR inline bool failed_impl( int ev, error_category const & cat ) +{ + if( cat == system_category() || cat == generic_category() ) + { + return ev != 0; + } + else + { + return cat.failed( ev ); + } +} + +#else + +inline bool failed_impl( int ev, error_category const & cat ) +{ + return cat.failed( ev ); +} + +#endif + } // namespace detail // class error_condition @@ -391,18 +418,21 @@ class error_condition { private: - int m_val; - error_category const * m_cat; + int val_; + bool failed_; + error_category const * cat_; public: // constructors: - BOOST_SYSTEM_CONSTEXPR error_condition() BOOST_NOEXCEPT: m_val( 0 ), m_cat( &generic_category() ) + BOOST_SYSTEM_CONSTEXPR error_condition() BOOST_NOEXCEPT: + val_( 0 ), failed_( false ), cat_( &generic_category() ) { } - BOOST_SYSTEM_CONSTEXPR error_condition( int val, const error_category & cat ) BOOST_NOEXCEPT: m_val( val ), m_cat( &cat ) + BOOST_SYSTEM_CONSTEXPR error_condition( int val, const error_category & cat ) BOOST_NOEXCEPT: + val_( val ), failed_( detail::failed_impl( val, cat ) ), cat_( &cat ) { } @@ -416,8 +446,9 @@ public: BOOST_SYSTEM_CONSTEXPR void assign( int val, const error_category & cat ) BOOST_NOEXCEPT { - m_val = val; - m_cat = &cat; + val_ = val; + failed_ = detail::failed_impl( val, cat ); + cat_ = &cat; } template @@ -430,37 +461,43 @@ public: BOOST_SYSTEM_CONSTEXPR void clear() BOOST_NOEXCEPT { - m_val = 0; - m_cat = &generic_category(); + val_ = 0; + failed_ = false; + cat_ = &generic_category(); } // observers: BOOST_SYSTEM_CONSTEXPR int value() const BOOST_NOEXCEPT { - return m_val; + return val_; } BOOST_SYSTEM_CONSTEXPR const error_category & category() const BOOST_NOEXCEPT { - return *m_cat; + return *cat_; } std::string message() const { - return m_cat->message( value() ); + return cat_->message( value() ); } char const * message( char * buffer, std::size_t len ) const BOOST_NOEXCEPT { - return m_cat->message( value(), buffer, len ); + return cat_->message( value(), buffer, len ); + } + + BOOST_SYSTEM_CONSTEXPR bool failed() const BOOST_NOEXCEPT + { + return failed_; } #if !defined(BOOST_NO_CXX11_EXPLICIT_CONVERSION_OPERATORS) BOOST_SYSTEM_CONSTEXPR explicit operator bool() const BOOST_NOEXCEPT // true if error { - return m_val != 0; + return failed_; } #else @@ -470,12 +507,12 @@ public: BOOST_SYSTEM_CONSTEXPR operator unspecified_bool_type() const BOOST_NOEXCEPT // true if error { - return m_val == 0? 0 : unspecified_bool_true; + return failed_? unspecified_bool_true: 0; } BOOST_SYSTEM_CONSTEXPR bool operator!() const BOOST_NOEXCEPT // true if no error { - return m_val == 0; + return !failed_; } #endif @@ -486,12 +523,12 @@ public: BOOST_SYSTEM_CONSTEXPR inline friend bool operator==( const error_condition & lhs, const error_condition & rhs ) BOOST_NOEXCEPT { - return lhs.m_val == rhs.m_val && *lhs.m_cat == *rhs.m_cat; + return lhs.val_ == rhs.val_ && *lhs.cat_ == *rhs.cat_; } BOOST_SYSTEM_CONSTEXPR inline friend bool operator<( const error_condition & lhs, const error_condition & rhs ) BOOST_NOEXCEPT { - return *lhs.m_cat < *rhs.m_cat || ( *lhs.m_cat == *rhs.m_cat && lhs.m_val < rhs.m_val ); + return *lhs.cat_ < *rhs.cat_ || ( *lhs.cat_ == *rhs.cat_ && lhs.val_ < rhs.val_ ); } #if defined(BOOST_SYSTEM_HAS_SYSTEM_ERROR) @@ -517,18 +554,21 @@ class error_code { private: - int m_val; - const error_category * m_cat; + int val_; + bool failed_; + const error_category * cat_; public: // constructors: - BOOST_SYSTEM_CONSTEXPR error_code() BOOST_NOEXCEPT: m_val( 0 ), m_cat( &system_category() ) + BOOST_SYSTEM_CONSTEXPR error_code() BOOST_NOEXCEPT: + val_( 0 ), failed_( false ), cat_( &system_category() ) { } - BOOST_SYSTEM_CONSTEXPR error_code( int val, const error_category & cat ) BOOST_NOEXCEPT: m_val( val ), m_cat( &cat ) + BOOST_SYSTEM_CONSTEXPR error_code( int val, const error_category & cat ) BOOST_NOEXCEPT: + val_( val ), failed_( detail::failed_impl( val, cat ) ), cat_( &cat ) { } @@ -542,8 +582,9 @@ public: BOOST_SYSTEM_CONSTEXPR void assign( int val, const error_category & cat ) BOOST_NOEXCEPT { - m_val = val; - m_cat = &cat; + val_ = val; + failed_ = detail::failed_impl( val, cat ); + cat_ = &cat; } template @@ -556,42 +597,48 @@ public: BOOST_SYSTEM_CONSTEXPR void clear() BOOST_NOEXCEPT { - m_val = 0; - m_cat = &system_category(); + val_ = 0; + failed_ = false; + cat_ = &system_category(); } // observers: BOOST_SYSTEM_CONSTEXPR int value() const BOOST_NOEXCEPT { - return m_val; + return val_; } BOOST_SYSTEM_CONSTEXPR const error_category & category() const BOOST_NOEXCEPT { - return *m_cat; + return *cat_; } error_condition default_error_condition() const BOOST_NOEXCEPT { - return m_cat->default_error_condition( value() ); + return cat_->default_error_condition( value() ); } std::string message() const { - return m_cat->message( value() ); + return cat_->message( value() ); } char const * message( char * buffer, std::size_t len ) const BOOST_NOEXCEPT { - return m_cat->message( value(), buffer, len ); + return cat_->message( value(), buffer, len ); + } + + BOOST_SYSTEM_CONSTEXPR bool failed() const BOOST_NOEXCEPT + { + return failed_; } #if !defined(BOOST_NO_CXX11_EXPLICIT_CONVERSION_OPERATORS) BOOST_SYSTEM_CONSTEXPR explicit operator bool() const BOOST_NOEXCEPT // true if error { - return m_val != 0; + return failed_; } #else @@ -601,12 +648,12 @@ public: BOOST_SYSTEM_CONSTEXPR operator unspecified_bool_type() const BOOST_NOEXCEPT // true if error { - return m_val == 0? 0 : unspecified_bool_true; + return failed_? unspecified_bool_true: 0; } BOOST_SYSTEM_CONSTEXPR bool operator!() const BOOST_NOEXCEPT // true if no error { - return m_val == 0; + return !failed_; } #endif @@ -618,12 +665,12 @@ public: BOOST_SYSTEM_CONSTEXPR inline friend bool operator==( const error_code & lhs, const error_code & rhs ) BOOST_NOEXCEPT { - return lhs.m_val == rhs.m_val && *lhs.m_cat == *rhs.m_cat; + return lhs.val_ == rhs.val_ && *lhs.cat_ == *rhs.cat_; } BOOST_SYSTEM_CONSTEXPR inline friend bool operator<( const error_code & lhs, const error_code & rhs ) BOOST_NOEXCEPT { - return *lhs.m_cat < *rhs.m_cat || ( *lhs.m_cat == *rhs.m_cat && lhs.m_val < rhs.m_val ); + return *lhs.cat_ < *rhs.cat_ || ( *lhs.cat_ == *rhs.cat_ && lhs.val_ < rhs.val_ ); } #if defined(BOOST_SYSTEM_HAS_SYSTEM_ERROR) @@ -819,6 +866,11 @@ inline char const * error_category::message( int ev, char * buffer, std::size_t #endif } +inline bool error_category::failed( int ev ) const BOOST_NOEXCEPT +{ + return ev != 0; +} + } // namespace system } // namespace boost diff --git a/test/Jamfile.v2 b/test/Jamfile.v2 index 03ef7c4..cea6d10 100644 --- a/test/Jamfile.v2 +++ b/test/Jamfile.v2 @@ -127,6 +127,7 @@ system-run error_category_test.cpp ; system-run generic_category_test.cpp ; system-run system_category_test.cpp ; system-run after_main_test.cpp ; +system-run failed_test.cpp ; # Quick (CI) test run quick.cpp ; diff --git a/test/failed_test.cpp b/test/failed_test.cpp new file mode 100644 index 0000000..67a317d --- /dev/null +++ b/test/failed_test.cpp @@ -0,0 +1,179 @@ + +// Copyright 2018 Peter Dimov. +// Distributed under the Boost Software License, Version 1.0. + +// Avoid spurious VC++ warnings +#define _CRT_SECURE_NO_WARNINGS + +#include +#include +#include + +using namespace boost::system; + +struct http_category_impl: public error_category +{ + char const * name() const BOOST_NOEXCEPT + { + return "http"; + } + + std::string message( int ev ) const + { + char buffer[ 32 ]; + + std::sprintf( buffer, "HTTP/1.0 %d", ev ); + return buffer; + } + + bool failed( int ev ) const BOOST_NOEXCEPT + { + return !( ev >= 200 && ev < 300 ); + } +}; + +error_category const & http_category() +{ + static const http_category_impl instance; + return instance; +} + +#define TEST_NOT_FAILED(ec) BOOST_TEST( !ec.failed() ); BOOST_TEST( ec? false: true ); BOOST_TEST( !ec ); +#define TEST_FAILED(ec) BOOST_TEST( ec.failed() ); BOOST_TEST( ec ); BOOST_TEST( !!ec ); + +template void test() +{ + { + Ec ec; + TEST_NOT_FAILED( ec ); + + ec.assign( 1, generic_category() ); + TEST_FAILED( ec ); + + ec.clear(); + TEST_NOT_FAILED( ec ); + + ec = Ec( 1, generic_category() ); + TEST_FAILED( ec ); + + ec = Ec(); + TEST_NOT_FAILED( ec ); + } + + { + Ec ec; + TEST_NOT_FAILED( ec ); + + ec.assign( 1, system_category() ); + TEST_FAILED( ec ); + + ec.clear(); + TEST_NOT_FAILED( ec ); + + ec = Ec( 1, system_category() ); + TEST_FAILED( ec ); + + ec = Ec(); + TEST_NOT_FAILED( ec ); + } + + { + Ec ec( 0, generic_category() ); + TEST_NOT_FAILED( ec ); + + ec.assign( 1, system_category() ); + TEST_FAILED( ec ); + + ec = Ec( 0, system_category() ); + TEST_NOT_FAILED( ec ); + } + + { + Ec ec( 1, generic_category() ); + TEST_FAILED( ec ); + + ec.assign( 0, system_category() ); + TEST_NOT_FAILED( ec ); + } + + { + Ec ec( 0, system_category() ); + TEST_NOT_FAILED( ec ); + + ec.assign( 1, generic_category() ); + TEST_FAILED( ec ); + + ec = Ec( 0, generic_category() ); + TEST_NOT_FAILED( ec ); + } + + { + Ec ec( 1, system_category() ); + TEST_FAILED( ec ); + + ec.assign( 0, generic_category() ); + TEST_NOT_FAILED( ec ); + } + + { + Ec ec( 0, http_category() ); + TEST_FAILED( ec ); + + ec.assign( 200, http_category() ); + TEST_NOT_FAILED( ec ); + + ec = Ec( 404, http_category() ); + TEST_FAILED( ec ); + } + +} + +int main() +{ + BOOST_TEST( !generic_category().failed( 0 ) ); + BOOST_TEST( generic_category().failed( 7 ) ); + + BOOST_TEST( !system_category().failed( 0 ) ); + BOOST_TEST( system_category().failed( 7 ) ); + + BOOST_TEST( http_category().failed( 0 ) ); + BOOST_TEST( !http_category().failed( 200 ) ); + BOOST_TEST( http_category().failed( 404 ) ); + + test(); + test(); + + { + error_condition ec( errc::success ); + TEST_NOT_FAILED( ec ); + + ec = errc::address_family_not_supported; + TEST_FAILED( ec ); + } + + { + error_condition ec( errc::address_family_not_supported ); + TEST_FAILED( ec ); + + ec = errc::success; + TEST_NOT_FAILED( ec ); + } + + { + error_code ec( make_error_code( errc::success ) ); + TEST_NOT_FAILED( ec ); + + ec = make_error_code( errc::address_family_not_supported ); + TEST_FAILED( ec ); + } + + { + error_code ec( make_error_code( errc::address_family_not_supported ) ); + TEST_FAILED( ec ); + + ec = make_error_code( errc::success ); + TEST_NOT_FAILED( ec ); + } + + return boost::report_errors(); +} From be972baaa3f14862750f32e2eaa4f890e74277b2 Mon Sep 17 00:00:00 2001 From: Peter Dimov Date: Sat, 22 Sep 2018 19:33:04 +0300 Subject: [PATCH 6/9] Add a constructor to http_category_impl to placate clang++-3.8 and below --- test/failed_test.cpp | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/test/failed_test.cpp b/test/failed_test.cpp index 67a317d..118d35f 100644 --- a/test/failed_test.cpp +++ b/test/failed_test.cpp @@ -13,6 +13,12 @@ using namespace boost::system; struct http_category_impl: public error_category { + // clang++ 3.8 and below: initialization of const object + // requires a user-provided default constructor + BOOST_SYSTEM_CONSTEXPR http_category_impl() BOOST_NOEXCEPT + { + } + char const * name() const BOOST_NOEXCEPT { return "http"; From e7c1079c4fd48602e80df4a887f50f70115e471c Mon Sep 17 00:00:00 2001 From: Peter Dimov Date: Sat, 22 Sep 2018 20:05:31 +0300 Subject: [PATCH 7/9] Try to work around g++-5 constexpr issue in failed_impl --- include/boost/system/error_code.hpp | 35 ++++++++++++++++++++++------- 1 file changed, 27 insertions(+), 8 deletions(-) diff --git a/include/boost/system/error_code.hpp b/include/boost/system/error_code.hpp index 99d23a1..c2b1bc0 100644 --- a/include/boost/system/error_code.hpp +++ b/include/boost/system/error_code.hpp @@ -385,7 +385,33 @@ template struct enable_if // failed_impl -#if defined(BOOST_SYSTEM_HAS_CONSTEXPR) +#if !defined(BOOST_SYSTEM_HAS_CONSTEXPR) + +inline bool failed_impl( int ev, error_category const & cat ) +{ + return cat.failed( ev ); +} + +#elif BOOST_WORKAROUND(BOOST_GCC, < 60000) + +inline bool failed2_impl( int ev, error_category const & cat ) +{ + return cat.failed( ev ); +} + +BOOST_SYSTEM_CONSTEXPR inline bool failed_impl( int ev, error_category const & cat ) +{ + if( cat == system_category() || cat == generic_category() ) + { + return ev != 0; + } + else + { + return failed2_impl( ev, cat ); + } +} + +#else BOOST_SYSTEM_CONSTEXPR inline bool failed_impl( int ev, error_category const & cat ) { @@ -399,13 +425,6 @@ BOOST_SYSTEM_CONSTEXPR inline bool failed_impl( int ev, error_category const & c } } -#else - -inline bool failed_impl( int ev, error_category const & cat ) -{ - return cat.failed( ev ); -} - #endif } // namespace detail From 91aeb86f5734800e1bb3426562306d86fcc0082a Mon Sep 17 00:00:00 2001 From: Peter Dimov Date: Sat, 22 Sep 2018 21:00:06 +0300 Subject: [PATCH 8/9] Disable constexpr on g++ 5 --- include/boost/system/detail/config.hpp | 4 ++++ include/boost/system/error_code.hpp | 19 ------------------- 2 files changed, 4 insertions(+), 19 deletions(-) diff --git a/include/boost/system/detail/config.hpp b/include/boost/system/detail/config.hpp index fde93cb..2ad8201 100644 --- a/include/boost/system/detail/config.hpp +++ b/include/boost/system/detail/config.hpp @@ -33,6 +33,10 @@ # define BOOST_SYSTEM_HAS_CONSTEXPR #endif +#if BOOST_WORKAROUND(BOOST_GCC, < 60000) +# undef BOOST_SYSTEM_HAS_CONSTEXPR +#endif + #if defined(BOOST_SYSTEM_HAS_CONSTEXPR) # define BOOST_SYSTEM_CONSTEXPR constexpr #else diff --git a/include/boost/system/error_code.hpp b/include/boost/system/error_code.hpp index c2b1bc0..f413980 100644 --- a/include/boost/system/error_code.hpp +++ b/include/boost/system/error_code.hpp @@ -392,25 +392,6 @@ inline bool failed_impl( int ev, error_category const & cat ) return cat.failed( ev ); } -#elif BOOST_WORKAROUND(BOOST_GCC, < 60000) - -inline bool failed2_impl( int ev, error_category const & cat ) -{ - return cat.failed( ev ); -} - -BOOST_SYSTEM_CONSTEXPR inline bool failed_impl( int ev, error_category const & cat ) -{ - if( cat == system_category() || cat == generic_category() ) - { - return ev != 0; - } - else - { - return failed2_impl( ev, cat ); - } -} - #else BOOST_SYSTEM_CONSTEXPR inline bool failed_impl( int ev, error_category const & cat ) From f821d5e74a717e70d257aa5b64815042240df618 Mon Sep 17 00:00:00 2001 From: Peter Dimov Date: Sat, 22 Sep 2018 21:06:31 +0300 Subject: [PATCH 9/9] Add failed_constexpr_test.cpp --- test/Jamfile.v2 | 1 + test/failed_constexpr_test.cpp | 58 ++++++++++++++++++++++++++++++++++ 2 files changed, 59 insertions(+) create mode 100644 test/failed_constexpr_test.cpp diff --git a/test/Jamfile.v2 b/test/Jamfile.v2 index cea6d10..ee73b6b 100644 --- a/test/Jamfile.v2 +++ b/test/Jamfile.v2 @@ -128,6 +128,7 @@ system-run generic_category_test.cpp ; system-run system_category_test.cpp ; system-run after_main_test.cpp ; system-run failed_test.cpp ; +system-run- failed_constexpr_test.cpp ; # Quick (CI) test run quick.cpp ; diff --git a/test/failed_constexpr_test.cpp b/test/failed_constexpr_test.cpp new file mode 100644 index 0000000..e9ccab5 --- /dev/null +++ b/test/failed_constexpr_test.cpp @@ -0,0 +1,58 @@ + +// Copyright 2018 Peter Dimov. +// Distributed under the Boost Software License, Version 1.0. + +#include +#include +#include + +#if !defined(BOOST_SYSTEM_HAS_CONSTEXPR) + +BOOST_PRAGMA_MESSAGE("Skipping constexpr test, BOOST_SYSTEM_HAS_CONSTEXPR isn't defined") +int main() {} + +#else + +using namespace boost::system; + +constexpr error_code ec1( 1, system_category() ); + +BOOST_STATIC_ASSERT( ec1.failed() ); +BOOST_STATIC_ASSERT( ec1 ); +BOOST_STATIC_ASSERT( !!ec1 ); + +constexpr error_code ec2( 2, generic_category() ); + +BOOST_STATIC_ASSERT( ec2.failed() ); +BOOST_STATIC_ASSERT( ec2 ); +BOOST_STATIC_ASSERT( !!ec2 ); + +constexpr error_code ec3; + +BOOST_STATIC_ASSERT( !ec3.failed() ); +BOOST_STATIC_ASSERT( ec3? false: true ); +BOOST_STATIC_ASSERT( !ec3 ); + +constexpr error_condition en1( 1, system_category() ); + +BOOST_STATIC_ASSERT( en1.failed() ); +BOOST_STATIC_ASSERT( en1 ); +BOOST_STATIC_ASSERT( !!en1 ); + +constexpr error_condition en2( 2, generic_category() ); + +BOOST_STATIC_ASSERT( en2.failed() ); +BOOST_STATIC_ASSERT( en2 ); +BOOST_STATIC_ASSERT( !!en2 ); + +constexpr error_condition en3; + +BOOST_STATIC_ASSERT( !en3.failed() ); +BOOST_STATIC_ASSERT( en3? false: true ); +BOOST_STATIC_ASSERT( !en3 ); + +int main() +{ +} + +#endif