blob: c1b54c87a709a9e74bc8d05ed9d47577ae4c8ae6 [file] [log] [blame]
nabkah01002e5692022-10-10 12:36:46 +01001/*
2 * Copyright (c) 2022, Arm Limited. All rights reserved.
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 *
6 */
7
8#include <stdbool.h>
9#include <stdint.h>
10
11#include <debug.h>
12#include <heap/page_alloc.h>
13#include <spinlock.h>
14#include <utils_def.h>
15
16#include <platform_def.h>
17
18static uint64_t memory_used;
19static uint64_t heap_base_addr;
20static u_register_t heap_addr;
21static uint64_t heap_size;
22static bool heap_initialised = HEAP_INIT_FAILED;
23static spinlock_t mem_lock;
24
25/*
26 * Initialize the memory heap space to be used
27 * @heap_base: heap base address
28 * @heap_len: heap size for use
29 */
30int page_pool_init(uint64_t heap_base, uint64_t heap_len)
31{
32 const uint64_t plat_max_addr = (uint64_t)DRAM_BASE + (uint64_t)DRAM_SIZE;
33 uint64_t max_addr = heap_base + heap_len;
34
35 if (heap_len == 0ULL) {
36 ERROR("heap_len must be non-zero value\n");
37 heap_initialised = HEAP_INVALID_LEN;
38 } else if (max_addr >= plat_max_addr) {
39 ERROR("heap_base + heap[0x%llx] must not exceed platform"
40 "max address[0x%llx]\n", max_addr, plat_max_addr);
41
42 heap_initialised = HEAP_OUT_OF_RANGE;
43 } else {
44 heap_base_addr = heap_base;
45 memory_used = heap_base;
46 heap_size = heap_len;
47 heap_initialised = HEAP_INIT_SUCCESS;
48 }
49 return heap_initialised;
50}
51
52/*
53 * Return the pointer to the allocated pages
54 * @bytes_size: pages to allocate in byte unit
55 */
56void *page_alloc(u_register_t bytes_size)
57{
58 if (heap_initialised != HEAP_INIT_SUCCESS) {
59 ERROR("heap need to be initialised first\n");
60 return HEAP_NULL_PTR;
61 }
62 if (bytes_size == 0UL) {
63 ERROR("bytes_size must be non-zero value\n");
64 return HEAP_NULL_PTR;
65 }
66
67 spin_lock(&mem_lock);
68
69 if ((memory_used + bytes_size) >= (heap_base_addr + heap_size)) {
70 ERROR("Reached to max KB allowed[%llu]\n", (heap_size/1024U));
71 goto unlock_failed;
72 }
73 /* set pointer to current used heap memory cursor */
74 heap_addr = memory_used;
75 /* move used memory cursor by bytes_size */
76 memory_used += bytes_size;
77 spin_unlock(&mem_lock);
78
79 return (void *)heap_addr;
80
81unlock_failed:/* failed allocation */
82 spin_unlock(&mem_lock);
83 return HEAP_NULL_PTR;
84}
85
86/*
87 * Reset heap memory usage cursor to heap base address
88 */
89void page_pool_reset(void)
90{
91 /*
92 * No race condition here, only lead cpu running TFTF test case can
93 * reset the memory allocation
94 */
95 memory_used = heap_base_addr;
96}
97
98void page_free(u_register_t address)
99{
100 /* No memory free is needed in current TFTF test scenarios */
101}