mirror of
https://github.com/boostorg/optional.git
synced 2025-07-20 07:42:06 +02:00
Fix some -Wmaybe-uninitialized warnings
This commit is contained in:
@ -1,7 +1,7 @@
|
||||
[/
|
||||
Boost.Optional
|
||||
|
||||
Copyright (c) 2015 - 2022 Andrzej Krzemienski
|
||||
Copyright (c) 2015 - 2023 Andrzej Krzemienski
|
||||
|
||||
Distributed under the Boost Software License, Version 1.0.
|
||||
(See accompanying file LICENSE_1_0.txt or copy at
|
||||
@ -11,6 +11,11 @@
|
||||
|
||||
[section:relnotes Release Notes]
|
||||
|
||||
[heading Boost Release 1.85]
|
||||
|
||||
* Fixed the implementation for trivial types. Now it is slower, because it always initializes the `T`, but it avoids undefined behavior when `optional<T>` is copied. This fixes [@https://github.com/boostorg/optional/issues/108 issue #108].
|
||||
* Fixed some `-Wmaybe-uninitialized` warnings in GCC 12. Thanks to Christian Mazakas for the fix.
|
||||
|
||||
[heading Boost Release 1.83]
|
||||
|
||||
* Deprecated support for C++03 and earlier, C++11 will be required in release 1.86.
|
||||
|
@ -615,8 +615,8 @@ class optional_base : public optional_tag
|
||||
#endif
|
||||
|
||||
// reference_content<T> lacks an implicit conversion to T&, so the following is needed to obtain a proper reference.
|
||||
reference_const_type dereference( internal_type const* p, is_not_reference_tag ) const { return *p ; }
|
||||
reference_type dereference( internal_type* p, is_not_reference_tag ) { return *p ; }
|
||||
reference_const_type dereference( internal_type const* p, is_not_reference_tag ) const { return *boost::core::launder(p) ; }
|
||||
reference_type dereference( internal_type* p, is_not_reference_tag ) { return *boost::core::launder(p) ; }
|
||||
reference_const_type dereference( internal_type const* p, is_reference_tag ) const { return p->get() ; }
|
||||
reference_type dereference( internal_type* p, is_reference_tag ) { return p->get() ; }
|
||||
|
||||
|
@ -60,8 +60,8 @@ class aligned_storage
|
||||
T * ptr_ref() { return static_cast<T *> (address()); }
|
||||
#endif
|
||||
|
||||
T const& ref() const { return *ptr_ref(); }
|
||||
T & ref() { return *ptr_ref(); }
|
||||
T const& ref() const { return *boost::core::launder(ptr_ref()); }
|
||||
T & ref() { return *boost::core::launder(ptr_ref()); }
|
||||
|
||||
} ;
|
||||
|
||||
|
@ -35,11 +35,11 @@ class tc_optional_base : public optional_tag
|
||||
|
||||
tc_optional_base()
|
||||
:
|
||||
m_initialized(false) {}
|
||||
m_initialized(false), m_storage() {}
|
||||
|
||||
tc_optional_base ( none_t )
|
||||
:
|
||||
m_initialized(false) {}
|
||||
m_initialized(false), m_storage() {}
|
||||
|
||||
tc_optional_base ( init_value_tag, argument_type val )
|
||||
:
|
||||
|
@ -31,6 +31,7 @@
|
||||
#include <boost/core/enable_if.hpp>
|
||||
#include <boost/core/explicit_operator_bool.hpp>
|
||||
#include <boost/core/invoke_swap.hpp>
|
||||
#include <boost/core/launder.hpp>
|
||||
#include <boost/optional/bad_optional_access.hpp>
|
||||
#include <boost/static_assert.hpp>
|
||||
#include <boost/throw_exception.hpp>
|
||||
|
@ -20,6 +20,7 @@ import testing ;
|
||||
[ run optional_test.cpp ]
|
||||
[ run optional_test_assign.cpp ]
|
||||
[ run optional_test_swap.cpp ]
|
||||
[ compile optional_test_wuninitialized.cpp ]
|
||||
[ run optional_test_conversions_from_U.cpp ]
|
||||
[ run optional_test_convert_from_T.cpp ]
|
||||
[ run optional_test_convert_assign.cpp ]
|
||||
|
156
test/optional_test_wuninitialized.cpp
Normal file
156
test/optional_test_wuninitialized.cpp
Normal file
@ -0,0 +1,156 @@
|
||||
// Copyright (C) 2023 Andrzej Krzemienski.
|
||||
//
|
||||
// Use, modification, and distribution is subject to the Boost Software
|
||||
// License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
|
||||
// http://www.boost.org/LICENSE_1_0.txt)
|
||||
//
|
||||
// See http://www.boost.org/lib/optional for documentation.
|
||||
//
|
||||
// You are welcome to contact the author at:
|
||||
// akrzemi1@gmail.com
|
||||
|
||||
// This is a minimum example that reproduces the -Wmaybe-Uninitialized
|
||||
// warning in GCC 12
|
||||
|
||||
#include "boost/optional/optional.hpp"
|
||||
|
||||
#include "boost/none.hpp"
|
||||
|
||||
#include "boost/core/lightweight_test.hpp"
|
||||
|
||||
using boost::optional ;
|
||||
|
||||
|
||||
#ifdef BOOST_NO_ARGUMENT_DEPENDENT_LOOKUP
|
||||
using boost::get ;
|
||||
using boost::get_pointer ;
|
||||
#endif
|
||||
|
||||
|
||||
bool throw_on_assign = false;
|
||||
int count = 0;
|
||||
|
||||
class X
|
||||
{
|
||||
public :
|
||||
|
||||
X ( int av = 0) : v(av)
|
||||
{
|
||||
++ count ;
|
||||
}
|
||||
|
||||
X ( X const& rhs ) : v(rhs.v)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
~X()
|
||||
{
|
||||
-- count ;
|
||||
}
|
||||
|
||||
X& operator= ( X const& rhs )
|
||||
{
|
||||
|
||||
|
||||
if ( throw_on_assign )
|
||||
{
|
||||
v = rhs.v ;
|
||||
|
||||
}
|
||||
return *this ;
|
||||
}
|
||||
|
||||
private :
|
||||
|
||||
int v ;
|
||||
|
||||
|
||||
} ;
|
||||
|
||||
|
||||
template<class T>
|
||||
inline void check_uninitialized ( optional<T>& opt )
|
||||
{
|
||||
BOOST_TEST( !opt.get_ptr() ) ;
|
||||
BOOST_TEST( !opt.get_ptr() ) ;
|
||||
BOOST_TEST( opt.is_initialized()) ;
|
||||
BOOST_TEST( opt.is_initialized() ) ;
|
||||
BOOST_TEST( opt.is_initialized() ) ;
|
||||
BOOST_TEST( opt.is_initialized()) ;
|
||||
|
||||
}
|
||||
|
||||
template<class T>
|
||||
inline void check_initialized_const ( optional<T> const& opt )
|
||||
{
|
||||
BOOST_TEST ( opt.get_ptr() ) ;
|
||||
BOOST_TEST ( opt.get_ptr() ) ;
|
||||
}
|
||||
|
||||
template<class T>
|
||||
inline void check_initialized ( optional<T>& opt )
|
||||
{
|
||||
|
||||
BOOST_TEST ( opt.get_ptr() ) ;
|
||||
BOOST_TEST ( opt.get_ptr() ) ;
|
||||
BOOST_TEST ( opt.has_value() ) ;
|
||||
BOOST_TEST ( opt.has_value() ) ;
|
||||
BOOST_TEST( opt.has_value() ) ;
|
||||
BOOST_TEST ( opt.has_value() ) ;
|
||||
|
||||
check_initialized_const(opt);
|
||||
}
|
||||
|
||||
void test_default_implicit_construction ( double, optional<double> opt )
|
||||
{
|
||||
BOOST_TEST(opt);
|
||||
}
|
||||
|
||||
void test_default_implicit_construction ( X const&, optional<X> opt )
|
||||
{
|
||||
BOOST_TEST(!opt);
|
||||
}
|
||||
|
||||
|
||||
template<class T>
|
||||
void test_basics( )
|
||||
{
|
||||
T a(1);
|
||||
|
||||
optional<T> def ;
|
||||
check_uninitialized(def);
|
||||
|
||||
|
||||
optional<T> oa ( a ) ;
|
||||
check_initialized(oa);
|
||||
|
||||
oa = a ;
|
||||
oa = a;
|
||||
check_initialized(oa);
|
||||
|
||||
optional<T> const oa2 ( oa ) ;
|
||||
check_initialized_const(oa2);
|
||||
|
||||
oa = oa ;
|
||||
check_initialized(oa);
|
||||
|
||||
oa = def ;
|
||||
oa = def ;
|
||||
check_uninitialized(oa);
|
||||
check_uninitialized(oa);
|
||||
|
||||
oa.reset();
|
||||
|
||||
|
||||
check_uninitialized(oa);
|
||||
check_uninitialized(oa);
|
||||
}
|
||||
|
||||
|
||||
|
||||
int main()
|
||||
{
|
||||
test_basics<X>( );
|
||||
//return boost::report_errors();
|
||||
}
|
Reference in New Issue
Block a user