Skip to content

Commit

Permalink
Add detail/pp_utilities.hpp
Browse files Browse the repository at this point in the history
  • Loading branch information
pdimov committed Mar 14, 2021
1 parent c6fa6f1 commit ae5c3c8
Show file tree
Hide file tree
Showing 6 changed files with 178 additions and 3 deletions.
6 changes: 3 additions & 3 deletions include/boost/describe/detail/pp_for_each.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
// Distributed under the Boost Software License, Version 1.0.
// https://www.boost.org/LICENSE_1_0.txt

#define BOOST_DESCRIBE_PP_EXPAND(x) x
#include <boost/describe/detail/pp_utilities.hpp>

#define BOOST_DESCRIBE_PP_FOR_EACH_0(F, a)
#define BOOST_DESCRIBE_PP_FOR_EACH_1(F, a, x) F(a, x)
Expand Down Expand Up @@ -61,10 +61,10 @@
#define BOOST_DESCRIBE_PP_FOR_EACH_51(F, a, x, ...) BOOST_DESCRIBE_PP_EXPAND(F(a, x) BOOST_DESCRIBE_PP_FOR_EACH_50(F, a, __VA_ARGS__))
#define BOOST_DESCRIBE_PP_FOR_EACH_52(F, a, x, ...) BOOST_DESCRIBE_PP_EXPAND(F(a, x) BOOST_DESCRIBE_PP_FOR_EACH_51(F, a, __VA_ARGS__))

#define BOOST_DESCRIBE_PP_EXTRACT(_0, _1, _2, _3, _4, _5, _6, _7, _8, _9, _10, _11, _12, _13, _14, _15, _16, _17, _18, _19, _20, _21, _22, _23, _24, _25, _26, _27, _28, _29, _30, _31, _32, _33, _34, _35, _36, _37, _38, _39, _40, _41, _42, _43, _44, _45, _46, _47, _48, _49, _50, _51, _52, V, ...) V
#define BOOST_DESCRIBE_PP_FE_EXTRACT(_0, _1, _2, _3, _4, _5, _6, _7, _8, _9, _10, _11, _12, _13, _14, _15, _16, _17, _18, _19, _20, _21, _22, _23, _24, _25, _26, _27, _28, _29, _30, _31, _32, _33, _34, _35, _36, _37, _38, _39, _40, _41, _42, _43, _44, _45, _46, _47, _48, _49, _50, _51, _52, V, ...) V

#define BOOST_DESCRIBE_PP_FOR_EACH(F, ...) \
BOOST_DESCRIBE_PP_EXPAND(BOOST_DESCRIBE_PP_EXPAND(BOOST_DESCRIBE_PP_EXTRACT(__VA_ARGS__, \
BOOST_DESCRIBE_PP_EXPAND(BOOST_DESCRIBE_PP_EXPAND(BOOST_DESCRIBE_PP_FE_EXTRACT(__VA_ARGS__, \
BOOST_DESCRIBE_PP_FOR_EACH_52, \
BOOST_DESCRIBE_PP_FOR_EACH_51, \
BOOST_DESCRIBE_PP_FOR_EACH_50, \
Expand Down
48 changes: 48 additions & 0 deletions include/boost/describe/detail/pp_utilities.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
#ifndef BOOST_DESCRIBE_DETAIL_PP_UTILITIES_HPP_INCLUDED
#define BOOST_DESCRIBE_DETAIL_PP_UTILITIES_HPP_INCLUDED

// Copyright 2021 Peter Dimov
// Distributed under the Boost Software License, Version 1.0.
// https://www.boost.org/LICENSE_1_0.txt

#define BOOST_DESCRIBE_PP_EXPAND(x) x

#define BOOST_DESCRIBE_PP_CAT(x, y) BOOST_DESCRIBE_PP_CAT_I(x, y)
#define BOOST_DESCRIBE_PP_CAT_I(x, ...) x ## __VA_ARGS__

#if defined(_MSC_VER) && !defined(__clang__)

#define BOOST_DESCRIBE_PP_FIRST(x) BOOST_DESCRIBE_PP_FIRST_I((x))
#define BOOST_DESCRIBE_PP_FIRST_I(x) BOOST_DESCRIBE_PP_FIRST_II x
#define BOOST_DESCRIBE_PP_FIRST_II(x, ...) x

#else

#define BOOST_DESCRIBE_PP_FIRST(x) BOOST_DESCRIBE_PP_FIRST_I(x)
#define BOOST_DESCRIBE_PP_FIRST_I(x, ...) x

#endif

#define BOOST_DESCRIBE_PP_IS_PAREN_I(x) BOOST_DESCRIBE_PP_CAT(BOOST_DESCRIBE_PP_IS_PAREN_I_, BOOST_DESCRIBE_PP_IS_PAREN_II x)
#define BOOST_DESCRIBE_PP_IS_PAREN_II(...) 0
#define BOOST_DESCRIBE_PP_IS_PAREN_I_0 1,
#define BOOST_DESCRIBE_PP_IS_PAREN_I_BOOST_DESCRIBE_PP_IS_PAREN_II 0,

#define BOOST_DESCRIBE_PP_IS_PAREN(x) BOOST_DESCRIBE_PP_FIRST(BOOST_DESCRIBE_PP_IS_PAREN_I(x))

#define BOOST_DESCRIBE_PP_EMPTY

#define BOOST_DESCRIBE_PP_IS_EMPTY(x) BOOST_DESCRIBE_PP_IS_EMPTY_I(BOOST_DESCRIBE_PP_IS_PAREN(x), BOOST_DESCRIBE_PP_IS_PAREN(x BOOST_DESCRIBE_PP_EMPTY ()))
#define BOOST_DESCRIBE_PP_IS_EMPTY_I(x, y) BOOST_DESCRIBE_PP_IS_EMPTY_II(x, y)
#define BOOST_DESCRIBE_PP_IS_EMPTY_II(x, y) BOOST_DESCRIBE_PP_IS_EMPTY_III(x, y)
#define BOOST_DESCRIBE_PP_IS_EMPTY_III(x, y) BOOST_DESCRIBE_PP_IS_EMPTY_III_ ## x ## y
#define BOOST_DESCRIBE_PP_IS_EMPTY_III_00 0
#define BOOST_DESCRIBE_PP_IS_EMPTY_III_01 1
#define BOOST_DESCRIBE_PP_IS_EMPTY_III_10 0
#define BOOST_DESCRIBE_PP_IS_EMPTY_III_11 0

#define BOOST_DESCRIBE_PP_CALL(F, a, x) BOOST_DESCRIBE_PP_CAT(BOOST_DESCRIBE_PP_CALL_I_, BOOST_DESCRIBE_PP_IS_EMPTY(x))(F, a, x)
#define BOOST_DESCRIBE_PP_CALL_I_0(F, a, x) F(a, x)
#define BOOST_DESCRIBE_PP_CALL_I_1(F, a, x)

#endif // #ifndef BOOST_DESCRIBE_DETAIL_PP_UTILITIES_HPP_INCLUDED
3 changes: 3 additions & 0 deletions test/Jamfile
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@ project : requirements
run quick.cpp ;

run pp_for_each_test.cpp ;
run pp_is_paren_test.cpp ;
run pp_is_empty_test.cpp ;
run pp_call_test.cpp ;

run enumerators_test.cpp ;

Expand Down
43 changes: 43 additions & 0 deletions test/pp_call_test.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
// Copyright 2021 Peter Dimov
// Distributed under the Boost Software License, Version 1.0.
// https://www.boost.org/LICENSE_1_0.txt

#include <boost/describe/detail/pp_utilities.hpp>
#include <boost/describe/detail/config.hpp>
#include <boost/core/lightweight_test.hpp>

#if !defined(BOOST_DESCRIBE_CXX11)

#include <boost/config/pragma_message.hpp>

BOOST_PRAGMA_MESSAGE("Skipping test because C++11 is not available")
int main() {}

#else

#define S(x) S2(x)
#define S2(x) S3(x)
#define S3(x) #x

#define F(a, x) (a, x)

#if defined(_MSC_VER)
# pragma warning(disable: 4003) // not enough arguments for macro invocation
#endif

char const * s1 = S(BOOST_DESCRIBE_PP_CALL(F, a, x));
char const * s2 = "" S(BOOST_DESCRIBE_PP_CALL(F, a, ));
char const * s3 = S(BOOST_DESCRIBE_PP_CALL(F, a, () x));
char const * s4 = S(BOOST_DESCRIBE_PP_CALL(F, a, (b, c) x));

int main()
{
BOOST_TEST_CSTR_EQ( s1, "(a, x)" );
BOOST_TEST_CSTR_EQ( s2, "" );
BOOST_TEST_CSTR_EQ( s3, "(a, () x)" );
BOOST_TEST_CSTR_EQ( s4, "(a, (b, c) x)" );

return boost::report_errors();
}

#endif // !defined(BOOST_DESCRIBE_CXX11)
40 changes: 40 additions & 0 deletions test/pp_is_empty_test.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
// Copyright 2021 Peter Dimov
// Distributed under the Boost Software License, Version 1.0.
// https://www.boost.org/LICENSE_1_0.txt

#include <boost/describe/detail/pp_utilities.hpp>
#include <boost/describe/detail/config.hpp>
#include <boost/core/lightweight_test.hpp>

#if !defined(BOOST_DESCRIBE_CXX11)

#include <boost/config/pragma_message.hpp>

BOOST_PRAGMA_MESSAGE("Skipping test because C++11 is not available")
int main() {}

#else

#define S(x) S2(x)
#define S2(x) #x

#if defined(_MSC_VER)
# pragma warning(disable: 4003) // not enough arguments for macro invocation
#endif

char const * s1 = S(BOOST_DESCRIBE_PP_IS_EMPTY());
char const * s2 = S(BOOST_DESCRIBE_PP_IS_EMPTY(x));
char const * s3 = S(BOOST_DESCRIBE_PP_IS_EMPTY(() x));
char const * s4 = S(BOOST_DESCRIBE_PP_IS_EMPTY((a, b) x));

int main()
{
BOOST_TEST_CSTR_EQ( s1, "1" );
BOOST_TEST_CSTR_EQ( s2, "0" );
BOOST_TEST_CSTR_EQ( s3, "0" );
BOOST_TEST_CSTR_EQ( s4, "0" );

return boost::report_errors();
}

#endif // !defined(BOOST_DESCRIBE_CXX11)
41 changes: 41 additions & 0 deletions test/pp_is_paren_test.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
// Copyright 2021 Peter Dimov
// Distributed under the Boost Software License, Version 1.0.
// https://www.boost.org/LICENSE_1_0.txt

#include <boost/describe/detail/pp_utilities.hpp>
#include <boost/describe/detail/config.hpp>
#include <boost/core/lightweight_test.hpp>

#if !defined(BOOST_DESCRIBE_CXX11)

#include <boost/config/pragma_message.hpp>

BOOST_PRAGMA_MESSAGE("Skipping test because C++11 is not available")
int main() {}

#else

#define S(x) S2(x)
#define S2(x) S3(x)
#define S3(x) #x

#if defined(_MSC_VER)
# pragma warning(disable: 4003) // not enough arguments for macro invocation
#endif

char const * s1 = S(BOOST_DESCRIBE_PP_IS_PAREN());
char const * s2 = S(BOOST_DESCRIBE_PP_IS_PAREN(x));
char const * s3 = S(BOOST_DESCRIBE_PP_IS_PAREN(() x));
char const * s4 = S(BOOST_DESCRIBE_PP_IS_PAREN((a, b) x));

int main()
{
BOOST_TEST_CSTR_EQ( s1, "0" );
BOOST_TEST_CSTR_EQ( s2, "0" );
BOOST_TEST_CSTR_EQ( s3, "1" );
BOOST_TEST_CSTR_EQ( s4, "1" );

return boost::report_errors();
}

#endif // !defined(BOOST_DESCRIBE_CXX11)

0 comments on commit ae5c3c8

Please sign in to comment.