#ifndef KOKKOS_OPENMPTARGETSPACE_HPP
#define KOKKOS_OPENMPTARGETSPACE_HPP
#include <cstring>
#include <string>
#include <iosfwd>
#include <typeinfo>
#include <Kokkos_Core_fwd.hpp>
#ifdef KOKKOS_ENABLE_OPENMPTARGET
#include <Kokkos_HostSpace.hpp>
#include <omp.h>
namespace Kokkos {
namespace Impl {
} }
namespace Kokkos {
namespace Experimental {
class OpenMPTargetSpace {
public:
typedef OpenMPTargetSpace memory_space ;
typedef size_t size_type ;
typedef Kokkos::Experimental::OpenMPTarget execution_space ;
typedef Kokkos::Device<execution_space,memory_space> device_type;
OpenMPTargetSpace();
OpenMPTargetSpace( OpenMPTargetSpace && rhs ) = default ;
OpenMPTargetSpace( const OpenMPTargetSpace & rhs ) = default ;
OpenMPTargetSpace & operator = ( OpenMPTargetSpace && ) = default ;
OpenMPTargetSpace & operator = ( const OpenMPTargetSpace & ) = default ;
~OpenMPTargetSpace() = default ;
void * allocate( const size_t arg_alloc_size ) const ;
void deallocate( void * const arg_alloc_ptr
, const size_t arg_alloc_size ) const ;
private:
friend class Kokkos::Impl::SharedAllocationRecord< Kokkos::Experimental::OpenMPTargetSpace , void > ;
};
} }
namespace Kokkos {
namespace Impl {
template<>
class SharedAllocationRecord< Kokkos::Experimental::OpenMPTargetSpace , void >
: public SharedAllocationRecord< void , void >
{
private:
friend Kokkos::Experimental::OpenMPTargetSpace ;
typedef SharedAllocationRecord< void , void > RecordBase ;
SharedAllocationRecord( const SharedAllocationRecord & ) = delete ;
SharedAllocationRecord & operator = ( const SharedAllocationRecord & ) = delete ;
static void deallocate( RecordBase * );
static RecordBase s_root_record ;
const Kokkos::Experimental::OpenMPTargetSpace m_space ;
protected:
~SharedAllocationRecord();
SharedAllocationRecord() = default ;
SharedAllocationRecord( const Kokkos::Experimental::OpenMPTargetSpace & arg_space
, const std::string & arg_label
, const size_t arg_alloc_size
, const RecordBase::function_type arg_dealloc = & deallocate
);
public:
std::string get_label() const;
KOKKOS_INLINE_FUNCTION static
SharedAllocationRecord * allocate( const Kokkos::Experimental::OpenMPTargetSpace & arg_space
, const std::string & arg_label
, const size_t arg_alloc_size
);
static
void * allocate_tracked( const Kokkos::Experimental::OpenMPTargetSpace & arg_space
, const std::string & arg_label
, const size_t arg_alloc_size );
static
void * reallocate_tracked( void * const arg_alloc_ptr
, const size_t arg_alloc_size );
static
void deallocate_tracked( void * const arg_alloc_ptr );
static SharedAllocationRecord * get_record( void * arg_alloc_ptr );
static void print_records( std::ostream & , const Kokkos::Experimental::OpenMPTargetSpace & , bool detail = false );
};
} }
namespace Kokkos {
namespace Impl {
template<class ExecutionSpace>
struct DeepCopy<Kokkos::Experimental::OpenMPTargetSpace,Kokkos::Experimental::OpenMPTargetSpace,ExecutionSpace> {
DeepCopy( void * dst , const void * src , size_t n ) {
omp_target_memcpy( dst , const_cast<void*> (src) , n, 0, 0, omp_get_default_device(), omp_get_default_device());
}
DeepCopy( const ExecutionSpace& exec, void * dst , const void * src , size_t n ) {
exec.fence();
omp_target_memcpy( dst , const_cast<void*> (src) , n, 0, 0, omp_get_default_device(), omp_get_default_device());
}
};
template<class ExecutionSpace>
struct DeepCopy<Kokkos::Experimental::OpenMPTargetSpace,HostSpace,ExecutionSpace> {
DeepCopy( void * dst , const void * src , size_t n ) {
omp_target_memcpy( dst , const_cast<void*> (src) , n, 0, 0, omp_get_default_device(), omp_get_initial_device());
}
DeepCopy( const ExecutionSpace& exec, void * dst , const void * src , size_t n ) {
exec.fence();
omp_target_memcpy( dst , const_cast<void*> (src) , n, 0, 0, omp_get_default_device(), omp_get_initial_device());
}
};
template<class ExecutionSpace>
struct DeepCopy<HostSpace,Kokkos::Experimental::OpenMPTargetSpace,ExecutionSpace> {
DeepCopy( void * dst , const void * src , size_t n ) {
omp_target_memcpy( dst , const_cast<void*> (src) , n, 0, 0, omp_get_initial_device(), omp_get_default_device());
}
DeepCopy( const ExecutionSpace& exec, void * dst , const void * src , size_t n ) {
exec.fence();
omp_target_memcpy( dst , const_cast<void*> (src) , n, 0, 0, omp_get_initial_device(), omp_get_default_device());
}
};
template<>
struct VerifyExecutionCanAccessMemorySpace< Kokkos::HostSpace , Kokkos::Experimental::OpenMPTargetSpace >
{
enum { value = false };
inline static void verify( void ) { }
inline static void verify( const void * ) { }
};
} }
#endif
#endif