/*============================================================================= Copyright (c) 2011-2018 Bolero MURAKAMI https://github.com/bolero-MURAKAMI/Sprout 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 SPROUT_CSTRING_MEMCHR_HPP #define SPROUT_CSTRING_MEMCHR_HPP #include #include #include #include #include #include #include namespace sprout { namespace detail { template struct memchr_result { private: static void const* test(void const*); static void* test(void*); static void test(...); public: typedef decltype(test(std::declval())) type; }; template inline SPROUT_CONSTEXPR PtrIterator memchr_impl(PtrIterator found, PtrIterator last) { return found == last ? nullptr : found ; } template inline SPROUT_CONSTEXPR PtrIterator memchr(PtrIterator s, T c, std::size_t n) { return sprout::detail::memchr_impl( sprout::ptr_unindex( sprout::find( sprout::ptr_index(s), sprout::ptr_index(s, n), c ) ), s + n ); } } // namespace detail // 7.21.5.1 memchr function // // recursion depth: // O(log N) // #if 0 inline SPROUT_CONSTEXPR void const* memchr(void const* s, int c, std::size_t n) { return sprout::detail::memchr(static_cast(s), static_cast(c), n); } inline SPROUT_CONSTEXPR void* memchr(void* s, int c, std::size_t n) { return sprout::detail::memchr(static_cast(s), static_cast(c), n); } #endif template< typename T, typename sprout::enabler_if::type, void const*>::value>::type = sprout::enabler > inline SPROUT_CONSTEXPR void const* memchr(T s, int c, std::size_t n) { return sprout::detail::memchr(static_cast(s), static_cast(c), n); } template< typename T, typename sprout::enabler_if::type, void*>::value>::type = sprout::enabler > inline SPROUT_CONSTEXPR void* memchr(T s, int c, std::size_t n) { return sprout::detail::memchr(static_cast(s), static_cast(c), n); } } // namespace sprout #endif // #ifndef SPROUT_CSTRING_MEMCHR_HPP