12#ifndef MFEM_MEM_MANAGER_HPP
13#define MFEM_MEM_MANAGER_HPP
25#include <HYPRE_utilities.h>
26#if (21400 <= MFEM_HYPRE_VERSION) && (MFEM_HYPRE_VERSION < 21900)
27#include <_hypre_utilities.h>
230 if (
this == &orig) {
return *
this; }
260 explicit Memory(T *ptr,
int size,
bool own) {
Wrap(ptr, size, own); }
271 {
Wrap(ptr, size, mt, own); }
334 inline void New(
int size);
364 inline void Wrap(T *ptr,
int size,
bool own);
401 bool valid_host =
false,
bool valid_device =
true);
446 inline operator T*();
453 inline operator const T*()
const;
468 template <
typename U>
469 inline explicit operator U*();
479 template <
typename U>
480 inline explicit operator const U*()
const;
566 static constexpr std::size_t def_align_bytes_()
569 return alignof(max_align_t);
571 static constexpr std::size_t def_align_bytes = def_align_bytes_();
572 static constexpr std::size_t new_align_bytes =
573 alignof(T) > def_align_bytes ?
alignof(T) : def_align_bytes;
575 template <std::
size_t align_
bytes,
bool dummy = true>
struct Alloc
577#if __cplusplus < 201703L
578 static inline T *New(std::size_t)
581 MFEM_ASSERT(
false,
"overaligned type cannot use MemoryType::HOST");
585 static inline T *New(std::size_t size) {
return new T[size]; }
589#if __cplusplus < 201703L
590 template<
bool dummy>
struct Alloc<def_align_bytes,dummy>
592 static inline T *New(std::size_t size) {
return new T[size]; }
597 static inline T *NewHOST(std::size_t size)
599 return Alloc<new_align_bytes>::New(size);
614 template <
typename T>
friend class Memory;
617 MFEM_ENZYME_INACTIVE
static MemoryType host_mem_type;
620 MFEM_ENZYME_INACTIVE
static MemoryType device_mem_type;
623 MFEM_ENZYME_INACTIVE
static bool exists;
626 static bool Exists() {
return exists; }
637 MFEM_ENZYME_INACTIVE
static bool configured;
640#ifdef MFEM_USE_UMPIRE
641 static const char * h_umpire_name;
642 static const char * d_umpire_name;
643 static const char * d_umpire_2_name;
651 static void *New_(
void *h_tmp,
size_t bytes,
MemoryType mt,
unsigned &flags);
653 static void *New_(
void *h_tmp,
size_t bytes,
MemoryType h_mt,
654 MemoryType d_mt,
unsigned valid_flags,
unsigned &flags);
658 MFEM_ENZYME_INACTIVE
static void *Register_(
void *ptr,
void *h_ptr,
660 bool own,
bool alias,
unsigned &flags);
663 static void Register2_(
void *h_ptr,
void *d_ptr,
size_t bytes,
665 bool own,
bool alias,
unsigned &flags,
666 unsigned valid_flags);
669 static void Alias_(
void *base_h_ptr,
size_t offset,
size_t bytes,
670 unsigned base_flags,
unsigned &flags);
672 static void SetDeviceMemoryType_(
void *h_ptr,
unsigned flags,
676 MFEM_ENZYME_FN_LIKE_FREE
static void Delete_(
void *h_ptr,
MemoryType mt,
680 static void DeleteDevice_(
void *h_ptr,
unsigned & flags);
683 static bool MemoryClassCheck_(
MemoryClass mc,
void *h_ptr,
684 MemoryType h_mt,
size_t bytes,
unsigned flags);
688 MFEM_ENZYME_FN_LIKE_DYNCAST
static void *ReadWrite_(
void *h_ptr,
690 size_t bytes,
unsigned &flags);
692 MFEM_ENZYME_FN_LIKE_DYNCAST
static const void *Read_(
void *h_ptr,
694 size_t bytes,
unsigned &flags);
696 MFEM_ENZYME_FN_LIKE_DYNCAST
static void *Write_(
void *h_ptr,
MemoryType h_mt,
698 size_t bytes,
unsigned &flags);
700 static void SyncAlias_(
const void *base_h_ptr,
void *alias_h_ptr,
701 size_t alias_bytes,
unsigned base_flags,
702 unsigned &alias_flags);
706 MFEM_ENZYME_INACTIVE
static MemoryType GetDeviceMemoryType_(
void *h_ptr,
710 MFEM_ENZYME_INACTIVE
static MemoryType GetHostMemoryType_(
void *h_ptr);
713 static void CheckHostMemoryType_(
MemoryType h_mt,
void *h_ptr,
bool alias);
717 static void Copy_(
void *dest_h_ptr,
const void *src_h_ptr,
size_t bytes,
718 unsigned src_flags,
unsigned &dest_flags);
722 static void CopyToHost_(
void *dest_h_ptr,
const void *src_h_ptr,
723 size_t bytes,
unsigned src_flags);
727 static void CopyFromHost_(
void *dest_h_ptr,
const void *src_h_ptr,
728 size_t bytes,
unsigned &dest_flags);
731 static bool IsKnown_(
const void *h_ptr);
735 static bool IsAlias_(
const void *h_ptr);
738 static int CompareHostAndDevice_(
void *h_ptr,
size_t size,
unsigned flags);
747 void InsertDevice(
void *d_ptr,
void *h_ptr,
size_t bytes,
751 void InsertAlias(
const void *base_ptr,
void *alias_ptr,
752 const size_t bytes,
const bool base_is_alias);
755 void Erase(
void *h_ptr,
bool free_dev_ptr =
true);
758 void EraseDevice(
void *h_ptr);
761 void EraseAlias(
void *alias_ptr);
765 void *GetDevicePtr(
const void *h_ptr,
size_t bytes,
bool copy_data);
769 void *GetAliasDevicePtr(
const void *alias_ptr,
size_t bytes,
bool copy_data);
773 void *GetHostPtr(
const void *d_ptr,
size_t bytes,
bool copy_data);
777 void *GetAliasHostPtr(
const void *alias_ptr,
size_t bytes,
bool copy_data);
806 {
return dual_map[(int)mt]; }
825#ifdef MFEM_USE_UMPIRE
845 bool IsKnown(
const void *h_ptr) {
return IsKnown_(h_ptr); }
848 bool IsAlias(
const void *h_ptr) {
return IsAlias_(h_ptr); }
851 void RegisterCheck(
void *h_ptr);
855 int PrintPtrs(std::ostream &out =
mfem::out);
859 int PrintAliases(std::ostream &out =
mfem::out);
864#ifdef MFEM_USE_ENZYME
867 MemoryManager::Delete_(mem, MT, flags);
870 inline static void* __enzyme_allocation_like1[4] = {(
void*)
static_cast<void*(*)(
void*,
size_t,
MemoryType,
unsigned&)
>(MemoryManager::New_),
871 (
void*)1, (
void*)
"-1,2,3", (
void*)myfree
874 inline static void* __enzyme_allocation_like2[4] = {(
void*)
static_cast<void*(*)(
void*,
size_t,
MemoryType,
MemoryType,
unsigned,
unsigned&)
>(MemoryManager::New_),
875 (
void*)1, (
void*)
"-1,2,4", (
void*)MemoryManager::Delete_
883#if MFEM_HYPRE_VERSION < 21400
884#define HYPRE_MEMORY_DEVICE (0)
885#define HYPRE_MEMORY_HOST (1)
887#if MFEM_HYPRE_VERSION < 21900
894#if !defined(HYPRE_USING_GPU)
895 return HYPRE_MEMORY_HOST;
896#elif MFEM_HYPRE_VERSION < 23100
897 return HYPRE_MEMORY_DEVICE;
900 HYPRE_GetMemoryLocation(&loc);
908#if !defined(HYPRE_USING_GPU)
910#elif MFEM_HYPRE_VERSION < 23100
944 flags = OWNS_HOST | VALID_HOST;
947 (T*)MemoryManager::New_(
nullptr, size*
sizeof(T), h_mt, flags);
954 const size_t bytes = size*
sizeof(T);
956 if (mt_host) { flags = OWNS_HOST | VALID_HOST; }
959 h_ptr = (mt_host) ? h_tmp : (T*)MemoryManager::New_(h_tmp, bytes, mt, flags);
966 const size_t bytes = size*
sizeof(T);
967 this->h_mt = host_mt;
969 h_ptr = (T*)MemoryManager::New_(h_tmp, bytes, host_mt, device_mt,
978 flags = (own ? OWNS_HOST : 0) | VALID_HOST;
981 if (own && MemoryManager::Exists())
983 MemoryType h_ptr_mt = MemoryManager::GetHostMemoryType_(h_ptr);
984 MFEM_VERIFY(h_mt == h_ptr_mt,
985 "h_mt = " << (
int)h_mt <<
", h_ptr_mt = " << (
int)h_ptr_mt);
990 const size_t bytes = size*
sizeof(T);
991 MemoryManager::Register_(ptr, ptr, bytes, h_mt, own,
false, flags);
1006 flags = (own ? OWNS_HOST : 0) | VALID_HOST;
1016 h_ptr = (T*)MemoryManager::Register_(ptr, h_ptr, size*
sizeof(T), mt,
1020template <
typename T>
1022 bool own,
bool valid_host,
bool valid_device)
1029 MFEM_ASSERT(valid_host || valid_device,
"");
1030 const size_t bytes = size*
sizeof(T);
1032 MemoryManager::Register2_(h_ptr, d_ptr, bytes, h_mt, d_mt,
1034 valid_host*VALID_HOST|valid_device*VALID_DEVICE);
1037template <
typename T>
1040 MFEM_ASSERT(0 <= offset,
"invalid offset = " << offset);
1041 MFEM_ASSERT(0 <= size,
"invalid size = " << size);
1042 MFEM_ASSERT(offset + size <= base.
capacity,
1043 "invalid offset + size = " << offset + size
1044 <<
" > base capacity = " << base.
capacity);
1047 h_ptr = base.
h_ptr + offset;
1048 if (!(base.
flags & Registered))
1051#
if !defined(HYPRE_USING_GPU)
1055#elif MFEM_HYPRE_VERSION < 23100
1058 MemoryManager::Exists()
1065 MemoryManager::Register_(base.
h_ptr,
nullptr, base.
capacity*
sizeof(T),
1073 flags = (base.
flags | ALIAS) & ~(OWNS_HOST | OWNS_DEVICE);
1077 const size_t s_bytes = size*
sizeof(T);
1078 const size_t o_bytes = offset*
sizeof(T);
1079 MemoryManager::Alias_(base.
h_ptr, o_bytes, s_bytes, base.
flags, flags);
1082template <
typename T>
1086 if (!(flags & Registered))
1088 MemoryManager::Register_(h_ptr,
nullptr, capacity*
sizeof(T), h_mt,
1089 flags & OWNS_HOST, flags & ALIAS, flags);
1091 MemoryManager::SetDeviceMemoryType_(h_ptr, flags, d_mt);
1094template <
typename T>
1097 const bool registered = flags & Registered;
1099 const bool std_delete = !registered && mt_host;
1103 MemoryManager::Delete_((
void*)h_ptr, h_mt, flags);
1108 if (flags & OWNS_HOST) {
delete [] h_ptr; }
1113template <
typename T>
1116 if (flags & Registered)
1119 MemoryManager::DeleteDevice_((
void*)h_ptr, flags);
1123template <
typename T>
1126 MFEM_ASSERT((flags & VALID_HOST) && !(flags & VALID_DEVICE),
1127 "invalid host pointer access");
1131template <
typename T>
1134 MFEM_ASSERT((flags & VALID_HOST),
"invalid host pointer access");
1138template <
typename T>
1141 MFEM_ASSERT(Empty() ||
1142 ((flags & VALID_HOST) &&
1143 (std::is_const<T>::value || !(flags & VALID_DEVICE))),
1144 "invalid host pointer access");
1148template <
typename T>
1151 MFEM_ASSERT(Empty() || (flags & VALID_HOST),
"invalid host pointer access");
1155template <
typename T>
template <
typename U>
1158 MFEM_ASSERT(Empty() ||
1159 ((flags & VALID_HOST) &&
1160 (std::is_const<U>::value || !(flags & VALID_DEVICE))),
1161 "invalid host pointer access");
1162 return reinterpret_cast<U*
>(h_ptr);
1165template <
typename T>
template <
typename U>
1168 MFEM_ASSERT(Empty() || (flags & VALID_HOST),
"invalid host pointer access");
1169 return reinterpret_cast<U*
>(h_ptr);
1172template <
typename T>
1175 const size_t bytes = size *
sizeof(T);
1176 if (!(flags & Registered))
1179 MemoryManager::Register_(h_ptr,
nullptr, capacity*
sizeof(T), h_mt,
1180 flags & OWNS_HOST, flags & ALIAS, flags);
1182 return (T*)MemoryManager::ReadWrite_(h_ptr, h_mt, mc, bytes, flags);
1185template <
typename T>
1188 const size_t bytes = size *
sizeof(T);
1189 if (!(flags & Registered))
1192 MemoryManager::Register_(h_ptr,
nullptr, capacity*
sizeof(T), h_mt,
1193 flags & OWNS_HOST, flags & ALIAS, flags);
1195 return (
const T*)MemoryManager::Read_(h_ptr, h_mt, mc, bytes, flags);
1198template <
typename T>
1201 const size_t bytes = size *
sizeof(T);
1202 if (!(flags & Registered))
1205 MemoryManager::Register_(h_ptr,
nullptr, capacity*
sizeof(T), h_mt,
1206 flags & OWNS_HOST, flags & ALIAS, flags);
1208 return (T*)MemoryManager::Write_(h_ptr, h_mt, mc, bytes, flags);
1211template <
typename T>
1214 if (!(flags & Registered) && (other.
flags & Registered))
1216 MFEM_ASSERT(h_ptr == other.
h_ptr &&
1217 (flags & ALIAS) == (other.
flags & ALIAS),
1219 flags = (flags | Registered) & ~(OWNS_DEVICE | OWNS_INTERNAL);
1221 flags = (flags & ~(VALID_HOST | VALID_DEVICE)) |
1222 (other.
flags & (VALID_HOST | VALID_DEVICE));
1225template <
typename T>
1229 MFEM_ASSERT(!(flags & Registered) || (base.
flags & Registered),
1230 "invalid base state");
1231 if (!(base.
flags & Registered)) {
return; }
1232 MemoryManager::SyncAlias_(base.
h_ptr, h_ptr, alias_size*
sizeof(T),
1236template <
typename T>
1239 if (h_ptr ==
nullptr || !(flags & VALID_DEVICE)) {
return h_mt; }
1240 return MemoryManager::GetDeviceMemoryType_(h_ptr, flags & ALIAS);
1243template <
typename T>
1247 return MemoryManager::GetDeviceMemoryType_(h_ptr, flags & ALIAS);
1250template <
typename T>
1253 return flags & VALID_HOST ? true :
false;
1256template <
typename T>
1259 return flags & VALID_DEVICE ? true :
false;
1262template <
typename T>
1265 MFEM_VERIFY(src.
capacity>=size && capacity>=size,
"Incorrect size");
1266 if (size <= 0) {
return; }
1267 if (!(flags & Registered) && !(src.
flags & Registered))
1269 if (h_ptr != src.
h_ptr)
1271 MFEM_ASSERT(h_ptr + size <= src.
h_ptr || src.
h_ptr + size <= h_ptr,
1273 std::memcpy(h_ptr, src, size*
sizeof(T));
1279 MemoryManager::Copy_(h_ptr, src.
h_ptr, size*
sizeof(T), src.
flags, flags);
1283template <
typename T>
1286 MFEM_VERIFY(capacity>=size,
"Incorrect size");
1287 if (size <= 0) {
return; }
1288 if (!(flags & Registered))
1292 MFEM_ASSERT(h_ptr + size <= src || src + size <= h_ptr,
1294 std::memcpy(h_ptr, src, size*
sizeof(T));
1300 MemoryManager::CopyFromHost_(h_ptr, src, size*
sizeof(T), flags);
1304template <
typename T>
1310template <
typename T>
1313 MFEM_VERIFY(capacity>=size,
"Incorrect size");
1314 if (size <= 0) {
return; }
1315 if (!(flags & Registered))
1319 MFEM_ASSERT(h_ptr + size <= dest || dest + size <= h_ptr,
1321 std::memcpy(dest, h_ptr, size*
sizeof(T));
1326 MemoryManager::CopyToHost_(dest, h_ptr, size*
sizeof(T), flags);
1336template <
typename T>
1342template <
typename T>
1345 if (!(flags & VALID_HOST) || !(flags & VALID_DEVICE)) {
return 0; }
1346 return MemoryManager::CompareHostAndDevice_(h_ptr, size*
sizeof(T), flags);
A class to initialize the size of a Tensor.
bool IsKnown(const void *h_ptr)
Return true if the pointer is known by the memory manager.
static void SetUmpireDeviceAllocatorName(const char *d_name)
Set the device Umpire allocator name used with MemoryType::DEVICE_UMPIRE.
static void myfree(void *mem, MemoryType MT, unsigned &flags)
static const char * GetUmpireHostAllocatorName()
Get the host Umpire allocator name used with MemoryType::HOST_UMPIRE.
static void SetUmpireHostAllocatorName(const char *h_name)
Set the host Umpire allocator name used with MemoryType::HOST_UMPIRE.
static MemoryType GetHostMemoryType()
bool IsAlias(const void *h_ptr)
Return true if the pointer is known by the memory manager as an alias.
static const char * GetUmpireDevice2AllocatorName()
Get the device Umpire allocator name used with MemoryType::DEVICE_UMPIRE_2.
static void SetUmpireDevice2AllocatorName(const char *d_name)
Set the device Umpire allocator name used with MemoryType::DEVICE_UMPIRE_2.
static MemoryType GetDeviceMemoryType()
static MemoryType GetDualMemoryType(MemoryType mt)
Return the dual MemoryType of the given one, mt.
__attribute__((used)) inline static void *__enzyme_allocation_like2[4]
static const char * GetUmpireDeviceAllocatorName()
Get the device Umpire allocator name used with MemoryType::DEVICE_UMPIRE.
__attribute__((used)) inline static void *__enzyme_allocation_like1[4]
Class used by MFEM to store pointers to host and/or device memory.
void SetHostPtrOwner(bool own) const
Set/clear the ownership flag for the host pointer. Ownership indicates whether the pointer will be de...
void New(int size, MemoryType mt)
Allocate memory for size entries with the given MemoryType.
bool OwnsDevicePtr() const
Return true if the device pointer is owned. Ownership indicates whether the pointer will be deleted b...
T * Write(MemoryClass mc, int size)
Get write-only access to the memory with the given MemoryClass.
Memory(int size, MemoryType mt)
Allocate memory for size entries with the given MemoryType mt.
void Wrap(T *ptr, int size, MemoryType mt, bool own)
Wrap an externally allocated pointer, ptr, of the given MemoryType.
Memory(const Memory &base, int offset, int size)
Alias constructor. Create a Memory object that points inside the Memory object base.
MemoryType GetHostMemoryType() const
Return the host MemoryType of the Memory object.
bool DeviceIsValid() const
Return true if device pointer is valid.
Memory(int size, MemoryType h_mt, MemoryType d_mt)
Allocate memory for size entries with the given host MemoryType h_mt and device MemoryType d_mt.
void SetDeviceMemoryType(MemoryType d_mt)
Set the device MemoryType to be used by the Memory object.
void SetDevicePtrOwner(bool own) const
Set/clear the ownership flag for the device pointer. Ownership indicates whether the pointer will be ...
int Capacity() const
Return the size of the allocated memory.
void CopyFromHost(const T *src, int size)
Copy size entries from the host pointer src to *this.
T & operator[](int idx)
Array subscript operator for host memory.
void New(int size, MemoryType h_mt, MemoryType d_mt)
Allocate memory for size entries with the given host MemoryType h_mt and device MemoryType d_mt.
@ OWNS_INTERNAL
Ownership flag for internal Memory data.
@ VALID_HOST
Host pointer is valid.
@ OWNS_HOST
The host pointer will be deleted by Delete()
@ VALID_DEVICE
Device pointer is valid
@ ALIAS
Pointer is an alias.
MemoryType GetDeviceMemoryType() const
Return the device MemoryType of the Memory object. If the device MemoryType is not set,...
T * ReadWrite(MemoryClass mc, int size)
Get read-write access to the memory with the given MemoryClass.
MemoryType h_mt
Host memory type.
Memory & operator=(const Memory &orig)=default
Copy-assignment operator: default.
void Reset(MemoryType host_mt)
Reset the memory and set the host memory type.
void MakeAlias(const Memory &base, int offset, int size)
Create a memory object that points inside the memory object base.
bool HostIsValid() const
Return true if host pointer is valid.
~Memory()=default
Destructor: default.
bool UseDevice() const
Read the internal device flag.
void CopyToHost(T *dest, int size) const
Copy size entries from *this to the host pointer dest.
void SyncAlias(const Memory &base, int alias_size) const
Update the alias Memory *this to match the memory location (all valid locations) of its base Memory,...
bool OwnsHostPtr() const
Return true if the host pointer is owned. Ownership indicates whether the pointer will be deleted by ...
friend void MemoryPrintFlags(unsigned flags)
Print the state of a Memory object based on its internal flags. Useful in a debugger....
MemoryType GetMemoryType() const
Return a MemoryType that is currently valid. If both the host and the device pointers are currently v...
bool Empty() const
Return true if the Memory object is empty, see Reset().
T * h_ptr
Pointer to host memory. Not owned.
void Sync(const Memory &other) const
Copy the host/device pointer validity flags from other to *this.
Memory(const Memory &orig)=default
Copy constructor: default.
void PrintFlags() const
Print the internal flags.
void DeleteDevice(bool copy_to_host=true)
Delete the device pointer, if owned. If copy_to_host is true and the data is valid only on device,...
unsigned flags
Bit flags defined from the FlagMask enum.
const T * Read(MemoryClass mc, int size) const
Get read-only access to the memory with the given MemoryClass.
void UseDevice(bool use_dev) const
Set the internal device flag.
int CompareHostAndDevice(int size) const
If both the host and the device data are valid, compare their contents.
void CopyFrom(const Memory &src, int size)
Copy size entries from src to *this.
void Reset()
Reset the memory to be empty, ensuring that Delete() will be a no-op.
Memory(int size)
Allocate host memory for size entries.
void Wrap(T *ptr, int size, bool own)
Wrap an externally allocated host pointer, ptr with the current host memory type returned by MemoryMa...
void Delete()
Delete the owned pointers and reset the Memory object.
Memory(T *ptr, int size, MemoryType mt, bool own)
Wrap an externally allocated pointer, ptr, of the given MemoryType.
void CopyTo(Memory &dest, int size) const
Copy size entries from *this to dest.
void ClearOwnerFlags() const
Clear the ownership flags for the host and device pointers, as well as any internal data allocated by...
const T & operator[](int idx) const
Array subscript operator for host memory, const version.
Memory(MemoryType mt)
Creates a new empty Memory object with host MemoryType mt.
void Wrap(T *h_ptr, T *d_ptr, int size, MemoryType h_mt, bool own, bool valid_host=false, bool valid_device=true)
int capacity
Size of the allocated memory.
void New(int size)
Allocate host memory for size entries with the current host memory type returned by MemoryManager::Ge...
Memory & operator=(Memory &&orig)
Memory(T *ptr, int size, bool own)
Wrap an externally allocated host pointer, ptr with the current host memory type returned by MemoryMa...
bool IsDeviceMemory(MemoryType mt)
Return true if the given memory type is in MemoryClass::DEVICE.
const T * Read(const Memory< T > &mem, int size, bool on_dev=true)
Get a pointer for read access to mem with the mfem::Device's DeviceMemoryClass, if on_dev = true,...
constexpr int DeviceMemoryType
MemoryClass operator*(MemoryClass mc1, MemoryClass mc2)
Return a suitable MemoryClass from a pair of MemoryClasses.
OutStream out(std::cout)
Global stream used by the library for standard output. Initially it uses the same std::streambuf as s...
MemoryClass
Memory classes identify sets of memory types.
constexpr int MemoryTypeSize
Static casts to 'int' and sizes of some useful memory types.
MemoryManager mm
The (single) global memory manager object.
MemoryType GetMemoryType(MemoryClass mc)
Return a suitable MemoryType for a given MemoryClass.
constexpr int HostMemoryTypeSize
bool IsHostMemory(MemoryType mt)
Return true if the given memory type is in MemoryClass::HOST.
const char * MemoryTypeName[MemoryTypeSize]
Memory type names, used during Device:: configuration.
constexpr int HostMemoryType
bool HypreUsingGPU()
Return true if HYPRE is configured to use GPU.
constexpr int DeviceMemoryTypeSize
MemoryType
Memory types supported by MFEM.
@ HOST_32
Host memory; aligned at 32 bytes.
@ SIZE
Number of host and device memory types.
@ HOST_64
Host memory; aligned at 64 bytes.
@ HOST
Host memory; using new[] and delete[].
@ HOST_PINNED
Host memory: pinned (page-locked)
@ HOST_DEBUG
Host memory; allocated from a "host-debug" pool.
@ DEVICE
Device memory; using CUDA or HIP *Malloc and *Free.
HYPRE_MemoryLocation GetHypreMemoryLocation()
Return the configured HYPRE_MemoryLocation.
void MemoryPrintFlags(unsigned flags)
Print the state of a Memory object based on its internal flags. Useful in a debugger....
bool MemoryClassContainsType(MemoryClass mc, MemoryType mt)
Return true iff the MemoryType mt is contained in the MemoryClass mc.