Page Menu
Home
c4science
Search
Configure Global Search
Log In
Files
F77853238
Kokkos_Utilities.hpp
No One
Temporary
Actions
Download File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Award Token
Subscribers
None
File Metadata
Details
File Info
Storage
Attached
Created
Fri, Aug 16, 19:39
Size
12 KB
Mime Type
text/x-c++
Expires
Sun, Aug 18, 19:39 (2 d)
Engine
blob
Format
Raw Data
Handle
19933368
Attached To
rLAMMPS lammps
Kokkos_Utilities.hpp
View Options
/*
//@HEADER
// ************************************************************************
//
// Kokkos v. 2.0
// Copyright (2014) Sandia Corporation
//
// Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation,
// the U.S. Government retains certain rights in this software.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// 1. Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// 2. Redistributions in binary form must reproduce the above copyright
// notice, this list of conditions and the following disclaimer in the
// documentation and/or other materials provided with the distribution.
//
// 3. Neither the name of the Corporation nor the names of the
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY
// EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
// PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE
// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
//
// Questions? Contact H. Carter Edwards (hcedwar@sandia.gov)
//
// ************************************************************************
//@HEADER
*/
#ifndef KOKKOS_CORE_IMPL_UTILITIES_HPP
#define KOKKOS_CORE_IMPL_UTILITIES_HPP
#include <Kokkos_Macros.hpp>
#include <cstdint>
#include <type_traits>
//----------------------------------------------------------------------------
//----------------------------------------------------------------------------
namespace Kokkos { namespace Impl {
// same as std::forward
// needed to allow perfect forwarding on the device
template <typename T>
KOKKOS_INLINE_FUNCTION
constexpr
T&& forward( typename std::remove_reference<T>::type& arg ) noexcept
{ return static_cast<T&&>(arg); }
template <typename T>
KOKKOS_INLINE_FUNCTION
constexpr
T&& forward( typename std::remove_reference<T>::type&& arg ) noexcept
{ return static_cast<T&&>(arg); }
// same as std::move
// needed to allowing moving on the device
template <typename T>
KOKKOS_INLINE_FUNCTION
constexpr
typename std::remove_reference<T>::type&& move( T&& arg ) noexcept
{ return static_cast<typename std::remove_reference<T>::type&&>(arg); }
// empty function to allow expanding a variadic argument pack
template<typename... Args>
KOKKOS_INLINE_FUNCTION
void expand_variadic(Args &&...) {}
//----------------------------------------
// C++14 integer sequence
template< typename T , T ... Ints >
struct integer_sequence {
using value_type = T ;
static constexpr std::size_t size() noexcept { return sizeof...(Ints); }
};
template< typename T , std::size_t N >
struct make_integer_sequence_helper ;
template< typename T , T N >
using make_integer_sequence =
typename make_integer_sequence_helper<T,N>::type ;
template< typename T >
struct make_integer_sequence_helper< T , 0 >
{ using type = integer_sequence<T> ; };
template< typename T >
struct make_integer_sequence_helper< T , 1 >
{ using type = integer_sequence<T,0> ; };
template< typename T >
struct make_integer_sequence_helper< T , 2 >
{ using type = integer_sequence<T,0,1> ; };
template< typename T >
struct make_integer_sequence_helper< T , 3 >
{ using type = integer_sequence<T,0,1,2> ; };
template< typename T >
struct make_integer_sequence_helper< T , 4 >
{ using type = integer_sequence<T,0,1,2,3> ; };
template< typename T >
struct make_integer_sequence_helper< T , 5 >
{ using type = integer_sequence<T,0,1,2,3,4> ; };
template< typename T >
struct make_integer_sequence_helper< T , 6 >
{ using type = integer_sequence<T,0,1,2,3,4,5> ; };
template< typename T >
struct make_integer_sequence_helper< T , 7 >
{ using type = integer_sequence<T,0,1,2,3,4,5,6> ; };
template< typename T >
struct make_integer_sequence_helper< T , 8 >
{ using type = integer_sequence<T,0,1,2,3,4,5,6,7> ; };
template< typename X , typename Y >
struct make_integer_sequence_concat ;
template< typename T , T ... x , T ... y >
struct make_integer_sequence_concat< integer_sequence<T,x...>
, integer_sequence<T,y...> >
{ using type = integer_sequence< T , x ... , (sizeof...(x)+y)... > ; };
template< typename T , std::size_t N >
struct make_integer_sequence_helper {
using type = typename make_integer_sequence_concat
< typename make_integer_sequence_helper< T , N/2 >::type
, typename make_integer_sequence_helper< T , N - N/2 >::type
>::type ;
};
//----------------------------------------
template <std::size_t... Indices>
using index_sequence = integer_sequence<std::size_t, Indices...>;
template< std::size_t N >
using make_index_sequence = make_integer_sequence< std::size_t, N>;
//----------------------------------------
template <unsigned I, typename IntegerSequence>
struct integer_sequence_at;
template <unsigned I, typename T, T h0, T... tail>
struct integer_sequence_at<I, integer_sequence<T, h0, tail...> >
: public integer_sequence_at<I-1u, integer_sequence<T,tail...> >
{
static_assert( 8 <= I , "Reasoning Error" );
static_assert( I < integer_sequence<T, h0, tail...>::size(), "Error: Index out of bounds");
};
template < typename T, T h0, T... tail>
struct integer_sequence_at<0u, integer_sequence<T,h0, tail...> >
{
using type = T;
static constexpr T value = h0;
};
template < typename T, T h0, T h1, T... tail>
struct integer_sequence_at<1u, integer_sequence<T, h0, h1, tail...> >
{
using type = T;
static constexpr T value = h1;
};
template < typename T, T h0, T h1, T h2, T... tail>
struct integer_sequence_at<2u, integer_sequence<T, h0, h1, h2, tail...> >
{
using type = T;
static constexpr T value = h2;
};
template < typename T, T h0, T h1, T h2, T h3, T... tail>
struct integer_sequence_at<3u, integer_sequence<T, h0, h1, h2, h3, tail...> >
{
using type = T;
static constexpr T value = h3;
};
template < typename T, T h0, T h1, T h2, T h3, T h4, T... tail>
struct integer_sequence_at<4u, integer_sequence<T, h0, h1, h2, h3, h4, tail...> >
{
using type = T;
static constexpr T value = h4;
};
template < typename T, T h0, T h1, T h2, T h3, T h4, T h5, T... tail>
struct integer_sequence_at<5u, integer_sequence<T, h0, h1, h2, h3, h4, h5, tail...> >
{
using type = T;
static constexpr T value = h5;
};
template < typename T, T h0, T h1, T h2, T h3, T h4, T h5, T h6, T... tail>
struct integer_sequence_at<6u, integer_sequence<T, h0, h1, h2, h3, h4, h5, h6, tail...> >
{
using type = T;
static constexpr T value = h6;
};
template < typename T, T h0, T h1, T h2, T h3, T h4, T h5, T h6, T h7, T... tail>
struct integer_sequence_at<7u, integer_sequence<T, h0, h1, h2, h3, h4, h5, h6, h7, tail...> >
{
using type = T;
static constexpr T value = h7;
};
//----------------------------------------
template <typename T>
constexpr
T at( const unsigned, integer_sequence<T> ) noexcept
{ return ~static_cast<T>(0); }
template <typename T, T h0, T... tail>
constexpr
T at( const unsigned i, integer_sequence<T, h0> ) noexcept
{ return i==0u ? h0 : ~static_cast<T>(0); }
template <typename T, T h0, T h1>
constexpr
T at( const unsigned i, integer_sequence<T, h0, h1> ) noexcept
{ return i==0u ? h0 :
i==1u ? h1 : ~static_cast<T>(0);
}
template <typename T, T h0, T h1, T h2>
constexpr
T at( const unsigned i, integer_sequence<T, h0, h1, h2> ) noexcept
{ return i==0u ? h0 :
i==1u ? h1 :
i==2u ? h2 : ~static_cast<T>(0);
}
template <typename T, T h0, T h1, T h2, T h3>
constexpr
T at( const unsigned i, integer_sequence<T, h0, h1, h2, h3> ) noexcept
{ return i==0u ? h0 :
i==1u ? h1 :
i==2u ? h2 :
i==3u ? h3 : ~static_cast<T>(0);
}
template <typename T, T h0, T h1, T h2, T h3, T h4>
constexpr
T at( const unsigned i, integer_sequence<T, h0, h1, h2, h3, h4> ) noexcept
{ return i==0u ? h0 :
i==1u ? h1 :
i==2u ? h2 :
i==3u ? h3 :
i==4u ? h4 : ~static_cast<T>(0);
}
template <typename T, T h0, T h1, T h2, T h3, T h4, T h5>
constexpr
T at( const unsigned i, integer_sequence<T, h0, h1, h2, h3, h4, h5> ) noexcept
{ return i==0u ? h0 :
i==1u ? h1 :
i==2u ? h2 :
i==3u ? h3 :
i==4u ? h4 :
i==5u ? h5 : ~static_cast<T>(0);
}
template <typename T, T h0, T h1, T h2, T h3, T h4, T h5, T h6>
constexpr
T at( const unsigned i, integer_sequence<T, h0, h1, h2, h3, h4, h5, h6> ) noexcept
{ return i==0u ? h0 :
i==1u ? h1 :
i==2u ? h2 :
i==3u ? h3 :
i==4u ? h4 :
i==5u ? h5 :
i==6u ? h6 : ~static_cast<T>(0);
}
template <typename T, T h0, T h1, T h2, T h3, T h4, T h5, T h6, T h7, T... tail>
constexpr
T at( const unsigned i, integer_sequence<T, h0, h1, h2, h3, h4, h5, h6, h7, tail...> ) noexcept
{ return i==0u ? h0 :
i==1u ? h1 :
i==2u ? h2 :
i==3u ? h3 :
i==4u ? h4 :
i==5u ? h5 :
i==6u ? h6 :
i==7u ? h7 : at(i-8u, integer_sequence<T, tail...>{} );
}
//----------------------------------------
template < typename IntegerSequence
, typename ResultSequence = integer_sequence<typename IntegerSequence::value_type>
>
struct reverse_integer_sequence_helper;
template <typename T, T h0, T... tail, T... results>
struct reverse_integer_sequence_helper< integer_sequence<T, h0, tail...>, integer_sequence<T, results...> >
: public reverse_integer_sequence_helper< integer_sequence<T, tail...>, integer_sequence<T, h0, results...> >
{};
template <typename T, T... results>
struct reverse_integer_sequence_helper< integer_sequence<T>, integer_sequence<T, results...> >
{
using type = integer_sequence<T, results...>;
};
template <typename IntegerSequence>
using reverse_integer_sequence = typename reverse_integer_sequence_helper<IntegerSequence>::type;
//----------------------------------------
template < typename IntegerSequence
, typename Result
, typename ResultSequence = integer_sequence<typename IntegerSequence::value_type>
>
struct exclusive_scan_integer_sequence_helper;
template <typename T, T h0, T... tail, typename Result, T... results>
struct exclusive_scan_integer_sequence_helper
< integer_sequence<T, h0, tail...>
, Result
, integer_sequence<T, results...> >
: public exclusive_scan_integer_sequence_helper
< integer_sequence<T, tail...>
, std::integral_constant<T,Result::value+h0>
, integer_sequence<T, 0, (results+h0)...> >
{};
template <typename T, typename Result, T... results>
struct exclusive_scan_integer_sequence_helper
< integer_sequence<T>, Result, integer_sequence<T, results...> >
{
using type = integer_sequence<T, results...>;
static constexpr T value = Result::value ;
};
template <typename IntegerSequence>
struct exclusive_scan_integer_sequence
{
using value_type = typename IntegerSequence::value_type;
using helper =
exclusive_scan_integer_sequence_helper
< reverse_integer_sequence<IntegerSequence>
, std::integral_constant< value_type , 0 >
> ;
using type = typename helper::type ;
static constexpr value_type value = helper::value ;
};
//----------------------------------------
template < typename IntegerSequence
, typename Result
, typename ResultSequence = integer_sequence<typename IntegerSequence::value_type>
>
struct inclusive_scan_integer_sequence_helper;
template <typename T, T h0, T... tail, typename Result, T... results>
struct inclusive_scan_integer_sequence_helper
< integer_sequence<T, h0, tail...>
, Result
, integer_sequence<T, results...> >
: public inclusive_scan_integer_sequence_helper
< integer_sequence<T, tail...>
, std::integral_constant<T,Result::value+h0>
, integer_sequence<T, h0, (results+h0)...> >
{};
template <typename T, typename Result, T... results>
struct inclusive_scan_integer_sequence_helper
< integer_sequence<T>, Result, integer_sequence<T, results...> >
{
using type = integer_sequence<T, results...>;
static constexpr T value = Result::value ;
};
template <typename IntegerSequence>
struct inclusive_scan_integer_sequence
{
using value_type = typename IntegerSequence::value_type;
using helper =
inclusive_scan_integer_sequence_helper
< reverse_integer_sequence<IntegerSequence>
, std::integral_constant< value_type , 0 >
> ;
using type = typename helper::type ;
static constexpr value_type value = helper::value ;
};
}} // namespace Kokkos::Impl
#endif //KOKKOS_CORE_IMPL_UTILITIES_HPP
Event Timeline
Log In to Comment