EXSWHTEC-380 - Implement tests for Virtual Memory Management API functions #448

Change-Id: Ic766be69fddd0309f7ad4093465494cc14c7c70b


[ROCm/hip-tests commit: 00433d4f87]
Cette révision appartient à :
Mirza Halilcevic
2024-02-02 12:29:18 +05:30
révisé par Rakesh Roy
Parent ad4d04fa88
révision d439c6b986
23 fichiers modifiés avec 1043 ajouts et 787 suppressions
+55
Voir le fichier
@@ -0,0 +1,55 @@
# Copyright (c) 2023 Advanced Micro Devices, Inc. All Rights Reserved.
#
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to deal
# in the Software without restriction, including without limitation the rights
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the Software is
# furnished to do so, subject to the following conditions:
#
# The above copyright notice and this permission notice shall be included in all
# copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
# SOFTWARE.
set(TEST_SRC
hipMemGetAllocationGranularity.cc
hipMemRetainAllocationHandle.cc)
if(HIP_PLATFORM MATCHES "nvidia")
set(TEST_SRC
${TEST_SRC}
hipMemMapArrayAsync.cc)
if(UNIX) # Disabled on AMD due to defect EXSWHTEC-375
set(TEST_SRC
${TEST_SRC}
hipMemExportToShareableHandle.cc
hipMemImportFromShareableHandle.cc)
endif()
endif()
if(HIP_PLATFORM MATCHES "amd")
set(TEST_SRC
${TEST_SRC}
hipMemAddressFree.cc
hipMemAddressReserve.cc
hipMemCreate.cc
hipMemSetGetAccess.cc
hipMemGetAllocationPropertiesFromHandle.cc
hipMemMap.cc
hipMemRelease.cc
hipMemUnmap.cc
hipMemVmm_old.cc)
endif()
hip_add_exe_to_target(NAME VirtualMemoryManagementTest
TEST_SRC ${TEST_SRC}
TEST_TARGET_NAME build_tests COMMON_SHARED_SRC ${COMMON_SHARED_SRC})
+74
Voir le fichier
@@ -0,0 +1,74 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANNTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER INN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR INN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/**
* @addtogroup hipMemAddressFree hipMemAddressFree
* @{
* @ingroup VirtualMemoryManagementTest
* `hipError_t hipMemAddressFree (void* devPtr, size_t size)` -
* Frees an address range reservation made via hipMemAddressReserve.
*/
#include <hip_test_common.hh>
#include "hip_vmm_common.hh"
#define DATA_SIZE (1 << 13)
/**
* Test Description
* ------------------------
* - Negative Tests
* ------------------------
* - unit/virtualMemoryManagement/hipMemAddressFree.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemAddressFree_negative") {
size_t granularity = 0;
constexpr int N = DATA_SIZE;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
// Allocate virtual address range
hipDeviceptr_t ptrA;
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
SECTION("nullptr to devptr") {
REQUIRE(hipMemAddressFree(nullptr, size_mem) == hipErrorInvalidValue);
}
SECTION("pass zero to size") { REQUIRE(hipMemAddressFree(ptrA, 0) == hipErrorInvalidValue); }
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
}
+150
Voir le fichier
@@ -0,0 +1,150 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANNTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER INN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR INN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/**
* @addtogroup hipMemAddressReserve hipMemAddressReserve
* @{
* @ingroup VirtualMemoryManagementTest
* `hipError_t hipMemAddressReserve (void** ptr,
* size_t size,
* size_t alignment,
* void* addr,
* unsigned long long flags)` -
* Reserves an address range.
*/
#include <hip_test_common.hh>
#include "hip_vmm_common.hh"
#define DATA_SIZE (1 << 13)
/**
* Test Description
* ------------------------
* - Verify if reserved address returned by hipMemAddressReserve
* for different alignment values are correctly aligned.
* ------------------------
* - unit/virtualMemoryManagement/hipMemAddressReserve.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemAddressReserve_AlignmentTest") {
size_t granularity = 0;
constexpr int N = DATA_SIZE;
size_t buffer_size = N * sizeof(int);
constexpr int initializer = 0;
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
// Allocate virtual address range
hipDeviceptr_t ptrA;
size_t alignmnt = 1;
hipMemGenericAllocationHandle_t handle;
// Allocate physical memory
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate host memory and intialize data
std::vector<int> A_h(N), B_h(N);
// Initialize with data
for (size_t idx = 0; idx < N; idx++) {
A_h[idx] = idx;
}
// check for address alignment fron 2 to 1024
for (int iter = 0; iter < 12; iter++) {
alignmnt = alignmnt * 2;
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, alignmnt, 0, 0));
REQUIRE((reinterpret_cast<size_t>(ptrA) % alignmnt) == 0);
std::fill(B_h.begin(), B_h.end(), initializer);
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle, 0));
// Set access
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
// Make the address accessible to GPU 0
HIP_CHECK(hipMemSetAccess(ptrA, size_mem, &accessDesc, 1));
HIP_CHECK(hipMemcpyHtoD(ptrA, A_h.data(), buffer_size));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, buffer_size));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), A_h.data()));
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
}
HIP_CHECK(hipMemRelease(handle));
}
/**
* Test Description
* ------------------------
* - Negative Tests
* ------------------------
* - unit/virtualMemoryManagement/hipMemAddressReserve.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemAddressReserve_Negative") {
size_t granularity = 0;
constexpr int N = DATA_SIZE;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
// Allocate virtual address range
hipDeviceptr_t ptrA;
SECTION("Nullptr to ptr") {
REQUIRE(hipMemAddressReserve(nullptr, size_mem, 0, 0, 0) == hipErrorInvalidValue);
}
SECTION("pass size as 0") {
REQUIRE(hipMemAddressReserve(&ptrA, 0, 0, 0, 0) == hipErrorMemoryAllocation);
}
#if HT_NVIDIA
SECTION("pass non power of two for alignment") {
REQUIRE(hipMemAddressReserve(&ptrA, size_mem, 3, 0, 0) == hipErrorMemoryAllocation);
}
#endif
SECTION("pass size as non multiple of host page size") {
REQUIRE(hipMemAddressReserve(&ptrA, (size_mem - 1), 0, 0, 0) == hipErrorMemoryAllocation);
}
}
+445
Voir le fichier
@@ -0,0 +1,445 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/**
* @addtogroup hipMemCreate hipMemCreate
* @{
* @ingroup VirtualMemoryManagementTest
* `hipError_t hipMemCreate (hipMemGenericAllocationHandle_t* handle,
* size_t size,
* const hipMemAllocationProp* prop,
* unsigned long long flags)` -
* Creates a memory allocation described by the properties and size.
*/
#include <hip_test_kernels.hh>
#include <hip_test_common.hh>
#include "hip_vmm_common.hh"
#define THREADS_PER_BLOCK 512
#define NUM_OF_BUFFERS 3
#define DATA_SIZE (1 << 13)
/**
Kernel to perform Square of input data.
*/
static __global__ void square_kernel(int* Buff) {
int i = threadIdx.x + blockDim.x * blockIdx.x;
int temp = Buff[i] * Buff[i];
Buff[i] = temp;
}
/**
* Test Description
* ------------------------
* - Allocate physical memories for different multiples of
* granularity and deallocate them.
* ------------------------
* - unit/virtualMemoryManagement/hipMemCreate.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemCreate_BasicAllocateDeAlloc_MultGranularity") {
size_t granularity = 0;
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
hipMemGenericAllocationHandle_t handle;
// Allocate physical memory
for (int mul = 1; mul < 64; mul++) {
HIP_CHECK(hipMemCreate(&handle, granularity * mul, &prop, 0));
HIP_CHECK(hipMemRelease(handle));
}
}
/**
* Test Description
* ------------------------
* - Allocate physical memory and map it to virtual address range.
* After setting device permission, copy data from host to VMM memory
* and back to host. Verify the result. Release handle at end after
* unmapping VMM range.
* ------------------------
* - unit/virtualMemoryManagement/hipMemCreate.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemCreate_ChkDev2HstMemcpy_ReleaseHdlPostUnmap") {
size_t granularity = 0;
constexpr int N = DATA_SIZE;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
// Allocate physical memory
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate virtual address range
hipDeviceptr_t ptrA;
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle, 0));
// Set access
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
// Make the address accessible to GPU 0
HIP_CHECK(hipMemSetAccess(ptrA, size_mem, &accessDesc, 1));
// Allocate host memory and intialize data
std::vector<int> A_h(N), B_h(N);
// Initialize with data
for (size_t idx = 0; idx < N; idx++) {
A_h[idx] = idx;
}
HIP_CHECK(hipMemcpyHtoD(ptrA, A_h.data(), buffer_size));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, buffer_size));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), A_h.data()));
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
HIP_CHECK(hipMemRelease(handle));
}
/**
* Test Description
* ------------------------
* - Allocate physical memory and map it to virtual address
* range. After setting device permission, copy data from host
* to VMM memory and back to host. Verify the result. Release
* handle before the VMM range is used.
* ------------------------
* - unit/virtualMemoryManagement/hipMemCreate.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemCreate_ChkDev2HstMemcpy_ReleaseHdlPreUse") {
size_t granularity = 0;
constexpr int N = DATA_SIZE;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
// Allocate physical memory
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate virtual address range
hipDeviceptr_t ptrA;
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle, 0));
HIP_CHECK(hipMemRelease(handle));
// Set access
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
// Make the address accessible to GPU 0
HIP_CHECK(hipMemSetAccess(ptrA, size_mem, &accessDesc, 1));
// Allocate host memory and intialize data
std::vector<int> A_h(N), B_h(N);
// Initialize with data
for (size_t idx = 0; idx < N; idx++) {
A_h[idx] = idx;
}
HIP_CHECK(hipMemcpyHtoD(ptrA, A_h.data(), buffer_size));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, buffer_size));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), A_h.data()));
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
}
/**
* Test Description
* ------------------------
* - Allocate physical memory and map it to virtual address
* range. After setting device permission, copy data from host
* to device, launch kernel to square the data, copy data back
* to host. Verify the result.
* ------------------------
* - unit/virtualMemoryManagement/hipMemCreate.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemCreate_ChkWithKerLaunch") {
size_t granularity = 0;
constexpr int N = DATA_SIZE;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
// Allocate physical memory
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate virtual address range
hipDeviceptr_t ptrA;
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle, 0));
HIP_CHECK(hipMemRelease(handle));
// Set access
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
// Make the address accessible to GPU 0
HIP_CHECK(hipMemSetAccess(ptrA, size_mem, &accessDesc, 1));
std::vector<int> A_h(N), B_h(N), C_h(N);
// Initialize with data
for (size_t idx = 0; idx < N; idx++) {
A_h[idx] = idx;
C_h[idx] = idx * idx;
}
HIP_CHECK(hipMemcpyHtoD(ptrA, A_h.data(), buffer_size));
// Invoke kernel
hipLaunchKernelGGL(square_kernel, dim3(N / THREADS_PER_BLOCK), dim3(THREADS_PER_BLOCK), 0, 0,
static_cast<int*>(ptrA));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, buffer_size));
HIP_CHECK(hipDeviceSynchronize());
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), C_h.data()));
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
}
/**
* Test Description
* ------------------------
* - Allocate multiple non-contiguous physical memory chunks
* and map it to contiguous virtual address range. After setting
* device permission, copy data from host to device, launch kernel
* to square the data, copy data back to host. Verify the result.
* ------------------------
* - unit/virtualMemoryManagement/hipMemCreate.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemCreate_MapNonContiguousChunks") {
size_t granularity = 0;
constexpr int numOfBuffers = NUM_OF_BUFFERS;
constexpr int N = DATA_SIZE;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle[NUM_OF_BUFFERS];
// Allocate 3 physical memory chunks
for (int count = 0; count < numOfBuffers; count++) {
HIP_CHECK(hipMemCreate(&handle[count], size_mem, &prop, 0));
}
// Allocate virtual address range for all the memory chunks
hipDeviceptr_t ptrA;
HIP_CHECK(hipMemAddressReserve(&ptrA, (numOfBuffers * size_mem), 0, 0, 0));
for (int idx = 0; idx < numOfBuffers; idx++) {
uint64_t uiptr = reinterpret_cast<uint64_t>(ptrA);
uiptr = uiptr + idx * size_mem;
HIP_CHECK(hipMemMap(reinterpret_cast<void*>(uiptr), size_mem, 0, handle[idx], 0));
HIP_CHECK(hipMemRelease(handle[idx]));
}
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
// Make the address accessible to GPU 0
HIP_CHECK(hipMemSetAccess(ptrA, (numOfBuffers * size_mem), &accessDesc, 1));
std::vector<int> A_h(numOfBuffers * size_mem), B_h(numOfBuffers * size_mem),
C_h(numOfBuffers * size_mem);
// Fill Data
for (size_t idx = 0; idx < (numOfBuffers * N); idx++) {
A_h[idx] = idx;
C_h[idx] = idx * idx;
}
HIP_CHECK(hipMemcpyHtoD(ptrA, A_h.data(), numOfBuffers * buffer_size));
// Launch square kernel
hipLaunchKernelGGL(square_kernel, dim3(N / THREADS_PER_BLOCK), dim3(THREADS_PER_BLOCK), 0, 0,
static_cast<int*>(ptrA));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, numOfBuffers * buffer_size));
HIP_CHECK(hipDeviceSynchronize());
// Validate Results
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), C_h.data()));
for (int idx = 0; idx < numOfBuffers; idx++) {
uint64_t uiptr = reinterpret_cast<uint64_t>(ptrA);
uiptr = uiptr + idx * size_mem;
HIP_CHECK(hipMemUnmap(reinterpret_cast<void*>(uiptr), size_mem));
}
HIP_CHECK(hipMemAddressFree(ptrA, (numOfBuffers * size_mem)));
}
/**
* Test Description
* ------------------------
* - (Check if the VMM address can be memset) Map a physical chunk
* to the VMM address range. Memset the VMM address range with initial
* value. Validate.
* ------------------------
* - unit/virtualMemoryManagement/hipMemCreate.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemCreate_ChkWithMemset") {
size_t granularity = 0;
constexpr int N = DATA_SIZE;
size_t buffer_size = N * sizeof(int);
constexpr int init_val = 0;
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
// Allocate physical memory
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate virtual address range
hipDeviceptr_t ptrA;
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle, 0));
// Set access
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
// Make the address accessible to GPU 0
HIP_CHECK(hipMemSetAccess(ptrA, size_mem, &accessDesc, 1));
std::vector<int> A_h(N);
HIP_CHECK(hipMemset(ptrA, init_val, buffer_size));
HIP_CHECK(hipMemcpyDtoH(A_h.data(), ptrA, buffer_size));
for (int idx = 0; idx < N; idx++) {
REQUIRE(A_h[idx] == init_val);
}
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
HIP_CHECK(hipMemRelease(handle));
}
/**
* Test Description
* ------------------------
* - Negative Tests
* ------------------------
* - unit/virtualMemoryManagement/hipMemCreate.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemCreate_Negative") {
size_t granularity = 0;
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemGenericAllocationHandle_t handle;
hipMemAllocationProp prop = {};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Device
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
SECTION("Nullptr to handle") {
REQUIRE(hipMemCreate(nullptr, granularity, &prop, 0) == hipErrorInvalidValue);
}
SECTION("Nullptr to prop") {
REQUIRE(hipMemCreate(&handle, granularity, nullptr, 0) == hipErrorInvalidValue);
}
SECTION("pass size as 0") { REQUIRE(hipMemCreate(&handle, 0, &prop, 0) == hipErrorInvalidValue); }
SECTION("Pass prop type as invalid") {
prop.type = hipMemAllocationTypeInvalid;
REQUIRE(hipMemCreate(&handle, granularity, &prop, 0) == hipErrorInvalidValue);
}
SECTION("pass location as invalid") {
prop.location.type = hipMemLocationTypeInvalid;
REQUIRE(hipMemCreate(&handle, granularity, &prop, 0) == hipErrorInvalidValue);
}
SECTION("non multiple of granularity") {
REQUIRE(hipMemCreate(&handle, (granularity - 1), &prop, 0) == hipErrorInvalidValue);
}
SECTION("pass location id as -1") {
prop.location.id = -1; // set to non existing device
REQUIRE(hipMemCreate(&handle, granularity, &prop, 0) == hipErrorInvalidValue);
}
SECTION("pass location id as > highest device number") {
int numDevices = 0;
HIP_CHECK(hipGetDeviceCount(&numDevices));
prop.location.id = numDevices; // set to non existing device
REQUIRE(hipMemCreate(&handle, granularity, &prop, 0) == hipErrorInvalidValue);
}
}
@@ -0,0 +1,145 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/**
* @addtogroup hipMemExportToShareableHandle hipMemExportToShareableHandle
* @{
* @ingroup VirtualMemoryManagementTest
* `hipError_t hipMemExportToShareableHandle(void *shareableHandle,
* hipMemGenericAllocationHandle_t handle,
* hipMemAllocationHandleType handleType,
* unsigned long long flags)` -
* Exports an allocation to a requested shareable handle type.
*/
#include <hip_test_common.hh>
#include "hip_vmm_common.hh"
/**
* Test Description
* ------------------------
* - Basic sanity test.
* ------------------------
* - unit/virtualMemoryManagement/hipMemExportToShareableHandle.cc
* Test requirements
* ------------------------
* - Host specific (LINUX)
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemExportToShareableHandle_Positive_Basic") {
HIP_CHECK(hipFree(0));
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, 0));
checkVMMSupported(device);
hipMemAllocationProp prop = {};
prop.type = hipMemAllocationTypePinned;
prop.requestedHandleTypes = hipMemHandleTypePosixFileDescriptor;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device;
size_t granularity;
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
hipMemGenericAllocationHandle_t handle;
HIP_CHECK(hipMemCreate(&handle, granularity * 2, &prop, 0));
void* shareable_handle = nullptr;
HIP_CHECK(hipMemExportToShareableHandle(&shareable_handle, handle,
hipMemHandleTypePosixFileDescriptor, 0));
REQUIRE(shareable_handle != nullptr);
HIP_CHECK(hipMemRelease(handle));
}
/**
* Test Description
* ------------------------
* - Negative parameters test.
* ------------------------
* - unit/virtualMemoryManagement/hipMemExportToShareableHandle.cc
* Test requirements
* ------------------------
* - Host specific (LINUX)
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemExportToShareableHandle_Negative_Parameters") {
HIP_CHECK(hipFree(0));
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, 0));
checkVMMSupported(device);
hipMemAllocationProp prop = {};
prop.type = hipMemAllocationTypePinned;
prop.requestedHandleTypes = hipMemHandleTypePosixFileDescriptor;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device;
size_t granularity;
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
hipMemGenericAllocationHandle_t handle;
HIP_CHECK(hipMemCreate(&handle, granularity * 2, &prop, 0));
void* shareable_handle = nullptr;
SECTION("shareableHandle == nullptr") {
HIP_CHECK_ERROR(
hipMemExportToShareableHandle(nullptr, handle, hipMemHandleTypePosixFileDescriptor, 0),
hipErrorInvalidValue);
}
#if HT_AMD
SECTION("handle == nullptr") {
HIP_CHECK_ERROR(hipMemExportToShareableHandle(&shareable_handle, nullptr,
hipMemHandleTypePosixFileDescriptor, 0),
hipErrorInvalidValue);
}
#endif
SECTION("invalid handleType") {
HIP_CHECK_ERROR(
hipMemExportToShareableHandle(&shareable_handle, handle, hipMemHandleTypeWin32, 0),
hipErrorInvalidValue);
}
SECTION("non-zero flags") {
HIP_CHECK_ERROR(hipMemExportToShareableHandle(&shareable_handle, handle,
hipMemHandleTypePosixFileDescriptor, 1),
hipErrorInvalidValue);
}
HIP_CHECK(hipMemRelease(handle));
#if HT_AMD // segfaults on NVIDIA
SECTION("released handle") {
HIP_CHECK_ERROR(hipMemExportToShareableHandle(&shareable_handle, handle,
hipMemHandleTypePosixFileDescriptor, 0),
hipErrorInvalidValue);
}
#endif
}
@@ -0,0 +1,184 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANNTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER INN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR INN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/**
* @addtogroup hipMemGetAllocationGranularity hipMemGetAllocationGranularity
* @{
* @ingroup VirtualMemoryManagementTest
* `hipError_t hipMemGetAllocationGranularity (size_t* granularity,
* const hipMemAllocationProp* prop,
* hipMemAllocationGranularity_flags option)` -
* Calculates either the minimal or recommended granularity.
*/
#include <hip_test_checkers.hh>
#include <hip_test_kernels.hh>
#include <hip_test_common.hh>
#include "hip_vmm_common.hh"
/**
local function to invoke hipMemGetAllocationGranularity.
*/
void getGranularity(size_t* granularity, hipMemAllocationGranularity_flags option, int device) {
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(hipMemGetAllocationGranularity(granularity, &prop, option));
}
/**
* Test Description
* ------------------------
* - Functional Test to get granularity size for
* hipMemAllocationGranularityMinimum option.
* ------------------------
* - unit/virtualMemoryManagement/hipMemGetAllocationGranularity.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemGetAllocationGranularity_MinGranularity") {
HIP_CHECK(hipFree(0));
size_t granularity = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, 0));
checkVMMSupported(device);
getGranularity(&granularity, hipMemAllocationGranularityMinimum, 0);
REQUIRE(granularity > 0);
}
/**
* Test Description
* ------------------------
* - Functional Test to get granularity size for
* hipMemAllocationGranularityRecommended option.
* ------------------------
* - unit/virtualMemoryManagement/hipMemGetAllocationGranularity.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemGetAllocationGranularity_RecommendedGranularity") {
HIP_CHECK(hipFree(0));
size_t granularity = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, 0));
checkVMMSupported(device);
getGranularity(&granularity, hipMemAllocationGranularityRecommended, 0);
REQUIRE(granularity > 0);
}
/**
* Test Description
* ------------------------
* - Functional Test to get granularity size for
* hipMemAllocationGranularityMinimum option for all GPUs.
* ------------------------
* - unit/virtualMemoryManagement/hipMemGetAllocationGranularity.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemGetAllocationGranularity_AllGPUs") {
HIP_CHECK(hipFree(0));
int numDevices = 0;
HIP_CHECK(hipGetDeviceCount(&numDevices));
for (int dev = 0; dev < numDevices; dev++) {
size_t granularity = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, dev));
checkVMMSupported(device);
getGranularity(&granularity, hipMemAllocationGranularityRecommended, dev);
REQUIRE(granularity > 0);
}
}
/**
* Test Description
* ------------------------
* - Negative Tests
* ------------------------
* - unit/virtualMemoryManagement/hipMemGetAllocationGranularity.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemGetAllocationGranularity_NegativeTests") {
HIP_CHECK(hipFree(0));
size_t granularity = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, 0));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = 0; // Current Devices
SECTION("Granularity is nullptr") {
REQUIRE(hipErrorInvalidValue ==
hipMemGetAllocationGranularity(nullptr, &prop, hipMemAllocationGranularityMinimum));
}
#if HT_AMD // segfaults on NVIDIA
SECTION("Prop is nullptr") {
REQUIRE(
hipErrorInvalidValue ==
hipMemGetAllocationGranularity(&granularity, nullptr, hipMemAllocationGranularityMinimum));
}
#endif
#if HT_NVIDIA
SECTION("flag is invalid") {
REQUIRE(hipErrorInvalidValue ==
hipMemGetAllocationGranularity(&granularity, &prop,
(hipMemAllocationGranularity_flags)0xff));
}
#endif
#if HT_AMD // succeeds on NVIDIA
SECTION("device id > highest device id") {
int numDevices = 0;
HIP_CHECK(hipGetDeviceCount(&numDevices));
prop.location.id = numDevices; // set to non existing device
REQUIRE(
hipErrorInvalidValue ==
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
}
SECTION("device id < lowest device id") {
prop.location.id = -1; // set to non existing device
REQUIRE(
hipErrorInvalidValue ==
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
}
SECTION("allocation type as invalid") {
prop.type = hipMemAllocationTypeInvalid;
REQUIRE(
hipErrorInvalidValue ==
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
}
SECTION("location type as invalid") {
prop.location.type = hipMemLocationTypeInvalid;
REQUIRE(
hipErrorInvalidValue ==
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
}
#endif
}
@@ -0,0 +1,117 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANNTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER INN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR INN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/**
* @addtogroup hipMemGetAllocationPropertiesFromHandle hipMemGetAllocationPropertiesFromHandle
* @{
* @ingroup VirtualMemoryManagementTest
* `hipError_t hipMemGetAllocationPropertiesFromHandle(hipMemAllocationProp* prop,
* hipMemGenericAllocationHandle_t handle)` -
* Retrieve the property structure of the given handle.
*/
#include <hip_test_common.hh>
#include "hip_vmm_common.hh"
#define DATA_SIZE (1 << 13)
/**
* Test Description
* ------------------------
* - Functional test to verify the values of hipMemAllocationProp properties.
* ------------------------
* - unit/virtualMemoryManagement/hipMemGetAllocationPropertiesFromHandle.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemGetAllocationPropertiesFromHandle_functional") {
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, 0));
checkVMMSupported(device);
hipMemGenericAllocationHandle_t handle;
hipMemAllocationProp prop = {};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device;
// create a temp prop structure.
hipMemAllocationProp prop_temp = {};
size_t granularity = 0;
int N = DATA_SIZE;
size_t buffer_size = N * sizeof(int);
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t mem_size = ((granularity + buffer_size - 1) / granularity) * granularity;
// Allocate physical memory
HIP_CHECK(hipMemCreate(&handle, mem_size, &prop, 0));
// verify properties has been retrived from handle
HIP_CHECK(hipMemGetAllocationPropertiesFromHandle(&prop_temp, handle));
REQUIRE(prop_temp.type == prop.type);
REQUIRE(prop_temp.location.type == prop.location.type);
REQUIRE(prop_temp.location.id == prop.location.id);
HIP_CHECK(hipMemRelease(handle));
}
/**
* Test Description
* ------------------------
* - Negative Tests.
* ------------------------
* - unit/virtualMemoryManagement/hipMemGetAllocationPropertiesFromHandle.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemGetAllocationPropertiesFromHandle_Negative") {
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, 0));
checkVMMSupported(device);
hipMemGenericAllocationHandle_t handle;
hipMemAllocationProp prop = {};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device;
// create a temp prop structure.
hipMemAllocationProp prop_temp = {};
size_t granularity = 0;
int N = DATA_SIZE;
size_t buffer_size = N * sizeof(int);
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t mem_size = ((granularity + buffer_size - 1) / granularity) * granularity;
// Allocate physical memory
HIP_CHECK(hipMemCreate(&handle, mem_size, &prop, 0));
SECTION("Nullptr as prop") {
REQUIRE(hipMemGetAllocationPropertiesFromHandle(nullptr, handle) == hipErrorInvalidValue);
}
SECTION("null handle") {
prop.location.type = hipMemLocationTypeInvalid;
REQUIRE(hipMemGetAllocationPropertiesFromHandle(&prop_temp, nullptr) == hipErrorInvalidValue);
}
HIP_CHECK(hipMemRelease(handle));
}
@@ -0,0 +1,210 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/**
* @addtogroup hipMemExportToShareableHandle hipMemExportToShareableHandle
* @{
* @ingroup VirtualMemoryManagementTest
* `hipError_t hipMemImportFromShareableHandle(hipMemGenericAllocationHandle_t *handle,
* void *osHandle,
* hipMemAllocationHandleType shHandleType)` -
* Imports an allocation from a requested shareable handle type.
*/
#include <unistd.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <hip_test_common.hh>
#include "hip_vmm_common.hh"
/**
* Test Description
* ------------------------
* - Basic sanity test.
* ------------------------
* - unit/virtualMemoryManagement/hipMemImportFromShareableHandle.cc
* Test requirements
* ------------------------
* - Host specific (LINUX)
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemImportFromShareableHandle_Positive_Basic") {
HIP_CHECK(hipFree(0));
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, 0));
checkVMMSupported(device);
hipMemAllocationProp prop = {};
prop.type = hipMemAllocationTypePinned;
prop.requestedHandleTypes = hipMemHandleTypePosixFileDescriptor;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device;
size_t granularity;
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
hipMemGenericAllocationHandle_t handle;
HIP_CHECK(hipMemCreate(&handle, granularity * 2, &prop, 0));
void* shareable_handle = nullptr;
HIP_CHECK(hipMemExportToShareableHandle(&shareable_handle, handle,
hipMemHandleTypePosixFileDescriptor, 0));
hipMemGenericAllocationHandle_t imported_handle;
HIP_CHECK(hipMemImportFromShareableHandle(&imported_handle, shareable_handle,
hipMemHandleTypePosixFileDescriptor));
HIP_CHECK(hipMemRelease(handle));
}
/**
* Test Description
* ------------------------
* - Basic multiprocess sanity test.
* ------------------------
* - unit/virtualMemoryManagement/hipMemImportFromShareableHandle.cc
* Test requirements
* ------------------------
* - Host specific (LINUX)
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemImportFromShareableHandle_Positive_MultiProc") {
int fd[2];
REQUIRE(pipe(fd) == 0);
auto pid = fork();
REQUIRE(pid >= 0);
if (pid == 0) { // child
REQUIRE(close(fd[1]) == 0);
void* shareable_handle = nullptr;
REQUIRE(read(fd[0], &shareable_handle, sizeof(shareable_handle)) >= 0);
REQUIRE(close(fd[0]) == 0);
REQUIRE(shareable_handle != nullptr);
HIP_CHECK(hipFree(0));
hipMemGenericAllocationHandle_t imported_handle;
HIP_CHECK(hipMemImportFromShareableHandle(&imported_handle, shareable_handle,
hipMemHandleTypePosixFileDescriptor));
exit(0);
} else { // parent
REQUIRE(close(fd[0]) == 0);
HIP_CHECK(hipFree(0));
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, 0));
checkVMMSupported(device);
hipMemAllocationProp prop = {};
prop.type = hipMemAllocationTypePinned;
prop.requestedHandleTypes = hipMemHandleTypePosixFileDescriptor;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device;
size_t granularity;
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
hipMemGenericAllocationHandle_t handle;
HIP_CHECK(hipMemCreate(&handle, granularity * 2, &prop, 0));
void* shareable_handle = nullptr;
HIP_CHECK(hipMemExportToShareableHandle(&shareable_handle, handle,
hipMemHandleTypePosixFileDescriptor, 0));
REQUIRE(write(fd[1], &shareable_handle, sizeof(shareable_handle)) >= 0);
REQUIRE(close(fd[1]) == 0);
REQUIRE(wait(NULL) >= 0);
HIP_CHECK(hipMemRelease(handle));
}
}
/**
* Test Description
* ------------------------
* - Negative parameters test.
* ------------------------
* - unit/virtualMemoryManagement/hipMemImportFromShareableHandle.cc
* Test requirements
* ------------------------
* - Host specific (LINUX)
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemImportFromShareableHandle_Negative_Parameters") {
HIP_CHECK(hipFree(0));
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, 0));
checkVMMSupported(device);
hipMemAllocationProp prop = {};
prop.type = hipMemAllocationTypePinned;
prop.requestedHandleTypes = hipMemHandleTypePosixFileDescriptor;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device;
size_t granularity;
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
hipMemGenericAllocationHandle_t handle;
HIP_CHECK(hipMemCreate(&handle, granularity * 2, &prop, 0));
void* shareable_handle = nullptr;
HIP_CHECK(hipMemExportToShareableHandle(&shareable_handle, handle,
hipMemHandleTypePosixFileDescriptor, 0));
hipMemGenericAllocationHandle_t imported_handle;
#if HT_AMD
SECTION("handle == nullptr") {
HIP_CHECK_ERROR(hipMemImportFromShareableHandle(nullptr, shareable_handle,
hipMemHandleTypePosixFileDescriptor),
hipErrorInvalidValue);
}
#endif
SECTION("shareableHandle == nullptr") {
HIP_CHECK_ERROR(hipMemImportFromShareableHandle(&imported_handle, nullptr,
hipMemHandleTypePosixFileDescriptor),
hipErrorInvalidValue);
}
SECTION("invalid handleType") {
HIP_CHECK_ERROR(
hipMemImportFromShareableHandle(&imported_handle, shareable_handle, hipMemHandleTypeWin32),
hipErrorNotSupported);
}
HIP_CHECK(hipMemRelease(handle));
}
+632
Voir le fichier
@@ -0,0 +1,632 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANNTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER INN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR INN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/**
* @addtogroup hipMemMap hipMemMap
* @{
* @ingroup VirtualMemoryManagementTest
* `hipError_t hipMemMap (void* ptr,
* size_t size,
* size_t offset,
* hipMemGenericAllocationHandle_t handle,
* unsigned long long flags)` -
* Maps an allocation handle to a reserved virtual address range.
*/
#include <hip_test_common.hh>
#include "hip_vmm_common.hh"
constexpr int N = (1 << 13);
constexpr int num_buf = 3;
constexpr int initializer = 0;
/**
* Test Description
* ------------------------
* - Check if a physical chunk can be mapped/unmapped to same
* vmm address range repeatedly. This test validates physical memory
* euse using same vmm range.
* ------------------------
* - unit/virtualMemoryManagement/hipMemMap.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemMap_SameMemoryReuse") {
constexpr int iterations = 20;
size_t granularity = 0;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
// Allocate host memory and intialize data
std::vector<int> A_h(N), B_h(N), C_h(N);
// Initialize with data
for (size_t idx = 0; idx < N; idx++) {
A_h[idx] = idx;
C_h[idx] = idx * idx;
}
// Allocate a physical memory chunk
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate num_buf virtual address ranges
hipDeviceptr_t ptrA;
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
for (int i = 0; i < iterations; i++) {
std::fill(B_h.begin(), B_h.end(), initializer);
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle, 0));
// Set access to GPU 0
HIP_CHECK(hipMemSetAccess(ptrA, size_mem, &accessDesc, 1));
HIP_CHECK(hipMemcpyHtoD(ptrA, A_h.data(), buffer_size));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, buffer_size));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), A_h.data()));
#if HT_NVIDIA
square_kernel<<<dim3(N / threadsPerBlk), dim3(threadsPerBlk), 0, 0>>>(static_cast<int*>(ptrA));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, buffer_size));
HIP_CHECK(hipStreamSynchronize(0));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), C_h.data()));
#endif
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
}
// Release resources
HIP_CHECK(hipMemRelease(handle));
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
}
/**
* Test Description
* ------------------------
* - Check if a physical chunk can be mapped/unmapped for multiple
* vmm addresses. This test validates physical memory reuse using
* different vmm ranges.
* ------------------------
* - unit/virtualMemoryManagement/hipMemMap.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemMap_PhysicalMemoryReuse_SingleGPU") {
size_t granularity = 0;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
// Allocate host memory and intialize data
std::vector<int> A_h(N), B_h(N), C_h(N);
// Initialize with data
for (size_t idx = 0; idx < N; idx++) {
A_h[idx] = idx;
C_h[idx] = idx * idx;
}
// Allocate a physical memory chunk
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate num_buf virtual address ranges
hipDeviceptr_t ptrA[num_buf];
for (int buf = 0; buf < num_buf; buf++) {
HIP_CHECK(hipMemAddressReserve(&ptrA[buf], size_mem, 0, 0, 0));
}
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
for (int buf = 0; buf < num_buf; buf++) {
std::fill(B_h.begin(), B_h.end(), initializer);
HIP_CHECK(hipMemMap(ptrA[buf], size_mem, 0, handle, 0));
// Set access to GPU 0
HIP_CHECK(hipMemSetAccess(ptrA[buf], size_mem, &accessDesc, 1));
HIP_CHECK(hipMemcpyHtoD(ptrA[buf], A_h.data(), buffer_size));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA[buf], buffer_size));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), A_h.data()));
#if HT_NVIDIA
square_kernel<<<dim3(N / threadsPerBlk), dim3(threadsPerBlk), 0, 0>>>(
static_cast<int*>(ptrA[buf]));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA[buf], buffer_size));
HIP_CHECK(hipStreamSynchronize(0));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), C_h.data()));
#endif
HIP_CHECK(hipMemUnmap(ptrA[buf], size_mem));
}
// Release resources
HIP_CHECK(hipMemRelease(handle));
for (int buf = 0; buf < num_buf; buf++) {
HIP_CHECK(hipMemAddressFree(ptrA[buf], size_mem));
}
}
/**
* Test Description
* ------------------------
* - Check if a physical chunk can be mapped to multiple
* vmm addresses at the same time and check data values integrity
* between different VMMs.
* ------------------------
* - unit/virtualMemoryManagement/hipMemMap.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemMap_PhysicalMemory_Map2MultVMMs") {
size_t granularity = 0;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
// Allocate host memory and intialize data
std::vector<int> A_h(N), B_h(N);
// Initialize with data
for (size_t idx = 0; idx < N; idx++) {
A_h[idx] = idx;
}
// Allocate a physical memory chunk
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate num_buf virtual address ranges
hipDeviceptr_t ptrA[num_buf];
for (int buf = 0; buf < num_buf; buf++) {
HIP_CHECK(hipMemAddressReserve(&ptrA[buf], size_mem, 0, 0, 0));
}
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
for (int buf = 0; buf < num_buf; buf++) {
HIP_CHECK(hipMemMap(ptrA[buf], size_mem, 0, handle, 0));
}
// Copy data to VMM via ptrA[0]
HIP_CHECK(hipMemSetAccess(ptrA[0], size_mem, &accessDesc, 1));
HIP_CHECK(hipMemcpyHtoD(ptrA[0], A_h.data(), buffer_size));
// Validate the data contained in VMM using ptrA[0], ptrA[1],
// ......, ptrA[num_buf-1]
for (int buf = 0; buf < num_buf; buf++) {
std::fill(B_h.begin(), B_h.end(), initializer);
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA[buf], buffer_size));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), A_h.data()));
}
// Release resources
HIP_CHECK(hipMemRelease(handle));
for (int buf = 0; buf < num_buf; buf++) {
HIP_CHECK(hipMemAddressFree(ptrA[buf], size_mem));
}
}
/**
* Test Description
* ------------------------
* - Check if a physical chunk can be mapped/unmapped for
* multiple vmm addresses. This test validates physical memory
* reuse using different vmm ranges on multiple devices.
* ------------------------
* - unit/virtualMemoryManagement/hipMemMap.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemMap_PhysicalMemoryReuse_MultiDev") {
int devicecount = 0;
HIP_CHECK(hipGetDeviceCount(&devicecount));
if (devicecount < 2) {
HipTest::HIP_SKIP_TEST("Machine is Single GPU. Skipping Test..");
return;
}
size_t granularity = 0;
size_t buffer_size = N * sizeof(int);
for (int devX = 0; devX < devicecount; devX++) {
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, devX));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
// Allocate host memory and intialize data
std::vector<int> A_h(N), B_h(N);
// Initialize with data
for (size_t idx = 0; idx < N; idx++) {
A_h[idx] = idx;
}
// Allocate a physical memory chunk
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate devicecount virtual address ranges
std::vector<hipDeviceptr_t> ptrA(devicecount);
for (int devY = 0; devY < devicecount; devY++) {
HIP_CHECK(hipMemAddressReserve(&ptrA[devY], size_mem, 0, 0, 0));
}
for (int devY = 0; devY < devicecount; devY++) {
hipDevice_t deviceToTest;
HIP_CHECK(hipDeviceGet(&deviceToTest, devY));
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = deviceToTest;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
HIP_CHECK(hipSetDevice(devY));
std::fill(B_h.begin(), B_h.end(), initializer);
HIP_CHECK(hipMemMap(ptrA[devY], size_mem, 0, handle, 0));
// Set access to GPU 0
HIP_CHECK(hipMemSetAccess(ptrA[devY], size_mem, &accessDesc, 1));
HIP_CHECK(hipMemcpyHtoD(ptrA[devY], A_h.data(), buffer_size));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA[devY], buffer_size));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), A_h.data()));
HIP_CHECK(hipMemUnmap(ptrA[devY], size_mem));
}
HIP_CHECK(hipSetDevice(0)); // set the device back to 0.
// Release resources
HIP_CHECK(hipMemRelease(handle));
for (int devY = 0; devY < devicecount; devY++) {
HIP_CHECK(hipMemAddressFree(ptrA[devY], size_mem));
}
}
}
/**
* Test Description
* ------------------------
* - Check if different physical chunk can be mapped/unmapped
* for single vmm address. This test validates VMM memory reuse
* using different physical ranges.
* ------------------------
* - unit/virtualMemoryManagement/hipMemMap.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemMap_VMMMemoryReuse_SingleGPU") {
size_t granularity = 0;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle[num_buf];
// Allocate host memory and intialize data
std::vector<int> A_h(N), B_h(N), C_h(N);
// Initialize with data
for (size_t idx = 0; idx < N; idx++) {
A_h[idx] = idx;
C_h[idx] = idx * idx;
}
// Allocate a physical memory chunk
for (int buf = 0; buf < num_buf; buf++) {
HIP_CHECK(hipMemCreate(&handle[buf], size_mem, &prop, 0));
}
// Allocate num_buf virtual address ranges
hipDeviceptr_t ptrA;
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
// Map ptrA to physical chunk
for (int buf = 0; buf < num_buf; buf++) {
std::fill(B_h.begin(), B_h.end(), initializer);
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle[buf], 0));
// Set access to GPU 0
HIP_CHECK(hipMemSetAccess(ptrA, size_mem, &accessDesc, 1));
HIP_CHECK(hipMemcpyHtoD(ptrA, A_h.data(), buffer_size));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, buffer_size));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), A_h.data()));
#if HT_NVIDIA
square_kernel<<<dim3(N / threadsPerBlk), dim3(threadsPerBlk), 0, 0>>>(static_cast<int*>(ptrA));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, buffer_size));
HIP_CHECK(hipStreamSynchronize(0));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), C_h.data()));
#endif
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
}
// Release resources
for (int buf = 0; buf < num_buf; buf++) {
HIP_CHECK(hipMemRelease(handle[buf]));
}
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
}
/**
* Test Description
* ------------------------
* - Check if different physical chunk allocated in different devices
* can be mapped/unmapped to single vmm address. This test validates VMM
* memory reuse using different physical ranges.
* ------------------------
* - unit/virtualMemoryManagement/hipMemMap.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemMap_VMMMemoryReuse_MultiGPU") {
int deviceId = 0, devicecount = 0;
HIP_CHECK(hipGetDeviceCount(&devicecount));
if (devicecount < 2) {
HipTest::HIP_SKIP_TEST("Machine is Single GPU. Skipping Test..");
return;
}
size_t granularity = 0;
size_t buffer_size = N * sizeof(int);
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
std::vector<hipMemGenericAllocationHandle_t> handle(devicecount);
// Allocate host memory and intialize data
std::vector<int> A_h(N), B_h(N);
// Initialize with data
for (size_t idx = 0; idx < N; idx++) {
A_h[idx] = idx;
}
// Allocate a physical memory chunk
for (int dev = 0; dev < devicecount; dev++) {
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, dev));
prop.location.id = device;
HIP_CHECK(hipMemCreate(&handle[dev], size_mem, &prop, 0));
}
// Allocate devicecount virtual address ranges
hipDeviceptr_t ptrA;
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
// Map ptrA to physical chunk
SECTION("Set Access of VMM to Different GPU") {
for (int dev = 0; dev < devicecount; dev++) {
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, dev));
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
HIP_CHECK(hipSetDevice(dev));
std::fill(B_h.begin(), B_h.end(), initializer);
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle[dev], 0));
HIP_CHECK(hipMemSetAccess(ptrA, size_mem, &accessDesc, 1));
HIP_CHECK(hipMemcpyHtoD(ptrA, A_h.data(), buffer_size));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, buffer_size));
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), A_h.data()));
}
}
SECTION("Set Access of VMM to default GPU") {
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
for (int dev = 0; dev < devicecount; dev++) {
std::fill(B_h.begin(), B_h.end(), initializer);
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle[dev], 0));
HIP_CHECK(hipMemSetAccess(ptrA, size_mem, &accessDesc, 1));
HIP_CHECK(hipMemcpyHtoD(ptrA, A_h.data(), buffer_size));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, buffer_size));
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), A_h.data()));
}
}
HIP_CHECK(hipSetDevice(0));
// Release resources
for (int dev = 0; dev < devicecount; dev++) {
HIP_CHECK(hipMemRelease(handle[dev]));
}
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
}
/**
* Test Description
* ------------------------
* - Check if a partial part of a physical chunk can be mapped/unmapped
* to a smaller vmm address.
* ------------------------
* - unit/virtualMemoryManagement/hipMemMap.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemMap_MapPartialPhysicalMem") {
int deviceId = 0;
size_t granularity = 0;
size_t buffer_size = N * sizeof(int);
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
// Allocate host memory and intialize data
std::vector<int> A_h(N), B_h(N);
// Initialize with data
for (size_t idx = 0; idx < N; idx++) {
A_h[idx] = idx;
}
// Allocate a bigger physical memory chunk of twice size_mem
HIP_CHECK(hipMemCreate(&handle, 2 * size_mem, &prop, 0));
// Allocate virtual address range of size size_mem
hipDeviceptr_t ptrA;
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
std::fill(B_h.begin(), B_h.end(), initializer);
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle, 0));
HIP_CHECK(hipMemSetAccess(ptrA, size_mem, &accessDesc, 1));
HIP_CHECK(hipMemcpyHtoD(ptrA, A_h.data(), buffer_size));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, buffer_size));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), A_h.data()));
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
// Release resources
HIP_CHECK(hipMemRelease(handle));
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
}
/**
* Test Description
* ------------------------
* - Check if a partial part of a VMM range can be mapped/unmapped
* to a physical address.
* ------------------------
* - unit/virtualMemoryManagement/hipMemMap.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemMap_MapPartialVMMMem") {
int deviceId = 0;
size_t granularity = 0;
size_t buffer_size = N * sizeof(int);
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
// Allocate host memory and intialize data
std::vector<int> A_h(N), B_h(N);
// Initialize with data
for (size_t idx = 0; idx < N; idx++) {
A_h[idx] = idx;
}
// Allocate a bigger physical memory chunk of size_mem
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate virtual address range of size twice size_mem
hipDeviceptr_t ptrA;
HIP_CHECK(hipMemAddressReserve(&ptrA, 2 * size_mem, 0, 0, 0));
hipMemAccessDesc accessDesc = {};
accessDesc.location.type = hipMemLocationTypeDevice;
accessDesc.location.id = device;
accessDesc.flags = hipMemAccessFlagsProtReadWrite;
std::fill(B_h.begin(), B_h.end(), initializer);
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle, 0));
HIP_CHECK(hipMemSetAccess(ptrA, size_mem, &accessDesc, 1));
HIP_CHECK(hipMemcpyHtoD(ptrA, A_h.data(), buffer_size));
HIP_CHECK(hipMemcpyDtoH(B_h.data(), ptrA, buffer_size));
REQUIRE(true == std::equal(B_h.begin(), B_h.end(), A_h.data()));
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
// Release resources
HIP_CHECK(hipMemRelease(handle));
HIP_CHECK(hipMemAddressFree(ptrA, 2 * size_mem));
}
/**
* Test Description
* ------------------------
* - Negative Argument Tests
* ------------------------
* - unit/virtualMemoryManagement/hipMemMap.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemMap_negative") {
size_t granularity = 0;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
hipDeviceptr_t ptrA;
// Allocate physical memory
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate virtual address range
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
SECTION("nullptr to ptrA") {
REQUIRE(hipMemMap(nullptr, size_mem, 0, handle, 0) == hipErrorInvalidValue);
}
SECTION("pass zero to size") {
REQUIRE(hipMemMap(&ptrA, 0, 0, handle, 0) == hipErrorInvalidValue);
}
SECTION("pass negative to offset") {
REQUIRE(hipMemMap(&ptrA, size_mem, -1, handle, 0) == hipErrorInvalidValue);
}
HIP_CHECK(hipMemRelease(handle));
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
}
+110
Voir le fichier
@@ -0,0 +1,110 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/**
* @addtogroup hipMemMapArrayAsync hipMemMapArrayAsync
* @{
* @ingroup VirtualMemoryManagementTest
* `hipError_t hipMemMapArrayAsync(hipArrayMapInfo *mapInfoList,
* unsigned int count,
* hipStream_t stream)` -
* Maps or unmaps subregions of sparse HIP arrays and sparse HIP mipmapped arrays.
*/
#include <hip_array_common.hh>
#include <hip_test_common.hh>
#include <resource_guards.hh>
#include "hip_vmm_common.hh"
/**
* Test Description
* ------------------------
* - Basic sanity test.
* ------------------------
* - unit/virtualMemoryManagement/hipMemMapArrayAsync.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemMapArrayAsync_Positive_Basic") {
HIP_CHECK(hipFree(0));
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, 0));
checkVMMSupported(device);
CHECK_IMAGE_SUPPORT;
hipmipmappedArray array;
HIP_ARRAY3D_DESCRIPTOR desc = {};
using vec_info = vector_info<float>;
desc.Format = vec_info::format;
desc.NumChannels = vec_info::size;
desc.Width = 1;
desc.Height = 1;
desc.Flags = CUDA_ARRAY3D_SPARSE;
unsigned int levels = 2;
HIP_CHECK(hipMipmappedArrayCreate(&array, &desc, levels));
hipMemAllocationProp prop = {};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device;
prop.allocFlags.usage = CU_MEM_CREATE_USAGE_TILE_POOL;
size_t granularity;
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityRecommended));
hipMemGenericAllocationHandle_t handle;
HIP_CHECK(hipMemCreate(&handle, granularity, &prop, 0));
hipArrayMapInfo map_info_list = {};
map_info_list.resourceType = HIP_RESOURCE_TYPE_MIPMAPPED_ARRAY;
map_info_list.resource.mipmap = array;
map_info_list.subresourceType = hipArraySparseSubresourceTypeSparseLevel;
map_info_list.subresource.sparseLevel.extentWidth = 1;
map_info_list.subresource.sparseLevel.extentHeight = 1;
map_info_list.subresource.sparseLevel.extentDepth = 1;
map_info_list.memOperationType = hipMemOperationTypeMap;
map_info_list.memHandleType = hipMemHandleTypeGeneric;
map_info_list.memHandle.memHandle = handle;
map_info_list.deviceBitMask = 0x1;
StreamGuard stream(Streams::created);
HIP_CHECK(hipMemMapArrayAsync(&map_info_list, 1, stream.stream()));
HIP_CHECK(hipStreamSynchronize(stream.stream()));
map_info_list.memOperationType = hipMemOperationTypeUnmap;
map_info_list.memHandle.memHandle = NULL;
HIP_CHECK(hipMemMapArrayAsync(&map_info_list, 1, stream.stream()));
HIP_CHECK(hipStreamSynchronize(stream.stream()));
HIP_CHECK(hipMemRelease(handle));
HIP_CHECK(hipMipmappedArrayDestroy(array));
}
+46
Voir le fichier
@@ -0,0 +1,46 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANNTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER INN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR INN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/**
* @addtogroup hipMemRelease hipMemRelease
* @{
* @ingroup VirtualMemoryManagementTest
* `hipMemRelease(hipMemGenericAllocationHandle_t handle)` -
* Release a memory handle representing a memory allocation which was previously
* allocated through hipMemCreate.
*/
#include <hip_test_common.hh>
/**
* Test Description
* ------------------------
* - Negative Tests
* ------------------------
* - unit/virtualMemoryManagement/hipMemRelease.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemRelease_negative") {
SECTION("Nullptr to handle") { REQUIRE(hipMemRelease(nullptr) == hipErrorInvalidValue); }
}
@@ -0,0 +1,141 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/**
* @addtogroup hipMemRetainAllocationHandle hipMemRetainAllocationHandle
* @{
* @ingroup VirtualMemoryManagementTest
* `hipError_t hipMemRetainAllocationHandle(hipMemGenericAllocationHandle_t* handle,
* void* addr)` -
* Returns the allocation handle of the backing memory allocation given the address.
*/
#include <hip_test_kernels.hh>
#include <hip_test_common.hh>
#include "hip_vmm_common.hh"
#define DATA_SIZE (1 << 13)
/**
* Test Description
* ------------------------
* - Create a VM mapped to physical memory. Input addr to
* hipMemRetainAllocationHandle and validate the handle.
* ------------------------
* - unit/virtualMemoryManagement/hipMemRetainAllocationHandle.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemRetainAllocationHandle_SetGet") {
HIP_CHECK(hipFree(0));
size_t granularity = 0;
constexpr int N = DATA_SIZE;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
hipDeviceptr_t ptrA;
// Allocate physical memory
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate virtual address range
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle, 0));
// Test hipMemRetainAllocationHandle
hipMemGenericAllocationHandle_t gethandle;
// Check beginning of VMM ptr
HIP_CHECK(hipMemRetainAllocationHandle(&gethandle, reinterpret_cast<void*>(ptrA)));
REQUIRE(gethandle == handle);
HIP_CHECK(hipMemRelease(handle));
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
}
/**
* Test Description
* ------------------------
* - Negative Tests
* ------------------------
* - unit/virtualMemoryManagement/hipMemRetainAllocationHandle.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemRetainAllocationHandle_NegTst") {
HIP_CHECK(hipFree(0));
size_t granularity = 0;
constexpr int N = DATA_SIZE;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
hipDeviceptr_t ptrA;
// Allocate physical memory
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate virtual address range
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle, 0));
// Test hipMemRetainAllocationHandle
hipMemGenericAllocationHandle_t gethandle;
SECTION("nullptr handle") {
REQUIRE(hipMemRetainAllocationHandle(nullptr, reinterpret_cast<void*>(ptrA)) ==
hipErrorInvalidValue);
}
SECTION("nullptr Vmm ptr") {
REQUIRE(hipMemRetainAllocationHandle(&gethandle, nullptr) == hipErrorInvalidValue);
}
SECTION("not mapped address") {
hipDeviceptr_t ptrB;
HIP_CHECK(hipMemAddressReserve(&ptrB, size_mem, 0, 0, 0));
REQUIRE(hipMemRetainAllocationHandle(&gethandle, reinterpret_cast<void*>(ptrB)) ==
hipErrorInvalidValue);
HIP_CHECK(hipMemAddressFree(ptrB, size_mem));
}
HIP_CHECK(hipMemRelease(handle));
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
SECTION("unmapped address") {
REQUIRE(hipMemRetainAllocationHandle(&gethandle, reinterpret_cast<void*>(ptrA)) ==
hipErrorInvalidValue);
}
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
}
Fichier diff supprimé car celui-ci est trop grand Voir la Diff
+88
Voir le fichier
@@ -0,0 +1,88 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANNTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER INN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR INN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/**
* @addtogroup hipMemUnmap hipMemUnmap
* @{
* @ingroup VirtualMemoryManagementTest
* `hipError_t hipMemUnmap (void* ptr, size_t size)` -
* Unmap memory allocation of a given address range.
*/
#include <hip_test_common.hh>
#include "hip_vmm_common.hh"
constexpr int N = (1 << 13);
/**
* Test Description
* ------------------------
* - Negative Tests
* ------------------------
* - unit/virtualMemoryManagement/hipMemUnmap.cc
* Test requirements
* ------------------------
* - HIP_VERSION >= 6.1
*/
TEST_CASE("Unit_hipMemUnmap_negative") {
size_t granularity = 0;
size_t buffer_size = N * sizeof(int);
int deviceId = 0;
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, deviceId));
checkVMMSupported(device);
hipMemAllocationProp prop{};
prop.type = hipMemAllocationTypePinned;
prop.location.type = hipMemLocationTypeDevice;
prop.location.id = device; // Current Devices
HIP_CHECK(
hipMemGetAllocationGranularity(&granularity, &prop, hipMemAllocationGranularityMinimum));
REQUIRE(granularity > 0);
size_t size_mem = ((granularity + buffer_size - 1) / granularity) * granularity;
hipMemGenericAllocationHandle_t handle;
hipDeviceptr_t ptrA;
// Allocate physical memory
HIP_CHECK(hipMemCreate(&handle, size_mem, &prop, 0));
// Allocate virtual address range
HIP_CHECK(hipMemAddressReserve(&ptrA, size_mem, 0, 0, 0));
HIP_CHECK(hipMemMap(ptrA, size_mem, 0, handle, 0));
SECTION("nullptr to ptrA") { REQUIRE(hipMemUnmap(nullptr, size_mem) == hipErrorInvalidValue); }
SECTION("pass zero to size") { REQUIRE(hipMemUnmap(ptrA, 0) == hipErrorInvalidValue); }
#if HT_NVIDIA
SECTION("unmap a smaller size") {
REQUIRE(hipMemUnmap(ptrA, (size_mem - 1)) == hipErrorInvalidValue);
}
#endif
HIP_CHECK(hipMemRelease(handle));
HIP_CHECK(hipMemUnmap(ptrA, size_mem));
HIP_CHECK(hipMemAddressFree(ptrA, size_mem));
}
+95
Voir le fichier
@@ -0,0 +1,95 @@
/*
Copyright (c) 2022 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANNTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER INN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR INN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
/* Test Case Description:
1) This testcase verifies the basic scenario - supported on
all devices
*/
#include <cstdio>
#include <cstdint>
#include <algorithm>
#include <thread>
#include <chrono>
#include <vector>
#include <hip_test_common.hh>
#include <hip_test_kernels.hh>
#include <hip_test_checkers.hh>
/*
This testcase verifies HIP Mem VMM API basic scenario - supported on all devices
*/
TEST_CASE("Unit_hipMemVmm_Basic") {
int vmm = 0;
HIP_CHECK(hipDeviceGetAttribute(&vmm, hipDeviceAttributeVirtualMemoryManagementSupported, 0));
INFO("hipDeviceAttributeVirtualMemoryManagementSupported: " << vmm);
if (vmm == 0) {
SUCCEED(
"GPU 0 doesn't support hipDeviceAttributeVirtualMemoryManagement "
"attribute. Hence skipping the testing with Pass result.\n");
return;
}
size_t granularity = 0;
hipMemAllocationProp memAllocationProp;
memAllocationProp.type = hipMemAllocationTypePinned;
memAllocationProp.location.id = 0;
memAllocationProp.location.type = hipMemLocationTypeDevice;
HIP_CHECK(hipMemGetAllocationGranularity(&granularity, &memAllocationProp,
hipMemAllocationGranularityRecommended));
size_t size = 4 * 1024;
void* reservedAddress{nullptr};
HIP_CHECK(hipMemAddressReserve(&reservedAddress, size, granularity, nullptr, 0));
hipMemGenericAllocationHandle_t gaHandle{nullptr};
HIP_CHECK(hipMemCreate(&gaHandle, size, &memAllocationProp, 0));
HIP_CHECK(hipMemMap(reservedAddress, size, 0, gaHandle, 0));
hipDevice_t device;
HIP_CHECK(hipDeviceGet(&device, 0));
hipMemAccessDesc desc;
desc.location.type = hipMemLocationTypeDevice;
desc.location.id = device;
desc.flags = hipMemAccessFlagsProtReadWrite;
std::vector<char> values(size);
const char value = 1;
HIP_CHECK(hipMemSetAccess(reservedAddress, size, &desc, 1));
HIP_CHECK(hipMemset(reservedAddress, value, size));
HIP_CHECK(hipMemcpy(&values[0], reservedAddress, size, hipMemcpyDeviceToHost));
for (size_t i = 0; i < size; ++i) {
REQUIRE(values[i] == value);
}
HIP_CHECK(hipMemUnmap(reservedAddress, size));
HIP_CHECK(hipMemRelease(gaHandle));
HIP_CHECK(hipMemAddressFree(reservedAddress, size));
}
+49
Voir le fichier
@@ -0,0 +1,49 @@
/*
Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
#pragma once
#include "hip_test_context.hh"
#define checkVMMSupported(device) \
{ \
int value = 0; \
hipDeviceAttribute_t attr = hipDeviceAttributeVirtualMemoryManagementSupported; \
HIP_CHECK(hipDeviceGetAttribute(&value, attr, device)); \
if (value == 0) { \
HipTest::HIP_SKIP_TEST("Machine does not support VMM. Skipping Test.."); \
return; \
} \
}
#define checkVMMSupportedRetVal(device) \
{ \
int value = 0; \
hipDeviceAttribute_t attr = hipDeviceAttributeVirtualMemoryManagementSupported; \
HIP_CHECK(hipDeviceGetAttribute(&value, attr, device)); \
if (value == 0) { \
HipTest::HIP_SKIP_TEST("Machine does not support VMM. Skipping Test.."); \
return true; \
} \
}
constexpr int threadsPerBlk = 64;