summaryrefslogtreecommitdiff
path: root/libs/context/src/windows/stack_traits.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'libs/context/src/windows/stack_traits.cpp')
-rw-r--r--libs/context/src/windows/stack_traits.cpp124
1 files changed, 124 insertions, 0 deletions
diff --git a/libs/context/src/windows/stack_traits.cpp b/libs/context/src/windows/stack_traits.cpp
new file mode 100644
index 000000000..7e67232e7
--- /dev/null
+++ b/libs/context/src/windows/stack_traits.cpp
@@ -0,0 +1,124 @@
+
+// Copyright Oliver Kowalke 2014.
+// 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)
+
+#include "boost/context/stack_traits.hpp"
+
+extern "C" {
+#include <windows.h>
+}
+
+//#if defined (BOOST_WINDOWS) || _POSIX_C_SOURCE >= 200112L
+
+#include <algorithm>
+#include <cmath>
+#include <cstddef>
+#include <cstring>
+#include <stdexcept>
+
+#include <boost/assert.hpp>
+#include <boost/context/detail/config.hpp>
+#if __cplusplus < 201103L
+# include <boost/thread.hpp>
+#else
+# include <mutex>
+#endif
+
+#include <boost/context/stack_context.hpp>
+
+// x86_64
+// test x86_64 before i386 because icc might
+// define __i686__ for x86_64 too
+#if defined(__x86_64__) || defined(__x86_64) \
+ || defined(__amd64__) || defined(__amd64) \
+ || defined(_M_X64) || defined(_M_AMD64)
+
+// Windows seams not to provide a constant or function
+// telling the minimal stacksize
+# define MIN_STACKSIZE 8 * 1024
+#else
+# define MIN_STACKSIZE 4 * 1024
+#endif
+
+#ifdef BOOST_HAS_ABI_HEADERS
+# include BOOST_ABI_PREFIX
+#endif
+
+namespace boost {
+namespace context {
+
+#if __cplusplus < 201103L
+void system_info_( SYSTEM_INFO * si)
+{ ::GetSystemInfo( si); }
+
+SYSTEM_INFO system_info()
+{
+ static SYSTEM_INFO si;
+ static boost::once_flag flag;
+ boost::call_once( flag, static_cast< void(*)( SYSTEM_INFO *) >( system_info_), & si);
+ return si;
+}
+#else
+SYSTEM_INFO system_info()
+{
+ static SYSTEM_INFO si;
+ static std::once_flag flag;
+ std::call_once( flag, [](){ ::GetSystemInfo( & si); } );
+ return si;
+}
+#endif
+
+std::size_t pagesize()
+{ return static_cast< std::size_t >( system_info().dwPageSize); }
+
+std::size_t page_count( std::size_t stacksize)
+{
+ return static_cast< std::size_t >(
+ std::floor(
+ static_cast< float >( stacksize) / pagesize() ) );
+}
+
+// Windows seams not to provide a limit for the stacksize
+// libcoco uses 32k+4k bytes as minimum
+bool
+stack_traits::is_unbounded() BOOST_NOEXCEPT
+{ return true; }
+
+std::size_t
+stack_traits::page_size() BOOST_NOEXCEPT
+{ return pagesize(); }
+
+std::size_t
+stack_traits::default_size() BOOST_NOEXCEPT
+{
+ std::size_t size = 64 * 1024; // 64 kB
+ if ( is_unbounded() )
+ return (std::max)( size, minimum_size() );
+
+ BOOST_ASSERT( maximum_size() >= minimum_size() );
+ return maximum_size() == minimum_size()
+ ? minimum_size()
+ : ( std::min)( size, maximum_size() );
+}
+
+// because Windows seams not to provide a limit for minimum stacksize
+std::size_t
+stack_traits::minimum_size() BOOST_NOEXCEPT
+{ return MIN_STACKSIZE; }
+
+// because Windows seams not to provide a limit for maximum stacksize
+// maximum_size() can never be called (pre-condition ! is_unbounded() )
+std::size_t
+stack_traits::maximum_size() BOOST_NOEXCEPT
+{
+ BOOST_ASSERT( ! is_unbounded() );
+ return 1 * 1024 * 1024 * 1024; // 1GB
+}
+
+}}
+
+#ifdef BOOST_HAS_ABI_HEADERS
+# include BOOST_ABI_SUFFIX
+#endif