mirror of
git://nv-tegra.nvidia.com/linux-nvgpu.git
synced 2025-12-22 17:36:20 +03:00
Open source GPL/LGPL release
This commit is contained in:
26
userspace/units/mm/allocators/bitmap_allocator/Makefile
Normal file
26
userspace/units/mm/allocators/bitmap_allocator/Makefile
Normal file
@@ -0,0 +1,26 @@
|
||||
# Copyright (c) 2019, NVIDIA CORPORATION. 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.
|
||||
|
||||
.SUFFIXES:
|
||||
|
||||
OBJS = bitmap_allocator.o
|
||||
MODULE = bitmap_allocator
|
||||
|
||||
include ../../../Makefile.units
|
||||
@@ -0,0 +1,33 @@
|
||||
################################### tell Emacs this is a -*- makefile-gmake -*-
|
||||
#
|
||||
# Copyright (c) 2019, NVIDIA CORPORATION. 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.
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
NVGPU_UNIT_NAME=bitmap_allocator
|
||||
|
||||
include $(NV_COMPONENT_DIR)/../../../Makefile.units.common.interface.tmk
|
||||
|
||||
# Local Variables:
|
||||
# indent-tabs-mode: t
|
||||
# tab-width: 8
|
||||
# End:
|
||||
# vi: set tabstop=8 noexpandtab:
|
||||
33
userspace/units/mm/allocators/bitmap_allocator/Makefile.tmk
Normal file
33
userspace/units/mm/allocators/bitmap_allocator/Makefile.tmk
Normal file
@@ -0,0 +1,33 @@
|
||||
################################### tell Emacs this is a -*- makefile-gmake -*-
|
||||
#
|
||||
# Copyright (c) 2019, NVIDIA CORPORATION. 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.
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
NVGPU_UNIT_NAME=bitmap_allocator
|
||||
|
||||
include $(NV_COMPONENT_DIR)/../../../Makefile.units.common.tmk
|
||||
|
||||
# Local Variables:
|
||||
# indent-tabs-mode: t
|
||||
# tab-width: 8
|
||||
# End:
|
||||
# vi: set tabstop=8 noexpandtab:
|
||||
@@ -0,0 +1,394 @@
|
||||
/*
|
||||
* Copyright (c) 2019, NVIDIA CORPORATION. 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.
|
||||
*/
|
||||
|
||||
#include <unit/io.h>
|
||||
#include <unit/unit.h>
|
||||
|
||||
#include <nvgpu/sizes.h>
|
||||
#include <nvgpu/types.h>
|
||||
#include <nvgpu/allocator.h>
|
||||
#include <nvgpu/posix/kmem.h>
|
||||
#include <nvgpu/posix/posix-fault-injection.h>
|
||||
|
||||
#include "common/mm/allocators/bitmap_allocator_priv.h"
|
||||
#include "bitmap_allocator.h"
|
||||
|
||||
#define BA_DEFAULT_BASE SZ_1K
|
||||
#define BA_DEFAULT_LENGTH (SZ_64K << 1)
|
||||
#define BA_DEFAULT_BLK_SIZE SZ_1K
|
||||
#define SZ_2K (SZ_1K << 1)
|
||||
#define SZ_8K (SZ_4K << 1)
|
||||
#define SZ_16K (SZ_4K << 2)
|
||||
#define SZ_32K (SZ_64K >> 1)
|
||||
|
||||
static struct nvgpu_allocator *na;
|
||||
|
||||
int test_nvgpu_bitmap_allocator_critical(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
u64 base = BA_DEFAULT_BASE;
|
||||
u64 length = BA_DEFAULT_LENGTH;
|
||||
u64 blk_size = BA_DEFAULT_BLK_SIZE;
|
||||
u64 flags = GPU_ALLOC_NO_ALLOC_PAGE;
|
||||
u64 addr, addr1;
|
||||
|
||||
na = (struct nvgpu_allocator *)
|
||||
nvgpu_kzalloc(g, sizeof(struct nvgpu_allocator));
|
||||
if (na == NULL) {
|
||||
unit_return_fail(m, "Could not allocate nvgpu_allocator\n");
|
||||
}
|
||||
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_bitmap", base, length,
|
||||
blk_size, 0ULL, flags, BITMAP_ALLOCATOR) != 0) {
|
||||
nvgpu_kfree(g, na);
|
||||
unit_return_fail(m, "bitmap_allocator init failed\n");
|
||||
}
|
||||
|
||||
addr1 = na->ops->alloc(na, SZ_2K);
|
||||
if (addr1 == 0) {
|
||||
unit_err(m, "%d: couldn't allocate 2K bits\n", __LINE__);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
addr = na->ops->alloc_fixed(na, SZ_4K, SZ_8K, SZ_1K);
|
||||
if (addr == 0) {
|
||||
unit_err(m, "%d: alloc_fixed failed to allocate 8K\n",
|
||||
__LINE__);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
/*
|
||||
* Alloate 0 bytes at 64K
|
||||
* Note: 0 bytes are actually allocated. But error handling should
|
||||
* be done by the user.
|
||||
*/
|
||||
addr = na->ops->alloc_fixed(na, SZ_64K, 0ULL, SZ_1K);
|
||||
if (addr == 0) {
|
||||
unit_err(m, "%d: alloc_fixed couldn't alloc 0 bytes at 64K\n",
|
||||
__LINE__);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
addr1 = na->ops->alloc(na, SZ_2K + 4);
|
||||
if (addr1 == 0) {
|
||||
unit_err(m, "%d: alloc failed to allocate 2052 bits\n",
|
||||
__LINE__);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
na->ops->free_alloc(na, addr1);
|
||||
|
||||
na->ops->free_fixed(na, SZ_4K, SZ_8K);
|
||||
|
||||
na->ops->fini(na);
|
||||
nvgpu_kfree(g, na);
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
|
||||
fail:
|
||||
na->ops->fini(na);
|
||||
nvgpu_kfree(g, na);
|
||||
|
||||
return UNIT_FAIL;
|
||||
|
||||
}
|
||||
|
||||
int test_nvgpu_bitmap_allocator_alloc(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
u64 alloc0, alloc3k, alloc4k, alloc_at64, addr, addr_fail;
|
||||
struct nvgpu_posix_fault_inj *kmem_fi =
|
||||
nvgpu_kmem_get_fault_injection();
|
||||
|
||||
/*
|
||||
* len = 0
|
||||
* Expect to fail
|
||||
*/
|
||||
alloc0 = na->ops->alloc(na, 0);
|
||||
if (alloc0 != 0) {
|
||||
unit_err(m, "ops->alloc allocated with len = 0\n");
|
||||
}
|
||||
|
||||
|
||||
alloc3k = na->ops->alloc(na, SZ_2K + 4);
|
||||
if (alloc3k == 0) {
|
||||
unit_return_fail(m, "couldn't allocate 2052 bits\n");
|
||||
}
|
||||
|
||||
/*
|
||||
* 2M is more than available for bitmap
|
||||
* Expect to fail
|
||||
*/
|
||||
addr_fail = na->ops->alloc(na, (SZ_1M << 1));
|
||||
if (addr_fail != 0) {
|
||||
unit_return_fail(m,
|
||||
"bitmap allocated more than available memory\n");
|
||||
}
|
||||
|
||||
/* Fault injection at nvgpu_bitmap_store_alloc */
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, true, 0);
|
||||
addr_fail = na->ops->alloc(na, (SZ_1K << 1));
|
||||
if (addr_fail != 0) {
|
||||
unit_return_fail(m,
|
||||
"ops->alloc allocated despite fault injection\n");
|
||||
}
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, false, 0);
|
||||
|
||||
na->ops->free_alloc(na, alloc3k);
|
||||
|
||||
na->ops->free_alloc(na, alloc3k);
|
||||
|
||||
alloc4k = na->ops->alloc(na, SZ_4K);
|
||||
if (alloc4k == 0) {
|
||||
unit_return_fail(m, "bitmap couldn't allocate 4K");
|
||||
}
|
||||
|
||||
addr = na->ops->alloc(na, SZ_8K);
|
||||
if (addr == 0) {
|
||||
unit_return_fail(m, "bitmap couldn't allocate 8K");
|
||||
}
|
||||
|
||||
addr = na->ops->alloc(na, SZ_16K);
|
||||
if (addr == 0) {
|
||||
unit_return_fail(m, "bitmap couldn't allocate 16K");
|
||||
}
|
||||
|
||||
addr = na->ops->alloc(na, SZ_32K);
|
||||
if (addr == 0) {
|
||||
unit_return_fail(m, "bitmap couldn't allocate 32K");
|
||||
}
|
||||
|
||||
/*
|
||||
* Requesting at allocated base address
|
||||
* Expect to fail
|
||||
*/
|
||||
addr_fail = na->ops->alloc_fixed(na, alloc4k, SZ_4K, SZ_1K);
|
||||
if (addr_fail != 0) {
|
||||
unit_return_fail(m,
|
||||
"allocated at already occupied address\n");
|
||||
}
|
||||
|
||||
/*
|
||||
* Unaligned base
|
||||
* Expect to fail
|
||||
*/
|
||||
addr_fail = na->ops->alloc_fixed(na, (SZ_64K + 1ULL), SZ_4K, SZ_1K);
|
||||
if (addr_fail != 0) {
|
||||
unit_return_fail(m,
|
||||
"ops->alloc_fixed allocated with unaligned base\n");
|
||||
}
|
||||
|
||||
alloc_at64 = na->ops->alloc_fixed(na, SZ_64K, (SZ_64K - 1ULL), SZ_1K);
|
||||
if (alloc_at64 == 0) {
|
||||
unit_return_fail(m,
|
||||
"ops->alloc_fixed failed to allocate 4097 bits\n");
|
||||
}
|
||||
|
||||
/*
|
||||
* Unaligned base
|
||||
* Expect to fail
|
||||
*/
|
||||
if (!EXPECT_BUG(na->ops->free_fixed(na, (SZ_64K + 1ULL), SZ_4K))) {
|
||||
unit_return_fail(m,
|
||||
"freeing unaligned base didn't trigger BUG()\n");
|
||||
}
|
||||
|
||||
na->ops->free_alloc(na, alloc4k);
|
||||
|
||||
/*
|
||||
* Allocate 4K
|
||||
* This allocation will require the bitmap allocator to find available
|
||||
* space before next_blk.
|
||||
*/
|
||||
alloc4k = na->ops->alloc(na, SZ_4K);
|
||||
if (alloc4k == 0) {
|
||||
unit_return_fail(m, "bitmap couldn't allocate 4K");
|
||||
}
|
||||
|
||||
na->ops->free_fixed(na, alloc_at64, (SZ_4K + 1ULL));
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
int test_nvgpu_bitmap_allocator_ops(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
u64 addr;
|
||||
|
||||
if (!na->ops->inited(na)) {
|
||||
unit_return_fail(m, "bitmap ops->inited incorrect\n");
|
||||
}
|
||||
|
||||
addr = na->ops->base(na);
|
||||
if (addr != BA_DEFAULT_BASE) {
|
||||
unit_return_fail(m, "bitmap ops->base incorrect\n");
|
||||
}
|
||||
|
||||
addr = na->ops->length(na);
|
||||
if (addr != BA_DEFAULT_LENGTH) {
|
||||
unit_return_fail(m, "bitmap ops->length incorrect\n");
|
||||
}
|
||||
|
||||
addr = na->ops->end(na);
|
||||
if (addr != (BA_DEFAULT_BASE + BA_DEFAULT_LENGTH)) {
|
||||
unit_return_fail(m, "bitmap ops->end incorrect\n");
|
||||
}
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
int test_nvgpu_bitmap_allocator_destroy(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
na->ops->fini(na);
|
||||
nvgpu_kfree(g, na);
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
int test_nvgpu_bitmap_allocator_init(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
u64 base = BA_DEFAULT_BASE;
|
||||
u64 length = BA_DEFAULT_LENGTH;
|
||||
u64 blk_size = BA_DEFAULT_BLK_SIZE;
|
||||
u64 flags = 0ULL;
|
||||
struct nvgpu_bitmap_allocator *ba;
|
||||
struct nvgpu_posix_fault_inj *kmem_fi =
|
||||
nvgpu_kmem_get_fault_injection();
|
||||
|
||||
na = (struct nvgpu_allocator *)
|
||||
nvgpu_kzalloc(g, sizeof(struct nvgpu_allocator));
|
||||
if (na == NULL) {
|
||||
unit_return_fail(m, "Could not allocate nvgpu_allocator\n");
|
||||
}
|
||||
|
||||
/* base = 0, length = 0, blk_size = 0 */
|
||||
if (!EXPECT_BUG(nvgpu_allocator_init(g, na, NULL, "test_bitmap", 0ULL,
|
||||
0ULL, 0ULL, 0ULL, flags, BITMAP_ALLOCATOR))) {
|
||||
na->ops->fini(na);
|
||||
unit_return_fail(m,
|
||||
"bitmap inited despite blk_size = base = length = 0\n");
|
||||
}
|
||||
|
||||
/*
|
||||
* blk_size = 0
|
||||
* Since base and length are not aligned with 0, init fails
|
||||
*/
|
||||
if (!EXPECT_BUG(nvgpu_allocator_init(g, na, NULL, "test_bitmap", base,
|
||||
length, 0ULL, 0ULL, flags, BITMAP_ALLOCATOR))) {
|
||||
unit_return_fail(m, "bitmap inited despite blk_size=0\n");
|
||||
}
|
||||
|
||||
/* Odd blk_size */
|
||||
if (!EXPECT_BUG(nvgpu_allocator_init(g, na, NULL, "test_bitmap", base,
|
||||
length, 3ULL, 0ULL, flags, BITMAP_ALLOCATOR))) {
|
||||
unit_return_fail(m, "bitmap inited despite odd blk_size\n");
|
||||
}
|
||||
|
||||
/* length unaligned */
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_bitmap", base, 0x0010,
|
||||
blk_size, 0ULL, flags, BITMAP_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m, "bitmap init despite unaligned length\n");
|
||||
}
|
||||
|
||||
/* base unaligned */
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_bitmap", 0x0100, length,
|
||||
blk_size, 0ULL, flags, BITMAP_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m, "bitmap init despite unaligned base\n");
|
||||
}
|
||||
|
||||
/* base = 0 */
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_bitmap", 0ULL, length,
|
||||
blk_size, 0ULL, flags, BITMAP_ALLOCATOR) != 0) {
|
||||
unit_return_fail(m, "bitmap init failed with base = 0\n");
|
||||
} else {
|
||||
ba = na->priv;
|
||||
if (ba->base != ba->blk_size) {
|
||||
na->ops->fini(na);
|
||||
unit_return_fail(m, "bitmap init with base=0 "
|
||||
"didn't update base = blk_size\n");
|
||||
}
|
||||
ba = NULL;
|
||||
na->ops->fini(na);
|
||||
}
|
||||
|
||||
/* length = 0 */
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_bitmap", 0ULL, 0ULL,
|
||||
blk_size, 0ULL, flags, BITMAP_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m, "bitmap inited with length = 0\n");
|
||||
}
|
||||
|
||||
/* Fault injection at nvgpu_bitmap_allocator alloc */
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, true, 0);
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_bitmap", base, length,
|
||||
blk_size, 0ULL, flags, BITMAP_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m, "bitmap inited despite "
|
||||
"fault injection at nvgpu_bitmap_allocator alloc\n");
|
||||
}
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, false, 0);
|
||||
|
||||
/* Fault injection at meta_data_cache create */
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, true, 1);
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_bitmap", base, length,
|
||||
blk_size, 0ULL, flags, BITMAP_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m, "bitmap inited despite "
|
||||
"fault injection at meta_data_cache\n");
|
||||
}
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, false, 0);
|
||||
|
||||
/* Fault injection at bitmap create */
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, true, 2);
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_bitmap", base, length,
|
||||
blk_size, 0ULL, flags, BITMAP_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m, "bitmap inited despite "
|
||||
"fault injection at bitmap create\n");
|
||||
}
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, false, 0);
|
||||
|
||||
/*
|
||||
* Initialize bitmap allocator
|
||||
* This ba will be used for further tests.
|
||||
*/
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_bitmap", base, length,
|
||||
blk_size, 0ULL, flags, BITMAP_ALLOCATOR) != 0) {
|
||||
unit_return_fail(m, "bitmap_allocator init failed\n");
|
||||
}
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
struct unit_module_test bitmap_allocator_tests[] = {
|
||||
|
||||
/* BA initialized in this test is used by next tests */
|
||||
UNIT_TEST(init, test_nvgpu_bitmap_allocator_init, NULL, 0),
|
||||
|
||||
/* These tests use bitmap allocator created in the first test */
|
||||
UNIT_TEST(ops, test_nvgpu_bitmap_allocator_ops, NULL, 0),
|
||||
UNIT_TEST(alloc, test_nvgpu_bitmap_allocator_alloc, NULL, 0),
|
||||
UNIT_TEST(free, test_nvgpu_bitmap_allocator_destroy, NULL, 0),
|
||||
|
||||
/* Tests GPU_ALLOC_NO_ALLOC_PAGE operations by bitmap allocator */
|
||||
UNIT_TEST(critical, test_nvgpu_bitmap_allocator_critical, NULL, 0),
|
||||
};
|
||||
|
||||
UNIT_MODULE(bitmap_allocator, bitmap_allocator_tests, UNIT_PRIO_NVGPU_TEST);
|
||||
@@ -0,0 +1,168 @@
|
||||
/*
|
||||
* Copyright (c) 2019-2020, NVIDIA CORPORATION. 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.
|
||||
*/
|
||||
|
||||
#ifndef UNIT_BITMAP_ALLOCATOR_H
|
||||
#define UNIT_BITMAP_ALLOCATOR_H
|
||||
|
||||
struct gk20a;
|
||||
struct unit_module;
|
||||
|
||||
/** @addtogroup SWUTS-mm-allocators-bitmap-allocator
|
||||
* @{
|
||||
*
|
||||
* Software Unit Test Specification for mm.allocators.bitmap_allocator
|
||||
*/
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_bitmap_allocator_init
|
||||
*
|
||||
* Description: Initialize bitmap allocator.
|
||||
*
|
||||
* Test Type: Feature, Error injection
|
||||
*
|
||||
* Targets: nvgpu_bitmap_allocator_init, nvgpu_bitmap_check_argument_limits,
|
||||
* nvgpu_allocator.ops.fini, nvgpu_alloc_to_gpu
|
||||
*
|
||||
* Input: None
|
||||
*
|
||||
* Steps:
|
||||
* - Initialize bitmap allocator with following characteristics.
|
||||
* - 1K memory base address.
|
||||
* - 128K length of memory.
|
||||
* - 1K block size.
|
||||
* - Use this bitmap allocator for rest of the tests.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_bitmap_allocator_init(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_bitmap_allocator_ops
|
||||
*
|
||||
* Description: Check bitmap_allocator attribute values using allocator ops.
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_allocator.ops.base, nvgpu_allocator.ops.length,
|
||||
* nvgpu_allocator.ops.end, nvgpu_allocator.ops.inited
|
||||
*
|
||||
* Input: test_nvgpu_bitmap_allocator_init
|
||||
*
|
||||
* Steps:
|
||||
* - Check bitmap_allocator attributes using allocator ops.
|
||||
* - Execute allocator ops to read attibute value.
|
||||
* - Confirm that value is equal to the default values set during
|
||||
* initialization.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_bitmap_allocator_ops(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_bitmap_allocator_alloc
|
||||
*
|
||||
* Description: Allocate various sizes of memory to test different scenarios.
|
||||
*
|
||||
* Test Type: Feature, Error injection
|
||||
*
|
||||
* Targets: nvgpu_allocator.ops.alloc, nvgpu_allocator.ops.free_alloc,
|
||||
* nvgpu_allocator.ops.alloc_fixed, nvgpu_allocator.ops.free_fixed,
|
||||
* nvgpu_bitmap_alloc_from_rbtree_node, bitmap_allocator,
|
||||
* alloc_loc, alloc_unlock
|
||||
*
|
||||
* Input: test_nvgpu_bitmap_allocator_init
|
||||
*
|
||||
* Steps:
|
||||
* - Allocate 3k memory using allocation functions.
|
||||
* - Confirm that allocation is successful.
|
||||
* - Allocate 2M which is more than available memory.
|
||||
* - Allocation is expected to fail.
|
||||
* - Allocate 4K, 8K, 16K and 32K memory segments.
|
||||
* - Confirm all allocations are successful.
|
||||
* - Allocate various memory segments using fixed allocation functions.
|
||||
* - Confirm aloocations are successful as expected.
|
||||
* - Free allocations.
|
||||
* - Confirm allocations are freed.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_bitmap_allocator_alloc(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_bitmap_allocator_destroy
|
||||
*
|
||||
* Description: Free memory used for bitmap allocator.
|
||||
*
|
||||
* Test Type: Other (clean up)
|
||||
*
|
||||
* Targets: nvgpu_allocator.ops.fini
|
||||
*
|
||||
* Input: test_nvgpu_bitmap_allocator_init
|
||||
*
|
||||
* Steps:
|
||||
* - Free bitmap_allocator allocated for this unit test.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_bitmap_allocator_destroy(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_bitmap_allocator_critical
|
||||
*
|
||||
* Description: Test allocator functions for bitmap allocator in latency
|
||||
* critical path.
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_allocator_init, nvgpu_bitmap_allocator_init,
|
||||
* nvgpu_bitmap_check_argument_limits, nvgpu_allocator.ops.alloc
|
||||
* nvgpu_allocator.ops.free_alloc, nvgpu_allocator.ops.alloc_fixed,
|
||||
* nvgpu_allocator.ops.free_fixed, nvgpu_allocator.ops.fini
|
||||
*
|
||||
* Input: None
|
||||
*
|
||||
* Steps:
|
||||
* - Initialize allocator with following characteristics.
|
||||
* - 1K memory base address.
|
||||
* - 128K memory length.
|
||||
* - 1K block size.
|
||||
* - GPU_ALLOC_NO_ALLOC_PAGE flag value.
|
||||
* - Allocate memory segments using allocation functions.
|
||||
* - Confirm allocations are successful.
|
||||
* - Free allocated memory segments.
|
||||
* - Free bitmap allocator used for this test.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_bitmap_allocator_critical(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
#endif /* UNIT_BITMAP_ALLOCATOR_H */
|
||||
26
userspace/units/mm/allocators/buddy_allocator/Makefile
Normal file
26
userspace/units/mm/allocators/buddy_allocator/Makefile
Normal file
@@ -0,0 +1,26 @@
|
||||
# Copyright (c) 2019, NVIDIA CORPORATION. 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.
|
||||
|
||||
.SUFFIXES:
|
||||
|
||||
OBJS = buddy_allocator.o
|
||||
MODULE = buddy_allocator
|
||||
|
||||
include ../../../Makefile.units
|
||||
@@ -0,0 +1,33 @@
|
||||
################################### tell Emacs this is a -*- makefile-gmake -*-
|
||||
#
|
||||
# Copyright (c) 2019, NVIDIA CORPORATION. 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.
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
NVGPU_UNIT_NAME=buddy_allocator
|
||||
|
||||
include $(NV_COMPONENT_DIR)/../../../Makefile.units.common.interface.tmk
|
||||
|
||||
# Local Variables:
|
||||
# indent-tabs-mode: t
|
||||
# tab-width: 8
|
||||
# End:
|
||||
# vi: set tabstop=8 noexpandtab:
|
||||
33
userspace/units/mm/allocators/buddy_allocator/Makefile.tmk
Normal file
33
userspace/units/mm/allocators/buddy_allocator/Makefile.tmk
Normal file
@@ -0,0 +1,33 @@
|
||||
################################### tell Emacs this is a -*- makefile-gmake -*-
|
||||
#
|
||||
# Copyright (c) 2019, NVIDIA CORPORATION. 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.
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
NVGPU_UNIT_NAME=buddy_allocator
|
||||
|
||||
include $(NV_COMPONENT_DIR)/../../../Makefile.units.common.tmk
|
||||
|
||||
# Local Variables:
|
||||
# indent-tabs-mode: t
|
||||
# tab-width: 8
|
||||
# End:
|
||||
# vi: set tabstop=8 noexpandtab:
|
||||
1052
userspace/units/mm/allocators/buddy_allocator/buddy_allocator.c
Normal file
1052
userspace/units/mm/allocators/buddy_allocator/buddy_allocator.c
Normal file
File diff suppressed because it is too large
Load Diff
290
userspace/units/mm/allocators/buddy_allocator/buddy_allocator.h
Normal file
290
userspace/units/mm/allocators/buddy_allocator/buddy_allocator.h
Normal file
@@ -0,0 +1,290 @@
|
||||
/*
|
||||
* Copyright (c) 2019-2020, NVIDIA CORPORATION. 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.
|
||||
*/
|
||||
|
||||
#ifndef UNIT_BUDDY_ALLOCATOR_H
|
||||
#define UNIT_BUDDY_ALLOCATOR_H
|
||||
|
||||
struct gk20a;
|
||||
struct unit_module;
|
||||
|
||||
/** @addtogroup SWUTS-mm-allocators-buddy-allocator
|
||||
* @{
|
||||
*
|
||||
* Software Unit Test Specification for mm.allocators.buddy_allocator
|
||||
*/
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_buddy_allocator_init
|
||||
*
|
||||
* Description: Initialize buddy allocator.
|
||||
*
|
||||
* Test Type: Feature, Error injection
|
||||
*
|
||||
* Targets: nvgpu_allocator_init, nvgpu_buddy_allocator_init,
|
||||
* nvgpu_buddy_check_argument_limits, nvgpu_buddy_set_attributes,
|
||||
* balloc_allocator_align, balloc_compute_max_order, balloc_init_lists,
|
||||
* balloc_max_order_in, balloc_get_order, balloc_get_order_list,
|
||||
* nvgpu_allocator.ops.fini
|
||||
*
|
||||
* Input: None
|
||||
*
|
||||
* Steps:
|
||||
* - Allocate memory for nvgpu allocator
|
||||
* - Initialize buddy allocator with different parameters to test init function.
|
||||
* - zero block size.
|
||||
* - block size which is not power of 2.
|
||||
* - max order set greater than GPU_BALLOC_MAX_ORDER.
|
||||
* - zero memory size.
|
||||
* - base address zero.
|
||||
* - unaligned base address.
|
||||
* - Confirm the output of the above test cases is as expected.
|
||||
* - Initialize buddy allocator with following attributes.
|
||||
* - 4K base address.
|
||||
* - 1M memory size.
|
||||
* - 4K block size.
|
||||
* - max order equal to GPU_BALLOC_MAX_ORDER.
|
||||
* - flags set to NULL.
|
||||
* - NULL vm.
|
||||
* - GVA space disabled.
|
||||
* - This initialized allocator will be used for this unit test.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_buddy_allocator_init(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_buddy_allocator_carveout
|
||||
*
|
||||
* Description: Test allocation of carveouts.
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_allocator.ops.alloc, nvgpu_allocator.ops.reserve_carveout,
|
||||
* nvgpu_allocator.ops.release_carveout,
|
||||
* nvgpu_alloc_carveout_from_co_entry
|
||||
*
|
||||
* Input: test_nvgpu_buddy_allocator_init
|
||||
*
|
||||
* Steps:
|
||||
* - Allocate segment of memory as carveout.
|
||||
* - Use reserved_carveout operation of buddy allocator to portion out segment
|
||||
* of memory.
|
||||
* - Confirm that the carveout is successful.
|
||||
* - Test carveout allocation with below variations.
|
||||
* - Carveout base address less than buddy allocator base address.
|
||||
* - Carveout length more than buddy allocator size.
|
||||
* - Unaligned base address.
|
||||
* - Reserve carveout after normal memory allocation.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_buddy_allocator_carveout(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_buddy_allocator_basic_ops
|
||||
*
|
||||
* Description: Test buddy allocator attribute and allocation functions.
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_allocator.ops.base, nvgpu_allocator.ops.length,
|
||||
* nvgpu_allocator.ops.end, nvgpu_allocator.ops.inited,
|
||||
* nvgpu_allocator.ops.space, nvgpu_allocator.ops.alloc,
|
||||
* nvgpu_allocator.ops.alloc_pte, nvgpu_allocator.ops.free_alloc,
|
||||
* nvgpu_allocator.ops.alloc_fixed, nvgpu_buddy_allocator_flag_ops,
|
||||
* nvgpu_buddy_from_buddy_entry, balloc_base_shift, buddy_allocator,
|
||||
* balloc_base_unshift, balloc_owner, balloc_order_to_len, alloc_lock,
|
||||
* alloc_unlock, nvgpu_alloc_to_gpu, nvgpu_buddy_from_rbtree_node,
|
||||
* nvgpu_fixed_alloc_from_rbtree_node
|
||||
*
|
||||
* Input: test_nvgpu_buddy_allocator_init
|
||||
*
|
||||
* Steps:
|
||||
* - Check buddy allocator attribute values.
|
||||
* - Use buddy allocator ops to check base, length, end and space values.
|
||||
* - Confirm that values match init values.
|
||||
* - Test memory allocation functions.
|
||||
* - Use alloc and alloc_fixed ops to allocate chunk of memory
|
||||
* - Confirm allocation is successful.
|
||||
* - Test allocation ops with below vaiations.
|
||||
* - Zero length memory segment.
|
||||
* - Allocate more than available memory.
|
||||
* - Unaligned base.
|
||||
* - Base address equal to previously assigned carveout base.
|
||||
* - Zero PTE size.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_buddy_allocator_basic_ops(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_buddy_allocator_destroy
|
||||
*
|
||||
* Description: Free buddy allocator used for previous tests.
|
||||
*
|
||||
* Test Type: Other (cleanup)
|
||||
*
|
||||
* Targets: nvgpu_allocator.ops.fini
|
||||
*
|
||||
* Input: test_nvgpu_buddy_allocator_init
|
||||
*
|
||||
* Steps:
|
||||
* - Free using buddy allocator fini ops
|
||||
* - Free nvgpu allocator
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_buddy_allocator_destroy(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_buddy_allocator_alloc
|
||||
*
|
||||
* Description: Test cleanup branch of memory allocations.
|
||||
*
|
||||
* Test Type: Feature, Error injection
|
||||
*
|
||||
* Targets: nvgpu_allocator_init, nvgpu_allocator.ops.alloc,
|
||||
* nvgpu_allocator.ops.alloc_fixed, nvgpu_buddy_allocator_flag_ops,
|
||||
* nvgpu_allocator.ops.fini
|
||||
*
|
||||
* Input: None
|
||||
*
|
||||
* Steps:
|
||||
* - Allocate nvgpu and buddy allocator for this test
|
||||
* - 4K base address.
|
||||
* - 1M memory size.
|
||||
* - 1K block size.
|
||||
* - Zero max order.
|
||||
* - flags set to 0.
|
||||
* - NULL vm.
|
||||
* - GVA space disabled.
|
||||
* - Inject fault at specific step to test alloc function cleanup.
|
||||
* - Allocate fixed memory segment, when part of memory is already allocated.
|
||||
* - Use alloc_fixed to test if such allocation is successful
|
||||
* - Test buddy allocator destroy function
|
||||
* - Increase count of buddy, split buddy and alloced buddy list lengths one
|
||||
* by one and check if destroy function triggers BUG()
|
||||
* - Free nvgpu and buddy allocator used in this test
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_buddy_allocator_alloc(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_buddy_allocator_with_small_pages
|
||||
*
|
||||
* Description: Test buddy allocator functions with big pages disabled.
|
||||
*
|
||||
* Test Type: Feature, Error injection
|
||||
*
|
||||
* Targets: nvgpu_allocator_init, nvgpu_buddy_allocator_init,
|
||||
* nvgpu_buddy_check_argument_limits, nvgpu_allocator.ops.inited
|
||||
* nvgpu_buddy_set_attributes, nvgpu_allocator.ops.alloc_pte,
|
||||
* nvgpu_allocator.ops.alloc_fixed, nvgpu_allocator.ops.fini
|
||||
*
|
||||
* Input: None
|
||||
*
|
||||
* Steps:
|
||||
* - Initialize vm environment with below characteristics.
|
||||
* - low_hole = 64K.
|
||||
* - aperture_size = GK20A_PMU_VA_SIZE.
|
||||
* - kernel_reserved = aperture_size - low_hole.
|
||||
* - flags = GPU_ALLOC_GVA_SPACE, GVA space enabled.
|
||||
* - userspace_managed = false, unified_va = false.
|
||||
* - big_pages = false.
|
||||
* - Initialize buddy allocator for this test.
|
||||
* - Base address = 1K.
|
||||
* - Allocator size = 1M.
|
||||
* - Block size = 1K.
|
||||
* - max order = 10.
|
||||
* - GVA space enabled.
|
||||
* - vm initialized in the previous step.
|
||||
* - Test sincere allocations with buddy allocator ops.
|
||||
* - Test alloc ops with below variations.
|
||||
* - Request more than available memory.
|
||||
* - Alloc with size unaligned with respect to PTE size.
|
||||
* - unusual page size.
|
||||
* - Length zero memory segment.
|
||||
* - Inject faults to test cleanup code.
|
||||
* - Free buddy allocator.
|
||||
* - Free vm environment.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_buddy_allocator_with_small_pages(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_buddy_allocator_with_big_pages
|
||||
*
|
||||
* Description: Test buddy allocator functions with big pages enabled.
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_allocator_init, nvgpu_buddy_allocator_init,
|
||||
* nvgpu_buddy_check_argument_limits, nvgpu_buddy_set_attributes,
|
||||
* nvgpu_allocator.ops.alloc_pte, nvgpu_allocator.ops.alloc_fixed
|
||||
* nvgpu_allocator.ops.alloc, nvgpu_allocator.ops.free_alloc,
|
||||
* nvgpu_allocator.ops.fini
|
||||
*
|
||||
* Input: None
|
||||
*
|
||||
* Steps:
|
||||
* - Initialize vm environment with below characteristics.
|
||||
* - low_hole = 64K.
|
||||
* - aperture_size = GK20A_PMU_VA_SIZE.
|
||||
* - kernel_reserved = aperture_size - low_hole.
|
||||
* - flags = GPU_ALLOC_GVA_SPACE, GVA space enabled.
|
||||
* - userspace_managed = false, unified_va = false.
|
||||
* - big_pages = true.
|
||||
* - Initialize buddy allocator for this test.
|
||||
* - Base address = 64M, PDE aligned.
|
||||
* - Allocator size = 256M.
|
||||
* - Block size = 4K.
|
||||
* - max order = GPU_BALLOC_MAX_ORDER.
|
||||
* - GVA space enabled.
|
||||
* - vm initialized in the previous step.
|
||||
* - Test sincere allocations with buddy allocator ops
|
||||
* - Test alloc ops with below variations
|
||||
* - base address less than buddy allocator base address
|
||||
* - unusual page size
|
||||
* - Free buddy allocator
|
||||
* - Free vm environment
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_buddy_allocator_with_big_pages(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
#endif /* UNIT_BUDDY_ALLOCATOR_H */
|
||||
26
userspace/units/mm/allocators/nvgpu_allocator/Makefile
Normal file
26
userspace/units/mm/allocators/nvgpu_allocator/Makefile
Normal file
@@ -0,0 +1,26 @@
|
||||
# Copyright (c) 2018, NVIDIA CORPORATION. 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.
|
||||
|
||||
.SUFFIXES:
|
||||
|
||||
OBJS = nvgpu_allocator.o
|
||||
MODULE = nvgpu_allocator
|
||||
|
||||
include ../../../Makefile.units
|
||||
@@ -0,0 +1,35 @@
|
||||
################################### tell Emacs this is a -*- makefile-gmake -*-
|
||||
#
|
||||
# Copyright (c) 2018-2019, NVIDIA CORPORATION. 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.
|
||||
#
|
||||
# tmake for SW Mobile component makefile
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
NVGPU_UNIT_NAME=nvgpu_allocator
|
||||
|
||||
include $(NV_COMPONENT_DIR)/../../../Makefile.units.common.interface.tmk
|
||||
|
||||
# Local Variables:
|
||||
# indent-tabs-mode: t
|
||||
# tab-width: 8
|
||||
# End:
|
||||
# vi: set tabstop=8 noexpandtab:
|
||||
35
userspace/units/mm/allocators/nvgpu_allocator/Makefile.tmk
Normal file
35
userspace/units/mm/allocators/nvgpu_allocator/Makefile.tmk
Normal file
@@ -0,0 +1,35 @@
|
||||
################################### tell Emacs this is a -*- makefile-gmake -*-
|
||||
#
|
||||
# Copyright (c) 2018-2019, NVIDIA CORPORATION. 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.
|
||||
#
|
||||
# tmake for SW Mobile component makefile
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
NVGPU_UNIT_NAME=nvgpu_allocator
|
||||
|
||||
include $(NV_COMPONENT_DIR)/../../../Makefile.units.common.tmk
|
||||
|
||||
# Local Variables:
|
||||
# indent-tabs-mode: t
|
||||
# tab-width: 8
|
||||
# End:
|
||||
# vi: set tabstop=8 noexpandtab:
|
||||
356
userspace/units/mm/allocators/nvgpu_allocator/nvgpu_allocator.c
Normal file
356
userspace/units/mm/allocators/nvgpu_allocator/nvgpu_allocator.c
Normal file
@@ -0,0 +1,356 @@
|
||||
/*
|
||||
* Copyright (c) 2018-2020, NVIDIA CORPORATION. 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.
|
||||
*/
|
||||
|
||||
#include <unit/io.h>
|
||||
#include <unit/unit.h>
|
||||
|
||||
#include <nvgpu/types.h>
|
||||
#include <nvgpu/sizes.h>
|
||||
#include <nvgpu/allocator.h>
|
||||
|
||||
#include "nvgpu_allocator.h"
|
||||
|
||||
#define OP_ALLOC 0
|
||||
#define OP_FREE 1
|
||||
#define OP_ALLOC_PTE 2
|
||||
#define OP_ALLOC_FIXED 3
|
||||
#define OP_FREE_FIXED 4
|
||||
#define OP_RESERVE_CARVEOUT 5
|
||||
#define OP_RELEASE_CARVEOUT 6
|
||||
#define OP_BASE 7
|
||||
#define OP_LENGTH 8
|
||||
#define OP_END 9
|
||||
#define OP_INITED 10
|
||||
#define OP_SPACE 11
|
||||
#define OP_NUMBER 12
|
||||
static bool dummy_op_called[OP_NUMBER];
|
||||
static const char *ops_str[] = {
|
||||
"alloc",
|
||||
"free_alloc",
|
||||
"alloc_pte",
|
||||
"alloc_fixed",
|
||||
"free fixed",
|
||||
"reserve_carveout",
|
||||
"release_carveout",
|
||||
"base",
|
||||
"length",
|
||||
"end",
|
||||
"inited",
|
||||
"space",
|
||||
};
|
||||
|
||||
static u64 dummy_alloc(struct nvgpu_allocator *allocator, u64 len)
|
||||
{
|
||||
dummy_op_called[OP_ALLOC] = true;
|
||||
return 0ULL;
|
||||
}
|
||||
|
||||
static void dummy_free(struct nvgpu_allocator *allocator, u64 addr)
|
||||
{
|
||||
dummy_op_called[OP_FREE] = true;
|
||||
}
|
||||
|
||||
static u64 dummy_alloc_pte(struct nvgpu_allocator *allocator, u64 len,
|
||||
u32 page_size)
|
||||
{
|
||||
dummy_op_called[OP_ALLOC_PTE] = true;
|
||||
return 0ULL;
|
||||
}
|
||||
|
||||
static u64 dummy_alloc_fixed(struct nvgpu_allocator *allocator,
|
||||
u64 base, u64 len, u32 page_size)
|
||||
{
|
||||
dummy_op_called[OP_ALLOC_FIXED] = true;
|
||||
return 0ULL;
|
||||
}
|
||||
|
||||
static void dummy_free_fixed(struct nvgpu_allocator *allocator,
|
||||
u64 base, u64 len)
|
||||
{
|
||||
dummy_op_called[OP_FREE_FIXED] = true;
|
||||
}
|
||||
|
||||
static int dummy_reserve_carveout(struct nvgpu_allocator *allocator,
|
||||
struct nvgpu_alloc_carveout *co)
|
||||
{
|
||||
dummy_op_called[OP_RESERVE_CARVEOUT] = true;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void dummy_release_carveout(struct nvgpu_allocator *allocator,
|
||||
struct nvgpu_alloc_carveout *co)
|
||||
{
|
||||
dummy_op_called[OP_RELEASE_CARVEOUT] = true;
|
||||
}
|
||||
|
||||
static u64 dummy_base(struct nvgpu_allocator *allocator)
|
||||
{
|
||||
dummy_op_called[OP_BASE] = true;
|
||||
return 0ULL;
|
||||
}
|
||||
|
||||
static u64 dummy_length(struct nvgpu_allocator *allocator)
|
||||
{
|
||||
dummy_op_called[OP_LENGTH] = true;
|
||||
return 0ULL;
|
||||
}
|
||||
|
||||
static u64 dummy_end(struct nvgpu_allocator *allocator)
|
||||
{
|
||||
dummy_op_called[OP_END] = true;
|
||||
return 0ULL;
|
||||
}
|
||||
|
||||
static bool dummy_inited(struct nvgpu_allocator *allocator)
|
||||
{
|
||||
dummy_op_called[OP_INITED] = true;
|
||||
return false;
|
||||
}
|
||||
|
||||
static u64 dummy_space(struct nvgpu_allocator *allocator)
|
||||
{
|
||||
dummy_op_called[OP_SPACE] = true;
|
||||
return false;
|
||||
}
|
||||
|
||||
static void dummy_fini(struct nvgpu_allocator *allocator)
|
||||
{
|
||||
}
|
||||
|
||||
static struct nvgpu_allocator_ops dummy_ops = {
|
||||
.alloc = dummy_alloc,
|
||||
.free_alloc = dummy_free,
|
||||
.alloc_pte = dummy_alloc_pte,
|
||||
.alloc_fixed = dummy_alloc_fixed,
|
||||
.free_fixed = dummy_free_fixed,
|
||||
.reserve_carveout = dummy_reserve_carveout,
|
||||
.release_carveout = dummy_release_carveout,
|
||||
.base = dummy_base,
|
||||
.length = dummy_length,
|
||||
.end = dummy_end,
|
||||
.inited = dummy_inited,
|
||||
.space = dummy_space,
|
||||
.fini = dummy_fini
|
||||
};
|
||||
|
||||
int test_nvgpu_alloc_ops_present(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
u32 i;
|
||||
int err;
|
||||
bool failed;
|
||||
struct nvgpu_allocator a;
|
||||
|
||||
memset(dummy_op_called, 0, sizeof(dummy_op_called));
|
||||
|
||||
err = nvgpu_alloc_common_init(&a, NULL, "test",
|
||||
NULL, false, &dummy_ops);
|
||||
if (err)
|
||||
unit_return_fail(m, "Unexpected common_init() fail!\n");
|
||||
|
||||
/*
|
||||
* Now that we have the allocator just call all the alloc functions and
|
||||
* make sure that the associated bool is true.
|
||||
*/
|
||||
nvgpu_alloc(&a, 0UL);
|
||||
nvgpu_alloc_pte(&a, 0UL, 0U);
|
||||
nvgpu_alloc_fixed(&a, 0UL, 0UL, 0U);
|
||||
nvgpu_free(&a, 0UL);
|
||||
nvgpu_free_fixed(&a, 0UL, 0UL);
|
||||
|
||||
nvgpu_alloc_reserve_carveout(&a, NULL);
|
||||
nvgpu_alloc_release_carveout(&a, NULL);
|
||||
|
||||
nvgpu_alloc_base(&a);
|
||||
nvgpu_alloc_length(&a);
|
||||
nvgpu_alloc_end(&a);
|
||||
nvgpu_alloc_initialized(&a);
|
||||
nvgpu_alloc_space(&a);
|
||||
|
||||
failed = false;
|
||||
for (i = 0; i < OP_NUMBER; i++) {
|
||||
if (!dummy_op_called[i]) {
|
||||
failed = true;
|
||||
unit_info(m, "%s did not call op function!\n",
|
||||
ops_str[i]);
|
||||
}
|
||||
}
|
||||
|
||||
if (failed)
|
||||
unit_return_fail(m, "OPs uncalled!\n");
|
||||
|
||||
/*
|
||||
* Next make sure that if the ops are NULL we don't crash or anything
|
||||
* like that.
|
||||
*
|
||||
* Note that not all ops have if NULL checks. We skip these in the unit
|
||||
* test.
|
||||
*/
|
||||
memset(dummy_op_called, 0, sizeof(dummy_op_called));
|
||||
memset(&dummy_ops, 0, sizeof(dummy_ops));
|
||||
|
||||
nvgpu_alloc_fixed(&a, 0UL, 0UL, 0U);
|
||||
nvgpu_free_fixed(&a, 0UL, 0UL);
|
||||
|
||||
nvgpu_alloc_reserve_carveout(&a, NULL);
|
||||
nvgpu_alloc_release_carveout(&a, NULL);
|
||||
|
||||
nvgpu_alloc_base(&a);
|
||||
nvgpu_alloc_length(&a);
|
||||
nvgpu_alloc_end(&a);
|
||||
nvgpu_alloc_initialized(&a);
|
||||
nvgpu_alloc_space(&a);
|
||||
|
||||
failed = false;
|
||||
for (i = 0; i < OP_NUMBER; i++) {
|
||||
if (dummy_op_called[i]) {
|
||||
failed = true;
|
||||
unit_info(m, "op function %s called despite null op!\n",
|
||||
ops_str[i]);
|
||||
}
|
||||
}
|
||||
|
||||
if (failed)
|
||||
unit_return_fail(m, "OPs called!\n");
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
int test_nvgpu_alloc_common_init(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
struct nvgpu_allocator a;
|
||||
struct nvgpu_allocator_ops ops = { };
|
||||
void *dummy_priv = (void *)0x10000;
|
||||
void *dummy_g = (void *)0x1000;
|
||||
|
||||
if (nvgpu_alloc_common_init(NULL, NULL, NULL, NULL, false, NULL) == 0)
|
||||
unit_return_fail(m, "Made NULL allocator!?\n");
|
||||
|
||||
/*
|
||||
* Hit all the invalid ops struct criteria.
|
||||
*/
|
||||
if (nvgpu_alloc_common_init(&a, NULL, "test", NULL, false, &ops) == 0)
|
||||
unit_return_fail(m, "common_init passes despite empty ops\n");
|
||||
|
||||
ops.alloc = dummy_alloc;
|
||||
if (nvgpu_alloc_common_init(&a, NULL, "test", NULL, false, &ops) == 0)
|
||||
unit_return_fail(m,
|
||||
"common_init passes despite missing free(),fini()\n");
|
||||
|
||||
ops.free_alloc = dummy_free;
|
||||
if (nvgpu_alloc_common_init(&a, NULL, "test", NULL, false, &ops) == 0)
|
||||
unit_return_fail(m,
|
||||
"common_init passes despite missing fini()\n");
|
||||
|
||||
ops.fini = dummy_fini;
|
||||
if (0 != nvgpu_alloc_common_init(&a, dummy_g, "test",
|
||||
dummy_priv, true, &ops))
|
||||
unit_return_fail(m, "common_init should have passed\n");
|
||||
|
||||
/*
|
||||
* Verify that the allocator struct actually is made correctly.
|
||||
*/
|
||||
if (a.g != dummy_g || a.priv != dummy_priv ||
|
||||
a.debug != true || a.ops != &ops)
|
||||
unit_return_fail(m, "Invalid data in allocator\n");
|
||||
|
||||
if (strcmp(a.name, "test") != 0)
|
||||
unit_return_fail(m, "Invalid name in allocator\n");
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
int test_nvgpu_alloc_destroy(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
struct nvgpu_allocator a;
|
||||
struct nvgpu_allocator zero_a = { };
|
||||
struct nvgpu_allocator_ops ops = {
|
||||
.alloc = dummy_alloc,
|
||||
.free_alloc = dummy_free,
|
||||
.fini = dummy_fini,
|
||||
};
|
||||
|
||||
|
||||
if (nvgpu_alloc_common_init(&a, NULL, "test", NULL, false, &ops) != 0)
|
||||
unit_return_fail(m, "common_init failed with valid input\n");
|
||||
|
||||
nvgpu_alloc_destroy(&a);
|
||||
|
||||
|
||||
if (memcmp(&a, &zero_a, sizeof(a)) != 0)
|
||||
unit_return_fail(m, "Allocator has not been memset to 0\n");
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
int test_nvgpu_allocator_init(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
struct nvgpu_allocator a;
|
||||
u64 base = SZ_4K;
|
||||
u64 size = SZ_64K;
|
||||
u64 blk_size = SZ_4K;
|
||||
u64 max_order = 0;
|
||||
u64 flags = 0ULL;
|
||||
|
||||
if (nvgpu_allocator_init(g, &a, NULL, "buddy", base, size, blk_size,
|
||||
max_order, flags, BUDDY_ALLOCATOR) != 0) {
|
||||
unit_return_fail(m, "failed to init buddy_allocator\n");
|
||||
} else {
|
||||
a.ops->fini(&a);
|
||||
}
|
||||
|
||||
#ifdef CONFIG_NVGPU_DGPU
|
||||
if (nvgpu_allocator_init(g, &a, NULL, "page", base, size, blk_size,
|
||||
max_order, flags, PAGE_ALLOCATOR) != 0) {
|
||||
unit_return_fail(m, "failed to init page_allocator\n");
|
||||
} else {
|
||||
a.ops->fini(&a);
|
||||
}
|
||||
#endif
|
||||
|
||||
if (nvgpu_allocator_init(g, &a, NULL, "bitmap", base, size, blk_size,
|
||||
max_order, flags, BITMAP_ALLOCATOR) != 0) {
|
||||
unit_return_fail(m, "failed to init bitmap_allocator\n");
|
||||
} else {
|
||||
a.ops->fini(&a);
|
||||
}
|
||||
|
||||
/* Initialize invalid allocator */
|
||||
if (nvgpu_allocator_init(g, &a, NULL, "invalid", base, size, blk_size,
|
||||
max_order, flags, -1) != -EINVAL) {
|
||||
unit_return_fail(m, "initialized invalid allocator\n");
|
||||
}
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
struct unit_module_test nvgpu_allocator_tests[] = {
|
||||
UNIT_TEST(common_init, test_nvgpu_alloc_common_init, NULL, 0),
|
||||
UNIT_TEST(alloc_destroy, test_nvgpu_alloc_destroy, NULL, 0),
|
||||
UNIT_TEST(alloc_ops, test_nvgpu_alloc_ops_present, NULL, 0),
|
||||
UNIT_TEST(allocator_init, test_nvgpu_allocator_init, NULL, 0),
|
||||
};
|
||||
|
||||
UNIT_MODULE(nvgpu_allocator, nvgpu_allocator_tests, UNIT_PRIO_NVGPU_TEST);
|
||||
125
userspace/units/mm/allocators/nvgpu_allocator/nvgpu_allocator.h
Normal file
125
userspace/units/mm/allocators/nvgpu_allocator/nvgpu_allocator.h
Normal file
@@ -0,0 +1,125 @@
|
||||
/*
|
||||
* Copyright (c) 2020, NVIDIA CORPORATION. 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.
|
||||
*/
|
||||
|
||||
#ifndef UNIT_NVGPU_ALLOCATOR_H
|
||||
#define UNIT_NVGPU_ALLOCATOR_H
|
||||
|
||||
struct gk20a;
|
||||
struct unit_module;
|
||||
|
||||
/** @addtogroup SWUTS-mm-allocators-nvgpu-allocator
|
||||
* @{
|
||||
*
|
||||
* Software Unit Test Specification for mm.allocators.nvgpu_allocator
|
||||
*/
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_alloc_common_init
|
||||
*
|
||||
* Description: Test common_init() function
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_alloc_common_init
|
||||
*
|
||||
* Input: None
|
||||
*
|
||||
* Steps:
|
||||
* - Initialize nvgpu allocator with default ops values.
|
||||
* - Confirm that the parameters passed to the function make their way into
|
||||
* allocator struct.
|
||||
* - Initialize nvgpu allocator for various invalid input cases.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_alloc_common_init(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_alloc_destroy
|
||||
*
|
||||
* Description: Test allocator destroy function
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_alloc_common_init, nvgpu_alloc_destroy
|
||||
*
|
||||
* Input: None
|
||||
*
|
||||
* Steps:
|
||||
* - Trigger allocator destroy function which further invokes fini() op.
|
||||
* - Allocator struct should be completely zeroed after this function.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_alloc_destroy(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_alloc_ops_present
|
||||
*
|
||||
* Description: Test allocator destroy function
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_alloc, nvgpu_alloc_pte, nvgpu_alloc_fixed, nvgpu_free_fixed,
|
||||
* nvgpu_alloc_reserve_carveout, nvgpu_alloc_release_carveout,
|
||||
* nvgpu_alloc_base, nvgpu_alloc_length, nvgpu_alloc_end, nvgpu_free,
|
||||
* nvgpu_alloc_initialized, nvgpu_alloc_space
|
||||
*
|
||||
* Input: None
|
||||
*
|
||||
* Steps:
|
||||
* - Test the logic for calling present ops.
|
||||
* - Actual functionality of the ops should be verified by the respective
|
||||
* allocator unit tests.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_alloc_ops_present(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_allocator_init
|
||||
*
|
||||
* Description: Test allocator init function
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_allocator_init, nvgpu_alloc_destroy
|
||||
*
|
||||
* Input: None
|
||||
*
|
||||
* Steps:
|
||||
* - Initialize each allocator and check that the allocator is created
|
||||
* successfully.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_allocator_init(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
#endif /* UNIT_NVGPU_ALLOCATOR_H */
|
||||
26
userspace/units/mm/allocators/page_allocator/Makefile
Normal file
26
userspace/units/mm/allocators/page_allocator/Makefile
Normal file
@@ -0,0 +1,26 @@
|
||||
# Copyright (c) 2019, NVIDIA CORPORATION. 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.
|
||||
|
||||
.SUFFIXES:
|
||||
|
||||
OBJS = page_allocator.o
|
||||
MODULE = page_allocator
|
||||
|
||||
include ../../../Makefile.units
|
||||
@@ -0,0 +1,33 @@
|
||||
################################### tell Emacs this is a -*- makefile-gmake -*-
|
||||
#
|
||||
# Copyright (c) 2019, NVIDIA CORPORATION. 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.
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
NVGPU_UNIT_NAME=page_allocator
|
||||
|
||||
include $(NV_COMPONENT_DIR)/../../../Makefile.units.common.interface.tmk
|
||||
|
||||
# Local Variables:
|
||||
# indent-tabs-mode: t
|
||||
# tab-width: 8
|
||||
# End:
|
||||
# vi: set tabstop=8 noexpandtab:
|
||||
33
userspace/units/mm/allocators/page_allocator/Makefile.tmk
Normal file
33
userspace/units/mm/allocators/page_allocator/Makefile.tmk
Normal file
@@ -0,0 +1,33 @@
|
||||
################################### tell Emacs this is a -*- makefile-gmake -*-
|
||||
#
|
||||
# Copyright (c) 2019, NVIDIA CORPORATION. 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.
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
NVGPU_UNIT_NAME=page_allocator
|
||||
|
||||
include $(NV_COMPONENT_DIR)/../../../Makefile.units.common.tmk
|
||||
|
||||
# Local Variables:
|
||||
# indent-tabs-mode: t
|
||||
# tab-width: 8
|
||||
# End:
|
||||
# vi: set tabstop=8 noexpandtab:
|
||||
644
userspace/units/mm/allocators/page_allocator/page_allocator.c
Normal file
644
userspace/units/mm/allocators/page_allocator/page_allocator.c
Normal file
@@ -0,0 +1,644 @@
|
||||
/*
|
||||
* Copyright (c) 2019-2020, NVIDIA CORPORATION. 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.
|
||||
*/
|
||||
|
||||
#include <unit/io.h>
|
||||
#include <unit/unit.h>
|
||||
|
||||
#include <nvgpu/gk20a.h>
|
||||
#include <nvgpu/sizes.h>
|
||||
#include <nvgpu/types.h>
|
||||
#include <nvgpu/allocator.h>
|
||||
|
||||
#include <nvgpu/posix/kmem.h>
|
||||
#include <nvgpu/posix/posix-fault-injection.h>
|
||||
|
||||
#include <nvgpu/page_allocator.h>
|
||||
#include "page_allocator.h"
|
||||
|
||||
#ifdef CONFIG_NVGPU_DGPU
|
||||
|
||||
#define BA_DEFAULT_BASE SZ_4K
|
||||
#define BA_DEFAULT_LENGTH SZ_1M
|
||||
#define BA_DEFAULT_BLK_SIZE SZ_4K
|
||||
#define SZ_2K (SZ_1K << 1)
|
||||
#define SZ_8K (SZ_4K << 1)
|
||||
#define SZ_16K (SZ_4K << 2)
|
||||
#define SZ_32K (SZ_64K >> 1)
|
||||
|
||||
static struct nvgpu_allocator *na;
|
||||
|
||||
/*
|
||||
* @fault_enable- Enable/Disable fault injection
|
||||
* @fault_at - If fault is enabled,
|
||||
fault_at contains fault_counter value
|
||||
otherwise,
|
||||
fault_at should be set to 0
|
||||
* @base - Base address of allocation in case of fixed allocation
|
||||
* @len - Length of memory to be allocated
|
||||
* @flags - Additional flags to be enabled
|
||||
* @ret_addr - Return address of allocation, this is used in free()
|
||||
* @expected_zero - Expected result of test
|
||||
* @error_msg - Message to be displayed if test fails
|
||||
*/
|
||||
struct test_parameters {
|
||||
bool fault_enable;
|
||||
u32 fault_at;
|
||||
u64 base;
|
||||
u64 len;
|
||||
u64 flags;
|
||||
u64 ret_addr;
|
||||
bool expected_zero;
|
||||
char *error_msg;
|
||||
};
|
||||
|
||||
static struct test_parameters fault_at_alloc_cache = {
|
||||
.fault_enable = true,
|
||||
.fault_at = 0,
|
||||
.base = 0ULL,
|
||||
.len = SZ_32K,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = true,
|
||||
.error_msg = "alloced despite fault injection at alloc_cache",
|
||||
};
|
||||
|
||||
static struct test_parameters fault_at_nvgpu_alloc = {
|
||||
.fault_enable = true,
|
||||
.fault_at = 1,
|
||||
.base = 0ULL,
|
||||
.len = SZ_32K,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = true,
|
||||
.error_msg = "alloced despite fault injection at nvgpu_alloc",
|
||||
};
|
||||
|
||||
static struct test_parameters fault_at_sgl_alloc = {
|
||||
.fault_enable = true,
|
||||
.fault_at = 1,
|
||||
.base = 0ULL,
|
||||
.len = SZ_32K,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = true,
|
||||
.error_msg = "alloced despite fault injection at sgl alloc",
|
||||
};
|
||||
|
||||
static struct test_parameters fault_at_page_cache = {
|
||||
.fault_enable = true,
|
||||
.fault_at = 2,
|
||||
.base = 0ULL,
|
||||
.len = SZ_32K,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = true,
|
||||
.error_msg = "alloced despite fault injection at page_cache",
|
||||
};
|
||||
|
||||
static struct test_parameters first_simple_alloc_32K = {
|
||||
.fault_enable = false,
|
||||
.fault_at = 0,
|
||||
.base = 0ULL,
|
||||
.len = SZ_32K,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = false,
|
||||
.error_msg = "first instance of 32K alloc failed",
|
||||
};
|
||||
|
||||
static struct test_parameters second_simple_alloc_32K = {
|
||||
.fault_enable = false,
|
||||
.fault_at = 0,
|
||||
.base = 0ULL,
|
||||
.len = SZ_32K,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = false,
|
||||
.error_msg = "second instance of 32K alloc failed",
|
||||
};
|
||||
|
||||
static struct test_parameters third_simple_alloc_32K = {
|
||||
.fault_enable = false,
|
||||
.fault_at = 0,
|
||||
.base = 0ULL,
|
||||
.len = SZ_32K,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = false,
|
||||
.error_msg = "third instance of 32K alloc failed",
|
||||
};
|
||||
|
||||
static struct test_parameters fourth_simple_alloc_32K = {
|
||||
.fault_enable = false,
|
||||
.fault_at = 0,
|
||||
.base = 0ULL,
|
||||
.len = SZ_32K,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = false,
|
||||
.error_msg = "fourth instance of 32K alloc failed",
|
||||
};
|
||||
|
||||
static struct test_parameters failing_alloc_16K = {
|
||||
.fault_enable = false,
|
||||
.fault_at = 0,
|
||||
.base = 0ULL,
|
||||
.len = SZ_16K,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = true,
|
||||
.error_msg = "16K alloc is supposed to fail",
|
||||
};
|
||||
|
||||
static struct test_parameters simple_alloc_8K = {
|
||||
.fault_enable = false,
|
||||
.fault_at = 0,
|
||||
.base = 0ULL,
|
||||
.len = SZ_8K,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = false,
|
||||
.error_msg = "8K alloc failed",
|
||||
};
|
||||
|
||||
static struct test_parameters failing_alloc_8K = {
|
||||
.fault_enable = false,
|
||||
.fault_at = 0,
|
||||
.base = SZ_64K,
|
||||
.len = SZ_8K,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = true,
|
||||
.error_msg = "8K alloc supposed to fail",
|
||||
};
|
||||
|
||||
static struct test_parameters alloc_no_scatter_gather = {
|
||||
.fault_enable = false,
|
||||
.fault_at = 0,
|
||||
.base = SZ_64K,
|
||||
.len = SZ_32K,
|
||||
.flags = GPU_ALLOC_NO_SCATTER_GATHER,
|
||||
.expected_zero = false,
|
||||
.error_msg = "32K alloc failed with no_scatter_gather enabled",
|
||||
};
|
||||
|
||||
static struct test_parameters simple_alloc_128K = {
|
||||
.fault_enable = false,
|
||||
.fault_at = 0,
|
||||
.base = SZ_128K << 2,
|
||||
.len = SZ_128K,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = false,
|
||||
.error_msg = "128K alloc failed",
|
||||
};
|
||||
|
||||
static struct test_parameters alloc_contiguous = {
|
||||
.fault_enable = false,
|
||||
.fault_at = 0,
|
||||
.base = 0ULL,
|
||||
.len = SZ_128K << 2,
|
||||
.flags = GPU_ALLOC_FORCE_CONTIG,
|
||||
.expected_zero = true,
|
||||
.error_msg = "contiguous alloc should have failed",
|
||||
};
|
||||
|
||||
static struct test_parameters simple_alloc_512K = {
|
||||
.fault_enable = false,
|
||||
.fault_at = 0,
|
||||
.base = 0ULL,
|
||||
.len = SZ_128K << 2,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = false,
|
||||
.error_msg = "8K alloc failed",
|
||||
};
|
||||
|
||||
static struct test_parameters alloc_more_than_available = {
|
||||
.fault_enable = false,
|
||||
.fault_at = 0,
|
||||
.base = 0ULL,
|
||||
.len = SZ_1M,
|
||||
.flags = 0ULL,
|
||||
.expected_zero = true,
|
||||
.error_msg = "Allocated more than available memory",
|
||||
};
|
||||
|
||||
int test_page_alloc(struct unit_module *m, struct gk20a *g, void *args)
|
||||
{
|
||||
struct test_parameters *param = (struct test_parameters *) args;
|
||||
struct nvgpu_page_allocator *pa = page_allocator(na);
|
||||
struct nvgpu_posix_fault_inj *kmem_fi =
|
||||
nvgpu_kmem_get_fault_injection();
|
||||
|
||||
pa->flags |= param->flags;
|
||||
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi,
|
||||
param->fault_enable, param->fault_at);
|
||||
|
||||
param->ret_addr = na->ops->alloc(na, param->len);
|
||||
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, false, 0);
|
||||
pa->flags &= ~(param->flags);
|
||||
|
||||
if ((param->expected_zero && (param->ret_addr == 0)) ||
|
||||
(!param->expected_zero && (param->ret_addr != 0))) {
|
||||
return UNIT_SUCCESS;
|
||||
} else {
|
||||
unit_return_fail(m, "%s", param->error_msg);
|
||||
}
|
||||
}
|
||||
|
||||
int test_page_free(struct unit_module *m, struct gk20a *g, void *args)
|
||||
{
|
||||
struct test_parameters *param = (struct test_parameters *) args;
|
||||
struct nvgpu_page_allocator *pa = page_allocator(na);
|
||||
|
||||
pa->flags |= param->flags;
|
||||
na->ops->free_alloc(na, param->ret_addr);
|
||||
pa->flags &= ~(param->flags);
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
int test_page_alloc_fixed(struct unit_module *m, struct gk20a *g, void *args)
|
||||
{
|
||||
struct test_parameters *param = (struct test_parameters *) args;
|
||||
struct nvgpu_page_allocator *pa = page_allocator(na);
|
||||
struct nvgpu_posix_fault_inj *kmem_fi =
|
||||
nvgpu_kmem_get_fault_injection();
|
||||
|
||||
pa->flags |= param->flags;
|
||||
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi,
|
||||
param->fault_enable, param->fault_at);
|
||||
|
||||
/* page_size = SZ_4K ignored in the function */
|
||||
param->ret_addr = na->ops->alloc_fixed(na,
|
||||
param->base, param->len, SZ_4K);
|
||||
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, false, 0);
|
||||
pa->flags &= ~(param->flags);
|
||||
|
||||
if ((param->expected_zero && (param->ret_addr == 0)) ||
|
||||
(!param->expected_zero && (param->ret_addr != 0))) {
|
||||
return UNIT_SUCCESS;
|
||||
} else {
|
||||
unit_return_fail(m, "%s", param->error_msg);
|
||||
}
|
||||
}
|
||||
|
||||
int test_page_free_fixed(struct unit_module *m, struct gk20a *g, void *args)
|
||||
{
|
||||
struct test_parameters *param = (struct test_parameters *) args;
|
||||
struct nvgpu_page_allocator *pa = page_allocator(na);
|
||||
|
||||
pa->flags |= param->flags;
|
||||
na->ops->free_fixed(na, param->ret_addr, param->len);
|
||||
pa->flags &= ~(param->flags);
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
int test_page_allocator_init_slabs(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
u64 base = SZ_64K;
|
||||
u64 length = SZ_128K;
|
||||
u64 blk_size = SZ_64K;
|
||||
u64 flags = GPU_ALLOC_4K_VIDMEM_PAGES;
|
||||
struct nvgpu_posix_fault_inj *kmem_fi =
|
||||
nvgpu_kmem_get_fault_injection();
|
||||
|
||||
na = (struct nvgpu_allocator *)
|
||||
nvgpu_kzalloc(g, sizeof(struct nvgpu_allocator));
|
||||
if (na == NULL) {
|
||||
unit_return_fail(m, "Could not allocate nvgpu_allocator\n");
|
||||
}
|
||||
|
||||
/* Fault injection at init_slabs */
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, true, 3);
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_page", base, length,
|
||||
blk_size, 0ULL, flags, PAGE_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m,
|
||||
"pa with slabs inited despite fault injection\n");
|
||||
}
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, false, 0);
|
||||
|
||||
/*
|
||||
* Expect to fail as blk_size is odd
|
||||
*/
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_page", base, length,
|
||||
SZ_4K + 1ULL, 0ULL, flags, PAGE_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m,
|
||||
"vidmem page allocator inited with odd blk_size\n");
|
||||
}
|
||||
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_page", base, length,
|
||||
SZ_4K, 0ULL, flags, PAGE_ALLOCATOR) != 0) {
|
||||
unit_return_fail(m,
|
||||
"vidmem page allocator inited with odd blk_size\n");
|
||||
} else {
|
||||
na->ops->fini(na);
|
||||
}
|
||||
|
||||
/*
|
||||
* Initialize page allocator
|
||||
* This will be used for further tests.
|
||||
*/
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_page", base, length,
|
||||
blk_size, 0ULL, flags, PAGE_ALLOCATOR) != 0) {
|
||||
unit_return_fail(m, "init with slabs failed\n");
|
||||
}
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
int test_page_allocator_sgt_ops(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
u64 addr;
|
||||
void *sgl = NULL;
|
||||
struct nvgpu_page_alloc *alloc = NULL;
|
||||
|
||||
addr = na->ops->alloc(na, SZ_32K);
|
||||
if (addr == 0) {
|
||||
unit_return_fail(m, "couldn't allocate 32K");
|
||||
}
|
||||
|
||||
/* Test page allocator sgt ops */
|
||||
alloc = (struct nvgpu_page_alloc *) addr;
|
||||
sgl = alloc->sgt.sgl;
|
||||
|
||||
if (alloc->sgt.ops->sgl_next(sgl) != NULL) {
|
||||
unit_return_fail(m, "sgl_next should be NULL\n");
|
||||
}
|
||||
|
||||
if (alloc->sgt.ops->sgl_phys(g, sgl) != alloc->base) {
|
||||
unit_return_fail(m, "sgl_phys != base address\n");
|
||||
}
|
||||
|
||||
if (alloc->sgt.ops->sgl_ipa(g, sgl) != alloc->base) {
|
||||
unit_return_fail(m, "sgl_ipa != base address\n");
|
||||
}
|
||||
|
||||
if (alloc->sgt.ops->sgl_dma(sgl) != alloc->base) {
|
||||
unit_return_fail(m, "sgl_dma != base address\n");
|
||||
}
|
||||
|
||||
if (alloc->sgt.ops->sgl_gpu_addr(g, sgl, NULL) != alloc->base) {
|
||||
unit_return_fail(m, "sgl_gpu_addr != base address\n");
|
||||
}
|
||||
|
||||
if (alloc->sgt.ops->sgl_ipa_to_pa(g, sgl, SZ_4K, NULL) != SZ_4K) {
|
||||
unit_return_fail(m, "sgl_ipa_to_pa != SZ_4K\n");
|
||||
}
|
||||
|
||||
if (alloc->sgt.ops->sgl_length(sgl) != SZ_32K) {
|
||||
unit_return_fail(m, "sgl_length != SZ_32K\n");
|
||||
}
|
||||
|
||||
alloc->sgt.ops->sgt_free(g, &alloc->sgt);
|
||||
|
||||
na->ops->free_alloc(na, addr);
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
int test_nvgpu_page_allocator_ops(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
u64 addr;
|
||||
int err;
|
||||
struct nvgpu_alloc_carveout test_co =
|
||||
NVGPU_CARVEOUT("test_co", 0ULL, 0ULL);
|
||||
test_co.base = BA_DEFAULT_BASE;
|
||||
test_co.length = SZ_8K;
|
||||
|
||||
if (!na->ops->inited(na)) {
|
||||
unit_return_fail(m, "ops not inited\n");
|
||||
}
|
||||
|
||||
addr = na->ops->base(na);
|
||||
if (addr != BA_DEFAULT_BASE) {
|
||||
unit_return_fail(m, "base incorrect\n");
|
||||
}
|
||||
|
||||
addr = na->ops->length(na);
|
||||
if (addr != BA_DEFAULT_LENGTH) {
|
||||
unit_return_fail(m, "length incorrect\n");
|
||||
}
|
||||
|
||||
addr = na->ops->end(na);
|
||||
if (addr != (BA_DEFAULT_BASE + BA_DEFAULT_LENGTH)) {
|
||||
unit_return_fail(m, "end incorrect\n");
|
||||
}
|
||||
|
||||
addr = na->ops->space(na);
|
||||
if (addr == 0) {
|
||||
unit_return_fail(m, "zero space allocated\n");
|
||||
}
|
||||
|
||||
err = na->ops->reserve_carveout(na, &test_co);
|
||||
if (err < 0) {
|
||||
unit_return_fail(m, "couldn't reserve 8K carveout\n");
|
||||
}
|
||||
|
||||
na->ops->release_carveout(na, &test_co);
|
||||
|
||||
addr = na->ops->alloc(na, SZ_32K);
|
||||
if (addr == 0) {
|
||||
unit_return_fail(m, "couldn't allocate 32K");
|
||||
}
|
||||
|
||||
err = na->ops->reserve_carveout(na, &test_co);
|
||||
if (err == 0) {
|
||||
unit_return_fail(m, "reserved carveout after alloc\n");
|
||||
}
|
||||
|
||||
na->ops->free_alloc(na, addr);
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
int test_nvgpu_page_allocator_destroy(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
na->ops->fini(na);
|
||||
if (na->priv != NULL) {
|
||||
unit_return_fail(m, "page allocator destroy failed\n");
|
||||
}
|
||||
nvgpu_kfree(g, na);
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
|
||||
int test_nvgpu_page_allocator_init(struct unit_module *m,
|
||||
struct gk20a *g, void *args)
|
||||
{
|
||||
u64 base = BA_DEFAULT_BASE;
|
||||
u64 length = BA_DEFAULT_LENGTH;
|
||||
u64 blk_size = BA_DEFAULT_BLK_SIZE;
|
||||
u64 flags = 0ULL;
|
||||
struct nvgpu_posix_fault_inj *kmem_fi =
|
||||
nvgpu_kmem_get_fault_injection();
|
||||
|
||||
na = (struct nvgpu_allocator *)
|
||||
nvgpu_kzalloc(g, sizeof(struct nvgpu_allocator));
|
||||
if (na == NULL) {
|
||||
unit_return_fail(m, "Could not allocate nvgpu_allocator\n");
|
||||
}
|
||||
|
||||
/*
|
||||
* expect to fail as blk_size < SZ_4K
|
||||
*/
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_page", base, length,
|
||||
0ULL, 0ULL, flags, PAGE_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m, "inited despite blk_size = 0\n");
|
||||
}
|
||||
|
||||
/* Fault injection at nvgpu_page_allocator allocation */
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, true, 0);
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_page", base, length,
|
||||
blk_size, 0ULL, flags, PAGE_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m,
|
||||
"inited despite fault injection at page_allocator\n");
|
||||
}
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, false, 0);
|
||||
|
||||
/* Fault injection at alloc_cache */
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, true, 1);
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_page", base, length,
|
||||
blk_size, 0ULL, flags, PAGE_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m,
|
||||
"inited despite fault injection at alloc_cache\n");
|
||||
}
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, false, 0);
|
||||
|
||||
/* Fault injection at slab_page_cache */
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, true, 2);
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_page", base, length,
|
||||
blk_size, 0ULL, flags, PAGE_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m,
|
||||
"inited despite fault injection at slab_page_cache\n");
|
||||
}
|
||||
nvgpu_posix_enable_fault_injection(kmem_fi, false, 0);
|
||||
|
||||
/*
|
||||
* expect to fail as blk_size is odd
|
||||
*/
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_page", base, length,
|
||||
SZ_4K + 3ULL, 0ULL, flags, PAGE_ALLOCATOR) == 0) {
|
||||
unit_return_fail(m, "inited despite odd blk_size\n");
|
||||
}
|
||||
|
||||
/* base = 0 */
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_page", 0ULL, length,
|
||||
blk_size, 0ULL, flags, PAGE_ALLOCATOR) != 0) {
|
||||
unit_return_fail(m, "init failed with base = 0\n");
|
||||
} else {
|
||||
na->ops->fini(na);
|
||||
}
|
||||
|
||||
/*
|
||||
* Initialize page allocator
|
||||
* This will be used for further tests.
|
||||
*/
|
||||
if (nvgpu_allocator_init(g, na, NULL, "test_page", base, length,
|
||||
blk_size, 0ULL, flags, PAGE_ALLOCATOR) != 0) {
|
||||
unit_return_fail(m, "init failed\n");
|
||||
}
|
||||
|
||||
return UNIT_SUCCESS;
|
||||
}
|
||||
#endif
|
||||
|
||||
struct unit_module_test page_allocator_tests[] = {
|
||||
#ifdef CONFIG_NVGPU_DGPU
|
||||
/* These tests create and evaluate page_allocator w/o 4K VIDMEM pages */
|
||||
UNIT_TEST(init, test_nvgpu_page_allocator_init, NULL, 0),
|
||||
UNIT_TEST(ops, test_nvgpu_page_allocator_ops, NULL, 0),
|
||||
UNIT_TEST(sgt_ops, test_page_allocator_sgt_ops, NULL, 0),
|
||||
|
||||
/* Below tests examine page allocation */
|
||||
/*
|
||||
* NOTE: The test order should not be changed. Previous test develop
|
||||
* memory allocation arrangement required for later tests.
|
||||
*/
|
||||
|
||||
/* These tests check execution with fault injection at various locations */
|
||||
UNIT_TEST(fixed_alloc_fault_at_alloc_cache, test_page_alloc_fixed, (void *) &fault_at_alloc_cache, 0),
|
||||
UNIT_TEST(fixed_alloc_fault_at_sgl_alloc, test_page_alloc_fixed, (void *) &fault_at_sgl_alloc, 0),
|
||||
UNIT_TEST(alloc_fault_at_alloc_cache, test_page_alloc, (void *) &fault_at_alloc_cache, 0),
|
||||
UNIT_TEST(alloc_fault_at_nvgpu_alloc, test_page_alloc, (void *) &fault_at_nvgpu_alloc, 0),
|
||||
/* Alloc some memory, this ensures fault injection at sgl alloc in next test */
|
||||
UNIT_TEST(simple_32K_alloc, test_page_alloc, (void *) &first_simple_alloc_32K, 0),
|
||||
UNIT_TEST(alloc_fault_at_sgl_alloc, test_page_alloc, (void *) &fault_at_sgl_alloc, 0),
|
||||
|
||||
/* Test different allocation scenarios using simple alloc function */
|
||||
UNIT_TEST(alloc_no_scatter_gather, test_page_alloc, (void *) &alloc_no_scatter_gather, 0),
|
||||
UNIT_TEST(free_no_scatter_gather, test_page_free, (void *) &alloc_no_scatter_gather, 0),
|
||||
/* Second free call checks execution when address is NULL */
|
||||
UNIT_TEST(free_no_scatter_gather_again, test_page_free, (void *) &alloc_no_scatter_gather, 0),
|
||||
UNIT_TEST(free_32K_alloc, test_page_free, (void *) &first_simple_alloc_32K, 0),
|
||||
UNIT_TEST(fixed_alloc_128K, test_page_alloc_fixed, (void *) &simple_alloc_128K, 0),
|
||||
/* After previous allocations, contiguous 512K memory isn't available */
|
||||
UNIT_TEST(contiguous_alloc_512K, test_page_alloc, (void *) &alloc_contiguous, 0),
|
||||
UNIT_TEST(simple_alloc_512K, test_page_alloc, (void *) &simple_alloc_512K, 0),
|
||||
UNIT_TEST(alloc_more_than_available, test_page_alloc, (void *) &alloc_more_than_available, 0),
|
||||
UNIT_TEST(free_alloc_512K, test_page_free, (void *) &simple_alloc_512K, 0),
|
||||
|
||||
UNIT_TEST(alloc_fixed_no_scatter_gather, test_page_alloc_fixed, (void *) &alloc_no_scatter_gather, 0),
|
||||
UNIT_TEST(free_fixed_no_scatter_gather, test_page_free_fixed, (void *) &alloc_no_scatter_gather, 0),
|
||||
/* Second free call checks execution when address is NULL */
|
||||
UNIT_TEST(free_fixed_no_scatter_gather_again, test_page_free_fixed, (void *) &alloc_no_scatter_gather, 0),
|
||||
UNIT_TEST(free_fixed_128K, test_page_free_fixed, (void *) &simple_alloc_128K, 0),
|
||||
|
||||
UNIT_TEST(destroy, test_nvgpu_page_allocator_destroy, NULL, 0),
|
||||
|
||||
/* These tests create and evaluate page_allocator w/ 4K VIDMEM pages */
|
||||
UNIT_TEST(init_slabs, test_page_allocator_init_slabs, NULL, 0),
|
||||
|
||||
/* Below tests examine slab allocation */
|
||||
/*
|
||||
* NOTE: The test order should not be changed. A test contructs
|
||||
* required memory structure for later tests.
|
||||
*/
|
||||
|
||||
/* These tests check execution with fault injection at various locations */
|
||||
UNIT_TEST(slabs_fault_at_alloc_cache, test_page_alloc, (void *) &fault_at_alloc_cache, 0),
|
||||
UNIT_TEST(slabs_fault_at_sgl_alloc, test_page_alloc, (void *) &fault_at_sgl_alloc, 0),
|
||||
UNIT_TEST(slabs_fault_at_page_cache, test_page_alloc, (void *) &fault_at_page_cache, 0),
|
||||
|
||||
/* Test different allocation scenarios */
|
||||
UNIT_TEST(add_partial_slab, test_page_alloc, (void *) &first_simple_alloc_32K, 0),
|
||||
UNIT_TEST(add_full_slab, test_page_alloc, (void *) &second_simple_alloc_32K, 0),
|
||||
UNIT_TEST(add_second_partial_slab, test_page_alloc, (void *) &third_simple_alloc_32K, 0),
|
||||
UNIT_TEST(add_second_full_slab, test_page_alloc, (void *) &fourth_simple_alloc_32K, 0),
|
||||
/* Note: No free memory available for allocation */
|
||||
UNIT_TEST(fixed_alloc_8K, test_page_alloc_fixed, (void *) &failing_alloc_8K, 0),
|
||||
/* Freeing allocated slabs, adds slabs to empty and free lists */
|
||||
UNIT_TEST(revert_partial_slab, test_page_free, (void *) &fourth_simple_alloc_32K, 0),
|
||||
UNIT_TEST(revert_second_partial_slab, test_page_free, (void *) &second_simple_alloc_32K, 0),
|
||||
UNIT_TEST(add_empty_slab, test_page_free, (void *) &first_simple_alloc_32K, 0),
|
||||
UNIT_TEST(free_slab, test_page_free, (void *) &third_simple_alloc_32K, 0),
|
||||
|
||||
UNIT_TEST(slabs_alloc_8K, test_page_alloc, (void *) &simple_alloc_8K, 0),
|
||||
UNIT_TEST(slabs_alloc_32K, test_page_alloc, (void *) &first_simple_alloc_32K, 0),
|
||||
/*
|
||||
* Note: Page allocator has only 2 slabs.
|
||||
* These are now allocated for 8K and 32K chunks
|
||||
*/
|
||||
UNIT_TEST(no_more_slabs, test_page_alloc, (void *) &failing_alloc_16K, 0),
|
||||
|
||||
UNIT_TEST(destroy_slabs, test_nvgpu_page_allocator_destroy, NULL, 0),
|
||||
#endif
|
||||
};
|
||||
|
||||
UNIT_MODULE(page_allocator, page_allocator_tests, UNIT_PRIO_NVGPU_TEST);
|
||||
258
userspace/units/mm/allocators/page_allocator/page_allocator.h
Normal file
258
userspace/units/mm/allocators/page_allocator/page_allocator.h
Normal file
@@ -0,0 +1,258 @@
|
||||
/*
|
||||
* Copyright (c) 2020, NVIDIA CORPORATION. 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.
|
||||
*/
|
||||
|
||||
#ifndef UNIT_PAGE_ALLOCATOR_H
|
||||
#define UNIT_PAGE_ALLOCATOR_H
|
||||
|
||||
struct gk20a;
|
||||
struct unit_module;
|
||||
|
||||
/** @addtogroup SWUTS-mm-allocators-page-allocator
|
||||
* @{
|
||||
*
|
||||
* Software Unit Test Specification for mm.allocators.page_allocator
|
||||
*/
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_page_allocator_init
|
||||
*
|
||||
* Description: Initialize page allocator.
|
||||
*
|
||||
* Test Type: Feature, Error injection
|
||||
*
|
||||
* Targets: nvgpu_allocator_init, nvgpu_page_allocator_init,
|
||||
* nvgpu_allocator.ops.fini
|
||||
*
|
||||
* Input: None
|
||||
*
|
||||
* Steps:
|
||||
* - Initialize page allocator with following characteristics.
|
||||
* - 4K memory base address.
|
||||
* - 1M length of memory.
|
||||
* - 4K block size.
|
||||
* - Check that page allocator initializations fails for scenarios such as
|
||||
* odd value of block_size and fault injection for memory allocation.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_page_allocator_init(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_page_allocator_ops
|
||||
*
|
||||
* Description: Test page allocator ops
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_allocator.ops.alloc, nvgpu_allocator.ops.free_alloc,
|
||||
* nvgpu_allocator.ops.reserve_carveout,
|
||||
* nvgpu_allocator.ops.release_carveout, nvgpu_allocator.ops.base,
|
||||
* nvgpu_allocator.ops.end, nvgpu_allocator.ops.length,
|
||||
* nvgpu_allocator.ops.inited, nvgpu_allocator.ops.space
|
||||
*
|
||||
* Input: test_nvgpu_page_allocator_init
|
||||
*
|
||||
* Steps:
|
||||
* - Check page_allocator attributes using allocator ops.
|
||||
* - Execute allocator ops to read attibute value.
|
||||
* - Confirm that value is equal to the default values set during
|
||||
* initialization.
|
||||
* - Allocate carveout and confirm that allocation is successful. Check that
|
||||
* carveout cannot be reserved after normal page allocation.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_page_allocator_ops(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_page_allocator_sgt_ops
|
||||
*
|
||||
* Description: Test page alloc sgt ops
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_page_alloc.nvgpu_sgt.nvgpu_sgt_ops.sgl_next,
|
||||
* nvgpu_page_alloc.nvgpu_sgt.nvgpu_sgt_ops.sgl_phys,
|
||||
* nvgpu_page_alloc.nvgpu_sgt.nvgpu_sgt_ops.sgl_ipa,
|
||||
* nvgpu_page_alloc.nvgpu_sgt.nvgpu_sgt_ops.sgl_ipa_to_pa,
|
||||
* nvgpu_page_alloc.nvgpu_sgt.nvgpu_sgt_ops.sgl_dma,
|
||||
* nvgpu_page_alloc.nvgpu_sgt.nvgpu_sgt_ops.sgl_length,
|
||||
* nvgpu_page_alloc.nvgpu_sgt.nvgpu_sgt_ops.sgl_gpu_addr,
|
||||
* nvgpu_page_alloc.nvgpu_sgt.nvgpu_sgt_ops.sgt_free
|
||||
*
|
||||
* Input: test_nvgpu_page_allocator_init
|
||||
*
|
||||
* Steps:
|
||||
* - Check allocated page attributes using sgt ops
|
||||
* - Confirm that allocation details are equal to values set during allocation.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_page_allocator_sgt_ops(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_page_alloc_fixed
|
||||
*
|
||||
* Description: Allocate memory at fixed address
|
||||
*
|
||||
* Test Type: Feature, Error injection
|
||||
*
|
||||
* Targets: nvgpu_allocator.ops.alloc_fixed
|
||||
*
|
||||
* Input: test_nvgpu_page_allocator_init or test_page_allocator_init_slabs,
|
||||
* args (fault_at_alloc_cache, fault_at_sgl_alloc, simple_alloc_128K,
|
||||
* alloc_no_scatter_gather, failing_alloc_8K)
|
||||
*
|
||||
* Steps:
|
||||
* - Allocate chunk of memory at fixed address as per test_parameters input.
|
||||
* - Check that result is equal to test_parameters expected output.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_page_alloc_fixed(struct unit_module *m, struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_page_alloc
|
||||
*
|
||||
* Description: Allocate memory using page allocator
|
||||
*
|
||||
* Test Type: Feature, Error injection
|
||||
*
|
||||
* Targets: nvgpu_allocator.ops.alloc
|
||||
*
|
||||
* Input: test_nvgpu_page_allocator_init or test_page_allocator_init_slabs,
|
||||
* args (fault_at_alloc_cache, fault_at_nvgpu_alloc,
|
||||
* first_simple_alloc_32K, fault_at_sgl_alloc, alloc_no_scatter_gather,
|
||||
* alloc_contiguous, simple_alloc_512K, alloc_more_than_available,
|
||||
* fault_at_page_cache, second_simple_alloc_32K, third_simple_alloc_32K,
|
||||
* fourth_simple_alloc_32K, simple_alloc_8K, failing_alloc_16K)
|
||||
*
|
||||
* Steps:
|
||||
* - Allocate chunk of memory at any address as per test_parameters input.
|
||||
* - Check that result is equal to test_parameters expected output.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_page_alloc(struct unit_module *m, struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_page_free
|
||||
*
|
||||
* Description: Free allocated memory
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_allocator.ops.free_alloc
|
||||
*
|
||||
* Input: test_nvgpu_page_allocator_init or test_page_allocator_init_slabs,
|
||||
* args (alloc_no_scatter_gather, first_simple_alloc_32K,
|
||||
* simple_alloc_512K, fourth_simple_alloc_32K, second_simple_alloc_32K,
|
||||
* first_simple_alloc_32K, third_simple_alloc_32K)
|
||||
*
|
||||
* Steps:
|
||||
* - Free allocated memory at given address as per test_parameters input.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_page_free(struct unit_module *m, struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_page_free_fixed
|
||||
*
|
||||
* Description: Free allocated page at given address
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_allocator.ops.free_fixed
|
||||
*
|
||||
* Input: test_nvgpu_page_allocator_init, args (alloc_no_scatter_gather,
|
||||
* simple_alloc_128K)
|
||||
*
|
||||
* Steps:
|
||||
* - Free allocated memory at fixed address as per test_parameters input.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_page_free_fixed(struct unit_module *m, struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_page_allocator_init_slabs
|
||||
*
|
||||
* Description: Initialize page allocator with slabs.
|
||||
*
|
||||
* Test Type: Feature, Error injection
|
||||
*
|
||||
* Targets: nvgpu_allocator_init, nvgpu_page_allocator_init,
|
||||
* nvgpu_page_alloc_init_slabs, nvgpu_allocator.ops.fini
|
||||
*
|
||||
* Input: None
|
||||
*
|
||||
* Steps:
|
||||
* - Initialize page allocator with following characteristics.
|
||||
* - 64K memory base address.
|
||||
* - 128K length of memory.
|
||||
* - 64K block size.
|
||||
* - Flags set to GPU_ALLOC_4K_VIDMEM_PAGES to enable slabs.
|
||||
* - Check that page allocator initializations fails for scenarios such as
|
||||
* odd value of block_size and fault injection for memory allocation.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_page_allocator_init_slabs(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* Test specification for: test_nvgpu_page_allocator_destroy
|
||||
*
|
||||
* Description: Destroy page allocator structure
|
||||
*
|
||||
* Test Type: Feature
|
||||
*
|
||||
* Targets: nvgpu_allocator.ops.fini
|
||||
*
|
||||
* Input: test_nvgpu_page_allocator_init or test_page_allocator_init_slabs
|
||||
*
|
||||
* Steps:
|
||||
* - De-initialize page allocator structure.
|
||||
*
|
||||
* Output: Returns SUCCESS if the steps above were executed successfully. FAIL
|
||||
* otherwise.
|
||||
*/
|
||||
int test_nvgpu_page_allocator_destroy(struct unit_module *m,
|
||||
struct gk20a *g, void *args);
|
||||
|
||||
/**
|
||||
* @}
|
||||
*/
|
||||
|
||||
#endif /* UNIT_PAGE_ALLOCATOR_H */
|
||||
Reference in New Issue
Block a user