Skip to content

Commit

Permalink
Make inplace_function's move operations "noexcept".
Browse files Browse the repository at this point in the history
Fixes #128.
  • Loading branch information
Quuxplusone committed Dec 1, 2018
1 parent 3b63ff7 commit 5c875e3
Show file tree
Hide file tree
Showing 2 changed files with 20 additions and 6 deletions.
12 changes: 6 additions & 6 deletions SG14/inplace_function.h
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,7 @@ template<typename R, typename... Args> struct vtable
{ ::new (dst_ptr) C{ (*static_cast<C*>(src_ptr)) }; }
},
relocate_ptr{ [](storage_ptr_t dst_ptr, storage_ptr_t src_ptr)
noexcept(std::is_nothrow_move_constructible<C>::value) -> void
noexcept -> void
{
::new (dst_ptr) C{ std::move(*static_cast<C*>(src_ptr)) };
static_cast<C*>(src_ptr)->~C();
Expand Down Expand Up @@ -220,7 +220,7 @@ class inplace_function<R(Args...), Capacity, Alignment>
);
}

inplace_function(inplace_function&& other) :
inplace_function(inplace_function&& other) noexcept :
vtable_ptr_{std::exchange(other.vtable_ptr_, std::addressof(inplace_function_detail::empty_vtable<R, Args...>))}
{
vtable_ptr_->relocate_ptr(
Expand Down Expand Up @@ -251,7 +251,7 @@ class inplace_function<R(Args...), Capacity, Alignment>
return *this;
}

inplace_function& operator= (inplace_function&& other)
inplace_function& operator= (inplace_function&& other) noexcept
{
if(this != std::addressof(other))
{
Expand Down Expand Up @@ -305,7 +305,7 @@ class inplace_function<R(Args...), Capacity, Alignment>
}

template<size_t Cap, size_t Align>
operator inplace_function<R(Args...), Cap, Align>() &&
operator inplace_function<R(Args...), Cap, Align>() && noexcept
{
static_assert(inplace_function_detail::is_valid_inplace_dst<
Cap, Align, Capacity, Alignment
Expand All @@ -316,7 +316,7 @@ class inplace_function<R(Args...), Capacity, Alignment>
return {vtable_ptr, vtable_ptr->relocate_ptr, std::addressof(storage_)};
}

void swap(inplace_function& other)
void swap(inplace_function& other) noexcept
{
if (this == std::addressof(other)) return;

Expand All @@ -339,7 +339,7 @@ class inplace_function<R(Args...), Capacity, Alignment>
std::swap(vtable_ptr_, other.vtable_ptr_);
}

friend void swap(inplace_function& lhs, inplace_function& rhs)
friend void swap(inplace_function& lhs, inplace_function& rhs) noexcept
{
lhs.swap(rhs);
}
Expand Down
14 changes: 14 additions & 0 deletions SG14_test/inplace_function_test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
#include <memory>
#include <string>
#include <type_traits>
#include <vector>

#define EXPECT_EQ(val1, val2) assert(val1 == val2)
#define EXPECT_TRUE(val) assert(val)
Expand Down Expand Up @@ -398,6 +399,18 @@ static void test_overloaded_operator_new()
EXPECT_EQ(43, fun(1));
}

void test_move_construction_is_noexcept()
{
using IPF = stdext::inplace_function<void(int), sizeof(Functor)>;
std::vector<IPF> vec;
vec.push_back(Functor());
copied = 0;
moved = 0;
vec.reserve(vec.capacity() + 1);
EXPECT_EQ(0, copied);
EXPECT_EQ(1, moved);
}

void sg14_test::inplace_function_test()
{
// first set of tests (from Optiver)
Expand Down Expand Up @@ -479,6 +492,7 @@ void sg14_test::inplace_function_test()
test_exception_safety();
test_nullptr();
test_overloaded_operator_new();
test_move_construction_is_noexcept();
}

#ifdef TEST_MAIN
Expand Down

0 comments on commit 5c875e3

Please sign in to comment.