Skip to content

Commit

Permalink
Merge pull request #79 from bitshares/for-custom-auth
Browse files Browse the repository at this point in the history
Changes for BSIP40 custom authorities
  • Loading branch information
abitmore committed Oct 25, 2018
2 parents a1d84f2 + 8174d63 commit bcdaaaa
Show file tree
Hide file tree
Showing 5 changed files with 119 additions and 4 deletions.
10 changes: 10 additions & 0 deletions include/fc/reflect/reflect.hpp
Expand Up @@ -87,6 +87,9 @@ void throw_bad_enum_cast( const char* k, const char* e );
visitor.TEMPLATE operator()<member_type,type,&type::elem>( BOOST_PP_STRINGIZE(elem) ); \
}

#define FC_REFLECT_VISIT_MEMBER_I( r, visitor, I, elem ) \
case I: FC_REFLECT_VISIT_MEMBER( r, visitor, elem ) break;


#define FC_REFLECT_BASE_MEMBER_COUNT( r, OP, elem ) \
OP fc::reflector<elem>::total_member_count
Expand All @@ -99,6 +102,13 @@ template<typename Visitor>\
static inline void visit( const Visitor& v ) { \
BOOST_PP_SEQ_FOR_EACH( FC_REFLECT_VISIT_BASE, v, INHERITS ) \
BOOST_PP_SEQ_FOR_EACH( FC_REFLECT_VISIT_MEMBER, v, MEMBERS ) \
}\
template<typename Visitor, typename IndexType>\
static inline void visit_local_member( const Visitor& v, IndexType index ) { \
switch( index ) {\
BOOST_PP_SEQ_FOR_EACH_I( FC_REFLECT_VISIT_MEMBER_I, v, MEMBERS ) \
default: break;\
}\
}

#define FC_REFLECT_DERIVED_IMPL_EXT( TYPE, INHERITS, MEMBERS ) \
Expand Down
72 changes: 68 additions & 4 deletions include/fc/static_variant.hpp
Expand Up @@ -10,6 +10,8 @@
*
**/
#pragma once

#include <functional>
#include <stdexcept>
#include <typeinfo>
#include <fc/exception/exception.hpp>
Expand Down Expand Up @@ -176,6 +178,36 @@ struct type_info<> {

} // namespace impl

template<typename Visitor,typename Data>
std::vector<std::function<typename Visitor::result_type(Visitor&,Data)>> init_wrappers()
{
return std::vector<std::function<typename Visitor::result_type(Visitor&,Data)>>();
}

template<typename Visitor,typename Data, typename T, typename ... Types>
std::vector<std::function<typename Visitor::result_type(Visitor&,Data)>> init_wrappers()
{
std::vector<std::function<typename Visitor::result_type(Visitor&,Data)>> result
= init_wrappers<Visitor,Data,Types...>();
result.insert( result.begin(), [] ( Visitor& v, Data d ) { return v( *reinterpret_cast<T*>( d ) ); } );
return result;
}

template<typename Visitor,typename Data>
std::vector<std::function<typename Visitor::result_type(Visitor&,Data)>> init_const_wrappers()
{
return std::vector<std::function<typename Visitor::result_type(Visitor&,Data)>>();
}

template<typename Visitor,typename Data, typename T, typename ... Types>
std::vector<std::function<typename Visitor::result_type(Visitor&,Data)>> init_const_wrappers()
{
std::vector<std::function<typename Visitor::result_type(Visitor&,Data)>> result
= init_const_wrappers<Visitor,Data,Types...>();
result.insert( result.begin(), [] ( Visitor& v, Data d ) { return v( *reinterpret_cast<const T*>( d ) ); } );
return result;
}

template<typename... Types>
class static_variant {
static_assert(impl::type_info<Types...>::no_reference_types, "Reference types are not permitted in static_variant.");
Expand Down Expand Up @@ -308,22 +340,54 @@ class static_variant {
}
template<typename visitor>
typename visitor::result_type visit(visitor& v) {
return impl::storage_ops<0, Types...>::apply(_tag, storage, v);
return visit( _tag, v, (void*) storage );
}

template<typename visitor>
typename visitor::result_type visit(const visitor& v) {
return impl::storage_ops<0, Types...>::apply(_tag, storage, v);
return visit( _tag, v, (void*) storage );
}

template<typename visitor>
typename visitor::result_type visit(visitor& v)const {
return impl::storage_ops<0, Types...>::apply(_tag, storage, v);
return visit( _tag, v, (const void*) storage );
}

template<typename visitor>
typename visitor::result_type visit(const visitor& v)const {
return impl::storage_ops<0, Types...>::apply(_tag, storage, v);
return visit( _tag, v, (const void*) storage );
}

template<typename visitor>
static typename visitor::result_type visit( tag_type tag, visitor& v, void* data )
{
static auto wrappers = init_wrappers<visitor,void*,Types...>();
FC_ASSERT( tag >= 0 && tag < count(), "Unsupported type ${tag}!", ("tag",tag) );
return wrappers[tag]( v, data );
}

template<typename visitor>
static typename visitor::result_type visit( tag_type tag, const visitor& v, void* data )
{
static auto wrappers = init_wrappers<const visitor,void*,Types...>();
FC_ASSERT( tag >= 0 && tag < count(), "Unsupported type ${tag}!", ("tag",tag) );
return wrappers[tag]( v, data );
}

template<typename visitor>
static typename visitor::result_type visit( tag_type tag, visitor& v, const void* data )
{
static auto wrappers = init_const_wrappers<visitor,const void*,Types...>();
FC_ASSERT( tag >= 0 && tag < count(), "Unsupported type ${tag}!", ("tag",tag) );
return wrappers[tag]( v, data );
}

template<typename visitor>
static typename visitor::result_type visit( tag_type tag, const visitor& v, const void* data )
{
static auto wrappers = init_const_wrappers<const visitor,const void*,Types...>();
FC_ASSERT( tag >= 0 && tag < count(), "Unsupported type ${tag}!", ("tag",tag) );
return wrappers[tag]( v, data );
}

static int count() { return impl::type_info<Types...>::count; }
Expand Down
2 changes: 2 additions & 0 deletions include/fc/variant.hpp
Expand Up @@ -92,6 +92,8 @@ namespace fc
void to_variant( const uint64_t& var, variant& vo, uint32_t max_depth = 1 );
void to_variant( const int64_t& var, variant& vo, uint32_t max_depth = 1 );

void to_variant( const bool& var, variant& vo, uint32_t max_depth = 1 );

void to_variant( const variant_object& var, variant& vo, uint32_t max_depth );
void from_variant( const variant& var, variant_object& vo, uint32_t max_depth );
void to_variant( const mutable_variant_object& var, variant& vo, uint32_t max_depth );
Expand Down
1 change: 1 addition & 0 deletions src/variant.cpp
Expand Up @@ -629,6 +629,7 @@ void from_variant( const variant& var, uint64_t& vo, uint32_t max_depth )
vo = var.as_uint64();
}

void to_variant( const bool& var, variant& vo, uint32_t max_depth ) { vo = uint64_t(var); }
void from_variant( const variant& var, bool& vo, uint32_t max_depth )
{
vo = var.as_bool();
Expand Down
38 changes: 38 additions & 0 deletions tests/stacktrace_test.cpp
@@ -1,9 +1,15 @@
#include <boost/test/unit_test.hpp>

#include <boost/algorithm/string.hpp>

#include <signal.h>

#include <fc/stacktrace.hpp>
#include <fc/static_variant.hpp>
#include <fc/thread/thread.hpp>

#include <iostream>

BOOST_AUTO_TEST_SUITE(fc_stacktrace)

BOOST_AUTO_TEST_CASE(stacktrace_test)
Expand Down Expand Up @@ -40,6 +46,38 @@ BOOST_AUTO_TEST_CASE(threaded_stacktrace_test)
#endif
}

#if BOOST_VERSION / 100000 >= 1 && ((BOOST_VERSION / 100) % 1000) >= 65
class _svdt_visitor
{
public:
typedef std::string result_type;
std::string operator()( int64_t i )const
{
std::stringstream ss;
fc::print_stacktrace(ss);
return ss.str();
}
template<typename T>
std::string operator()( T i )const { return "Unexpected!"; }
};

BOOST_AUTO_TEST_CASE(static_variant_depth_test)
{
int64_t i = 1;
fc::static_variant<uint8_t,uint16_t,uint32_t,uint64_t,int8_t,int16_t,int32_t,int64_t> test(i);

std::string stacktrace = test.visit( _svdt_visitor() );
//std::cerr << stacktrace << "\n";
std::vector<std::string> lines;
boost::split( lines, stacktrace, boost::is_any_of("\n") );
int count = 0;
for( const auto& line : lines )
if( line.find("_svdt_visitor") != std::string::npos ) count++;
BOOST_CHECK_LT( 3, count ); // test.visit(), static_variant::visit, function object, visitor
BOOST_CHECK_GT( 8, count ); // some is implementation-dependent
}
#endif

/* this test causes a segfault on purpose to test the event handler
BOOST_AUTO_TEST_CASE(cause_segfault)
{
Expand Down

0 comments on commit bcdaaaa

Please sign in to comment.