Skip to content

Commit 4554b71

Browse files
committed
Fix windows build
1 parent c5ce092 commit 4554b71

2 files changed

Lines changed: 49 additions & 27 deletions

File tree

‎src/iceberg/expected.h‎

Lines changed: 40 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -824,19 +824,7 @@ struct copy_assign_base<T, E, true, false> : move_ctor_base<T, E> {
824824
noexcept(std::is_nothrow_copy_constructible_v<T> &&
825825
std::is_nothrow_copy_assignable_v<T> &&
826826
std::is_nothrow_copy_constructible_v<E> &&
827-
std::is_nothrow_copy_assignable_v<E>) {
828-
if (this->m_has_val && rhs.m_has_val) {
829-
this->m_val = rhs.m_val;
830-
} else if (this->m_has_val) {
831-
expected_detail::reinit_expected(this->m_unexpect, this->m_val, rhs.m_unexpect);
832-
} else if (rhs.m_has_val) {
833-
expected_detail::reinit_expected(this->m_val, this->m_unexpect, rhs.m_val);
834-
} else {
835-
this->m_unexpect = rhs.m_unexpect;
836-
}
837-
this->m_has_val = rhs.m_has_val;
838-
return *this;
839-
}
827+
std::is_nothrow_copy_assignable_v<E>);
840828

841829
copy_assign_base& operator=(copy_assign_base&& rhs) = default;
842830
};
@@ -851,24 +839,49 @@ struct copy_assign_base<void, E, true, false> : move_ctor_base<void, E> {
851839
copy_assign_base(copy_assign_base&& rhs) = default;
852840

853841
constexpr copy_assign_base& operator=(const copy_assign_base& rhs) noexcept(
854-
std::is_nothrow_copy_constructible_v<E> && std::is_nothrow_copy_assignable_v<E>) {
855-
if (this->m_has_val && rhs.m_has_val) {
856-
// no-op
857-
} else if (this->m_has_val) {
858-
std::construct_at(std::addressof(this->m_unexpect), rhs.m_unexpect);
859-
this->m_has_val = false;
860-
} else if (rhs.m_has_val) {
861-
this->m_unexpect.~E();
862-
this->m_has_val = true;
863-
} else {
864-
this->m_unexpect = rhs.m_unexpect;
865-
}
866-
return *this;
867-
}
842+
std::is_nothrow_copy_constructible_v<E> && std::is_nothrow_copy_assignable_v<E>);
868843

869844
copy_assign_base& operator=(copy_assign_base&& rhs) = default;
870845
};
871846

847+
template <class T, class E>
848+
constexpr copy_assign_base<T, E, true, false>& copy_assign_base<T, E, true, false>::
849+
operator=(const copy_assign_base<T, E, true, false>& rhs) noexcept(
850+
std::is_nothrow_copy_constructible_v<T> && std::is_nothrow_copy_assignable_v<T> &&
851+
std::is_nothrow_copy_constructible_v<E> && std::is_nothrow_copy_assignable_v<E>) {
852+
if (this->m_has_val && rhs.m_has_val) {
853+
this->m_val = rhs.m_val;
854+
} else if (this->m_has_val) {
855+
expected_detail::reinit_expected(this->m_unexpect, this->m_val, rhs.m_unexpect);
856+
} else if (rhs.m_has_val) {
857+
expected_detail::reinit_expected(this->m_val, this->m_unexpect, rhs.m_val);
858+
} else {
859+
this->m_unexpect = rhs.m_unexpect;
860+
}
861+
this->m_has_val = rhs.m_has_val;
862+
return *this;
863+
}
864+
865+
template <class E>
866+
constexpr copy_assign_base<void, E, true, false>&
867+
copy_assign_base<void, E, true, false>::operator=(
868+
const copy_assign_base<void, E, true, false>&
869+
rhs) noexcept(std::is_nothrow_copy_constructible_v<E> &&
870+
std::is_nothrow_copy_assignable_v<E>) {
871+
if (this->m_has_val && rhs.m_has_val) {
872+
// no-op
873+
} else if (this->m_has_val) {
874+
std::construct_at(std::addressof(this->m_unexpect), rhs.m_unexpect);
875+
this->m_has_val = false;
876+
} else if (rhs.m_has_val) {
877+
this->m_unexpect.~E();
878+
this->m_has_val = true;
879+
} else {
880+
this->m_unexpect = rhs.m_unexpect;
881+
}
882+
return *this;
883+
}
884+
872885
template <class T, class E>
873886
inline constexpr bool is_expected_move_assignable_v =
874887
is_move_assignable_or_void_v<T> && is_move_constructible_or_void_v<T> &&

‎src/iceberg/test/expected_test.cc‎

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,9 @@
2020
#include "iceberg/expected.h"
2121

2222
#include <functional>
23+
#include <memory>
2324
#include <type_traits>
25+
#include <vector>
2426

2527
#include <gtest/gtest.h>
2628

@@ -77,6 +79,13 @@ TEST(ExpectedTest, ConversionToValueWithoutDefaultConstructor) {
7779
iceberg::expected<std::reference_wrapper<int>, int>>));
7880
}
7981

82+
TEST(ExpectedTest, SupportsMoveOnlyContainerValue) {
83+
using MoveOnlyContainer = std::vector<std::unique_ptr<int>>;
84+
iceberg::expected<MoveOnlyContainer, int> value{std::in_place};
85+
86+
EXPECT_TRUE(value.has_value());
87+
}
88+
8089
namespace {
8190

8291
// Counts live objects, to catch a value constructed without being destroyed.

0 commit comments

Comments
 (0)