Commit de4ce899 authored by Eric Niebler's avatar Eric Niebler Committed by Facebook Github Bot

get folly/experimental/pushmi building with gcc-5 again

Summary: Judging from the number of things that needed fixing, pushmi has been busted on gcc-5 for some time.

Reviewed By: yfeldblum, kirkshoop

Differential Revision: D13979146

fbshipit-source-id: 95def0ef6289b41e116a55359476ffec91787706
parent 4435c335
......@@ -325,7 +325,8 @@ PUSHMI_CONCEPT_DEF(
(concept ReceiveError)(R, E), //
requires(R& r, E&& e)( //
set_error(r, (E &&) e)) &&
Receiver<R> && SemiMovable<E>);
Receiver<R> && SemiMovable<E>
);
PUSHMI_CONCEPT_DEF(
template(class D, class... PropertyN) //
......
......@@ -135,7 +135,7 @@ PUSHMI_PP_IGNORE_CXX2A_COMPAT_BEGIN
PUSHMI_PP_IIF(X)(PUSHMI_PP_EMPTY, PUSHMI_PP_COMMA)()
#define PUSHMI_CONCEPT_ASSERT(...) \
static_assert((bool) (__VA_ARGS__), \
static_assert(static_cast<bool>(__VA_ARGS__), \
"Concept assertion failed : " #__VA_ARGS__)
////////////////////////////////////////////////////////////////////////////////
......@@ -225,14 +225,14 @@ PUSHMI_PP_IGNORE_CXX2A_COMPAT_BEGIN
#define PUSHMI_PP_DECL_DEF_IMPL(TPARAM, NAME, ARGS, ...) \
inline namespace _eager_ { \
PUSHMI_PP_CAT(PUSHMI_PP_DEF_, TPARAM) \
concept bool NAME = PUSHMI_PP_DEF_IMPL(__VA_ARGS__)(__VA_ARGS__); \
concept bool NAME = PUSHMI_PP_DEF_IMPL(__VA_ARGS__,)(__VA_ARGS__); \
} \
namespace lazy = _eager_; \
/**/
#else
// No requires expression:
#define PUSHMI_PP_DEF_IMPL_0(...) \
() -> std::enable_if_t<bool(__VA_ARGS__), int> \
() -> std::enable_if_t<static_cast<bool>(__VA_ARGS__), int> \
/**/
// Requires expression:
#define PUSHMI_PP_DEF_IMPL_1(...) \
......@@ -254,16 +254,16 @@ PUSHMI_PP_IGNORE_CXX2A_COMPAT_BEGIN
using Concept = PUSHMI_PP_CAT(NAME, Concept); \
PUSHMI_PP_IGNORE_CXX2A_COMPAT_BEGIN \
PUSHMI_PP_CAT(PUSHMI_PP_DEF_, TPARAM) \
static auto Requires_ PUSHMI_PP_DEF_IMPL(__VA_ARGS__)(__VA_ARGS__) { \
static auto Requires_ PUSHMI_PP_DEF_IMPL(__VA_ARGS__,)(__VA_ARGS__) { \
return 0; \
} \
PUSHMI_PP_IGNORE_CXX2A_COMPAT_END \
PUSHMI_PP_CAT(PUSHMI_PP_DEF_, TPARAM) \
struct Eval { \
template <class C_ = Concept> \
static constexpr decltype(::folly::pushmi::concepts::detail::gcc_bugs( \
&C_::template Requires_<PUSHMI_PP_EXPAND ARGS>)) \
impl(int) noexcept { \
template <class C_ = Concept, \
decltype(::folly::pushmi::concepts::detail::gcc_bugs( \
&C_::template Requires_<PUSHMI_PP_EXPAND ARGS>)) = nullptr> \
static constexpr bool impl(int) noexcept { \
return true; \
} \
static constexpr bool impl(long) noexcept { \
......@@ -275,7 +275,7 @@ PUSHMI_PP_IGNORE_CXX2A_COMPAT_BEGIN
template < \
class PMThis = Concept, \
bool PMB, \
class = std::enable_if_t<PMB == (bool)PMThis{}>> \
class = std::enable_if_t<PMB == static_cast<bool>(PMThis{})>> \
constexpr operator std::integral_constant<bool, PMB>() const noexcept { \
return {}; \
} \
......@@ -299,7 +299,8 @@ PUSHMI_PP_IGNORE_CXX2A_COMPAT_BEGIN
} \
PUSHMI_PP_CAT(PUSHMI_PP_DEF_, TPARAM) \
PUSHMI_INLINE_VAR constexpr bool NAME = \
(bool)PUSHMI_PP_CAT(NAME, Concept)::Eval<PUSHMI_PP_EXPAND ARGS> {} \
static_cast<bool>( \
PUSHMI_PP_CAT(NAME, Concept)::Eval<PUSHMI_PP_EXPAND ARGS>{}) \
/**/
#endif
......@@ -382,11 +383,11 @@ PUSHMI_PP_IGNORE_CXX2A_COMPAT_BEGIN
#define PUSHMI_TEMPLATE(...) \
template<__VA_ARGS__ PUSHMI_TEMPLATE_AUX_
#define PUSHMI_TEMPLATE_AUX_(...) , \
int (*PUSHMI_PP_CAT(_pushmi_concept_unique_, __LINE__))[ \
PUSHMI_COUNTER] = nullptr, \
std::enable_if_t<PUSHMI_PP_CAT(_pushmi_concept_unique_, __LINE__) || \
bool(PUSHMI_TEMPLATE_AUX_4(PUSHMI_PP_CAT( \
PUSHMI_TEMPLATE_AUX_3_, __VA_ARGS__))), int> = 0> \
bool PUSHMI_PP_CAT(_pushmi_false_, __LINE__) = false, \
std::enable_if_t< \
static_cast<bool>(PUSHMI_TEMPLATE_AUX_4(PUSHMI_PP_CAT( \
PUSHMI_TEMPLATE_AUX_3_, __VA_ARGS__))) || \
PUSHMI_PP_CAT(_pushmi_false_, __LINE__), int> = 0> \
/**/
#define PUSHMI_TEMPLATE_AUX_3_requires
#define PUSHMI_TEMPLATE_AUX_4(...) \
......@@ -444,7 +445,8 @@ using bool_ = std::integral_constant<bool, B>;
namespace concepts {
namespace detail {
bool gcc_bugs(...);
template<class T>
T gcc_bugs(T);
template <class>
inline constexpr bool requires_() {
......@@ -459,10 +461,10 @@ struct Or;
template <class T>
struct Not {
explicit constexpr operator bool() const noexcept {
return !(bool)T{};
return !static_cast<bool>(T{});
}
PUSHMI_TEMPLATE(class This = Not, bool B)
(requires B == (bool)This{}) constexpr
(requires B == static_cast<bool>(This{})) constexpr
operator std::integral_constant<bool, B>() const noexcept {
return {};
}
......@@ -484,9 +486,9 @@ struct And {
explicit constexpr operator bool() const noexcept {
return (bool)std::conditional_t<(bool)T{}, U, std::false_type>{};
}
PUSHMI_TEMPLATE(class This = And, bool B)
(requires B == (bool)This{}) constexpr
operator std::integral_constant<bool, B>() const noexcept {
PUSHMI_TEMPLATE(class This = And, bool B) //
(requires B == static_cast<bool>(This{})) //
constexpr operator std::integral_constant<bool, B>() const noexcept {
return {};
}
constexpr auto operator!() const noexcept {
......@@ -507,9 +509,9 @@ struct Or {
explicit constexpr operator bool() const noexcept {
return (bool)std::conditional_t<(bool)T{}, std::true_type, U>{};
}
PUSHMI_TEMPLATE(class This = Or, bool B)
(requires B == (bool)This{}) constexpr
operator std::integral_constant<bool, B>() const noexcept {
PUSHMI_TEMPLATE(class This = Or, bool B) //
(requires B == static_cast<bool>(This{})) //
constexpr operator std::integral_constant<bool, B>() const noexcept {
return {};
}
constexpr auto operator!() const noexcept {
......
......@@ -42,13 +42,15 @@ auto println = [](auto v) { std::cout << v << std::endl; };
// concat not yet implemented
template <class T, class E = std::exception_ptr>
auto concat = [](auto in) {
return mi::make_single_sender([in](auto out) mutable {
mi::submit(in, mi::make_receiver(out, [](auto out_, auto v) {
mi::submit(v, mi::any_receiver<E, T>(out_));
}));
});
};
auto concat() {
return [](auto in) {
return mi::make_single_sender([in](auto out) mutable {
mi::submit(in, mi::make_receiver(out, [](auto out_, auto v) {
mi::submit(v, mi::any_receiver<E, T>(out_));
}));
});
};
}
int main() {
get_setting() | op::transform([](int i) { return std::to_string(i); }) |
......@@ -65,7 +67,7 @@ int main() {
}
return mi::any_single_sender<std::exception_ptr, std::string>{
op::just(std::to_string(i))};
}) | concat<std::string> |
}) | concat<std::string>() |
op::submit(println);
std::cout << "OK" << std::endl;
......
......@@ -29,13 +29,15 @@ using namespace folly::pushmi::aliases;
// concat not yet implemented
template <class T, class E = std::exception_ptr>
auto concat = [](auto in) {
return mi::make_single_sender([in](auto out) mutable {
mi::submit(in, mi::make_receiver(out, [](auto out_, auto v) {
mi::submit(v, mi::any_receiver<E, T>(out_));
}));
});
};
auto concat() {
return [](auto in) {
return mi::make_single_sender([in](auto out) mutable {
mi::submit(in, mi::make_receiver(out, [](auto out_, auto v) {
mi::submit(v, mi::any_receiver<E, T>(out_));
}));
});
};
}
int main() {
auto stop_abort = mi::on_error([](auto) noexcept {});
......@@ -76,7 +78,7 @@ int main() {
} else {
return r_t{op::just(v)};
}
}) | concat<int> |
}) | concat<int>() |
op::submit();
// retry on error
......
......@@ -68,7 +68,7 @@ public:
static_assert(
SenderTo<Wrapped, any_receiver<E,This>>,
"Expecting to be passed a Sender that can send to a SingleReceiver"
" that accpets a value of type This and an error of type E");
" that accepts a value of type This and an error of type E");
struct s {
static void submit(void* pobj, void* s) {
return ::folly::pushmi::submit(
......
......@@ -403,7 +403,7 @@ PUSHMI_INLINE_VAR constexpr __adl::get_top_fn top{};
template <class T>
struct property_set_traits<
T,
std::enable_if_t<(bool)Invocable<T&> && not Valid<T&, __properties_t>>> {
void_t<invoke_result_t<T&>>> {
using properties = property_set<is_receiver<>>;
};
......
......@@ -99,13 +99,18 @@ struct tap_fn {
(requires Sender<In>&& Receiver<SideEffects>)
struct out_impl {
SideEffects sideEffects_;
template<class Out>
using tap_t =
decltype(
detail::make_tap(
std::declval<const SideEffects&>(),
std::declval<Out>()));
template<class Out>
using receiver_t = invoke_result_t<receiver_from_fn<In>, tap_t<Out>>;
PUSHMI_TEMPLATE(class Out)
(requires Receiver<Out>&& SenderTo<In, Out>&& SenderTo<
In,
decltype(
::folly::pushmi::detail::receiver_from_fn<In>()(detail::make_tap(
std::declval<SideEffects>(),
std::declval<Out>())))>)
receiver_t<Out>>)
auto operator()(Out out) const {
auto gang{::folly::pushmi::detail::receiver_from_fn<In>()(
detail::make_tap(sideEffects_, std::move(out)))};
......
......@@ -22,7 +22,8 @@ namespace folly {
namespace pushmi {
PUSHMI_TEMPLATE(class In, class Op)
(requires lazy::Sender<std::decay_t<In>>&& lazy::Invocable<Op&, In>) //
(requires PUSHMI_EXP(lazy::Sender<std::decay_t<In>> PUSHMI_AND
lazy::Invocable<Op&, In>)) //
decltype(auto)
operator|(In&& in, Op op) {
return op((In &&) in);
......
......@@ -15,6 +15,7 @@
*/
#pragma once
#include <folly/Traits.h>
#include <folly/experimental/pushmi/traits.h>
#include <folly/experimental/pushmi/forwards.h>
......@@ -35,7 +36,7 @@ struct property_traits {};
template <class T>
struct property_traits<
T,
std::enable_if_t<Valid<std::decay_t<T>, __property_category_t>>> {
void_t<__property_category_t<std::decay_t<T>>>> {
using property_category = __property_category_t<std::decay_t<T>>;
};
......@@ -45,7 +46,7 @@ using property_category_t = __property_category_t<property_traits<T>>;
PUSHMI_CONCEPT_DEF(
template(class T)
concept Property,
Valid<T, property_category_t>
True<__property_category_t<property_traits<T>>>
);
// in cases where Set contains T, allow T to find itself only once
......@@ -96,7 +97,7 @@ struct property_set_traits {};
template <class T>
struct property_set_traits<
T,
std::enable_if_t<Valid<std::decay_t<T>, __properties_t>>> {
void_t<__properties_t<std::decay_t<T>>>> {
using properties = __properties_t<std::decay_t<T>>;
};
......@@ -108,7 +109,7 @@ using properties_t = std::enable_if_t<
PUSHMI_CONCEPT_DEF(
template(class T)
concept Properties,
Valid<T, properties_t>
PropertySet<__properties_t<property_set_traits<T>>>
);
// find property in the specified set that matches the category of the property
......
......@@ -123,9 +123,8 @@ class any_receiver {
std::swap(that.vptr_, vptr_);
}
PUSHMI_TEMPLATE(class Wrapped)
(requires ReceiveValue<wrapped_t<Wrapped>, VN...>&& ReceiveError<
Wrapped,
E>)
(requires ReceiveValue<wrapped_t<Wrapped>, VN...>&& //
ReceiveError<wrapped_t<Wrapped>, E>)
explicit any_receiver(Wrapped obj) noexcept(insitu<Wrapped>())
: any_receiver{std::move(obj), bool_<insitu<Wrapped>()>{}} {
check<Wrapped>();
......
......@@ -92,7 +92,6 @@ class any_single_sender {
template <class T, class U = std::decay_t<T>>
using wrapped_t =
std::enable_if_t<!std::is_same<U, any_single_sender>::value, U>;
public:
using properties = property_set<is_sender<>, is_single<>>;
......@@ -102,13 +101,9 @@ class any_single_sender {
std::swap(that.vptr_, vptr_);
}
PUSHMI_TEMPLATE(class Wrapped)
(requires SenderTo<
wrapped_t<Wrapped>,
any_receiver<
E,
VN...>>) //
explicit any_single_sender(Wrapped obj) noexcept(insitu<Wrapped>())
PUSHMI_TEMPLATE(class Wrapped) //
(requires SenderTo<wrapped_t<Wrapped>, any_receiver<E, VN...>>) //
explicit any_single_sender(Wrapped obj) noexcept(insitu<Wrapped>())
: any_single_sender{std::move(obj), bool_<insitu<Wrapped>()>{}} {}
~any_single_sender() {
vptr_->op_(data_, nullptr);
......
......@@ -18,6 +18,7 @@
#include <functional>
#include <type_traits>
#include <folly/Traits.h>
#include <folly/experimental/pushmi/detail/functional.h>
#define PUSHMI_NOEXCEPT_AUTO(...) \
......@@ -74,9 +75,6 @@ PUSHMI_INLINE_VAR constexpr int sum_v = detail::sum_impl<Is...>();
template <class...>
struct typelist;
template <class...>
using void_t = void;
template <class T>
using remove_cvref_t = std::remove_cv_t<std::remove_reference_t<T>>;
......@@ -86,12 +84,6 @@ PUSHMI_CONCEPT_DEF(
true
);
PUSHMI_CONCEPT_DEF(
template(class T, template<class...> class C)
(concept Valid)(T, C),
True< C<T> >
);
PUSHMI_CONCEPT_DEF(
template (class T, template<class...> class Trait, class... Args)
(concept Satisfies)(T, Trait, Args...),
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment