190 changes: 79 additions & 111 deletions include/boost/context/continuation_winfib.hpp

Large diffs are not rendered by default.

9 changes: 9 additions & 0 deletions include/boost/context/detail/config.hpp
Expand Up @@ -104,4 +104,13 @@
# endif
#endif

// modern architectures have cachelines with 64byte length
// ARM Cortex-A15 32/64byte, Cortex-A9 16/32/64bytes
// MIPS 74K: 32byte, 4KEc: 16byte
// ist should be safe to use 64byte for all
static constexpr std::size_t cache_alignment{ 64 };
static constexpr std::size_t cacheline_length{ 64 };
// lookahead size for prefetching
static constexpr std::size_t prefetch_stride{ 4 * cacheline_length };

#endif // BOOST_CONTEXT_DETAIL_CONFIG_H
78 changes: 78 additions & 0 deletions include/boost/context/detail/prefetch.hpp
@@ -0,0 +1,78 @@
// Copyright Oliver Kowalke 2017.
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)

#ifndef BOOST_CONTEXT_DETAIL_PREFETCH_H
#define BOOST_CONTEXT_DETAIL_PREFETCH_H

#include <cstddef>
#include <cstdint>

#include <boost/config.hpp>
#include <boost/predef.h>

#include <boost/context/detail/config.hpp>

#if BOOST_COMP_INTEL || BOOST_COMP_INTEL_EMULATED
#include <immintrin.h>
#endif

#if BOOST_COMP_MSVC
#include <mmintrin.h>
#endif

#ifdef BOOST_HAS_ABI_HEADERS
# include BOOST_ABI_PREFIX
#endif

namespace boost {
namespace context {
namespace detail {

#if BOOST_COMP_GNUC || BOOST_COMP_CLANG
#define BOOST_HAS_PREFETCH 1
BOOST_FORCEINLINE
void prefetch( void * addr) {
// L1 cache : hint == 1
__builtin_prefetch( addr, 1, 1);
}
#elif BOOST_COMP_INTEL || BOOST_COMP_INTEL_EMULATED
#define BOOST_HAS_PREFETCH 1
BOOST_FORCEINLINE
void prefetch( void * addr) {
// L1 cache : hint == _MM_HINT_T0
_mm_prefetch( (const char *)addr, _MM_HINT_T0);
}
#elif BOOST_COMP_MSVC
#define BOOST_HAS_PREFETCH 1
BOOST_FORCEINLINE
void prefetch( void * addr) {
// L1 cache : hint == _MM_HINT_T0
_mm_prefetch( (const char *)addr, _MM_HINT_T0);
}
#endif

inline
void prefetch_range( void * addr, std::size_t len) {
#if defined(BOOST_HAS_PREFETCH)
void * vp = addr;
void * end = reinterpret_cast< void * >(
reinterpret_cast< uintptr_t >( addr) + static_cast< uintptr_t >( len) );
while ( vp < end) {
prefetch( vp);
vp = reinterpret_cast< void * >(
reinterpret_cast< uintptr_t >( vp) + static_cast< uintptr_t >( prefetch_stride) );
}
#endif
}

#undef BOOST_HAS_PREFETCH

}}}

#ifdef BOOST_HAS_ABI_HEADERS
# include BOOST_ABI_SUFFIX
#endif

#endif // BOOST_CONTEXT_DETAIL_PREFETCH_H
49 changes: 47 additions & 2 deletions test/Jamfile.v2
Expand Up @@ -25,9 +25,23 @@ project boost/context/test
<link>static
<threading>multi
<optimization>speed
<variant>release
;


rule configure-impl ( properties * )
{
local result ;
if ( ! ( <target-os>windows in $(properties) ) )
{
result = <context-impl>ucontext ;
}
else
{
result = <context-impl>winfib ;
}
return $(result) ;
}

test-suite minimal :
[ run test_invoke.cpp :
: :
Expand Down Expand Up @@ -63,6 +77,7 @@ test-suite minimal :

[ run test_callcc.cpp :
: :
<context-impl>fcontext
[ requires cxx11_auto_declarations
cxx11_constexpr
cxx11_defaulted_functions
Expand All @@ -75,7 +90,37 @@ test-suite minimal :
cxx11_rvalue_references
cxx11_template_aliases
cxx11_thread_local
cxx11_variadic_templates ] ] ;
cxx11_variadic_templates ]
: test_callcc_asm ]

test-suite full :
minimal ;

test-suite fc :
[ run test_fcontext.cpp :
: :
] ;

test-suite ec :
[ run test_execution_context.cpp :
: :
<conditional>@configure-impl
[ requires cxx11_auto_declarations
cxx11_constexpr
cxx11_defaulted_functions
cxx11_final
cxx11_hdr_thread
cxx11_hdr_tuple
cxx11_lambdas
cxx11_noexcept
cxx11_nullptr
cxx11_rvalue_references
cxx11_template_aliases
cxx11_thread_local
cxx11_variadic_templates ]
: test_call_native ] ;



test-suite full :
minimal ;
Expand Down
2 changes: 1 addition & 1 deletion test/test_callcc.cpp
Expand Up @@ -35,7 +35,7 @@

#if defined(BOOST_MSVC)
# pragma warning(push)
# pragma warning(disable: 4723)
# pragma warning(disable: 4702 4723 4996)
#endif

typedef boost::variant<int,std::string> variant_t;
Expand Down