mirror of
https://github.com/ARM-software/arm-trusted-firmware.git
synced 2025-04-16 09:34:18 +00:00
Merge "feat(qemu-sbsa): handle memory information" into integration
This commit is contained in:
commit
fc26a0fcac
2 changed files with 103 additions and 0 deletions
|
@ -61,6 +61,11 @@
|
|||
#define CACHE_WRITEBACK_SHIFT 6
|
||||
#define CACHE_WRITEBACK_GRANULE (1 << CACHE_WRITEBACK_SHIFT)
|
||||
|
||||
/*
|
||||
* Define the max number of memory nodes.
|
||||
*/
|
||||
#define PLAT_MAX_MEM_NODES 128
|
||||
|
||||
/*
|
||||
* Partition memory into secure ROM, non-secure DRAM, secure "SRAM",
|
||||
* and secure DRAM.
|
||||
|
|
|
@ -30,6 +30,8 @@ static int platform_version_minor;
|
|||
#define SIP_SVC_GET_GIC_ITS SIP_FUNCTION_ID(101)
|
||||
#define SIP_SVC_GET_CPU_COUNT SIP_FUNCTION_ID(200)
|
||||
#define SIP_SVC_GET_CPU_NODE SIP_FUNCTION_ID(201)
|
||||
#define SIP_SVC_GET_MEMORY_NODE_COUNT SIP_FUNCTION_ID(300)
|
||||
#define SIP_SVC_GET_MEMORY_NODE SIP_FUNCTION_ID(301)
|
||||
|
||||
static uint64_t gic_its_addr;
|
||||
|
||||
|
@ -38,9 +40,17 @@ typedef struct {
|
|||
uint32_t mpidr;
|
||||
} cpu_data;
|
||||
|
||||
typedef struct{
|
||||
uint32_t nodeid;
|
||||
uint64_t addr_base;
|
||||
uint64_t addr_size;
|
||||
} memory_data;
|
||||
|
||||
static struct {
|
||||
uint32_t num_cpus;
|
||||
uint32_t num_memnodes;
|
||||
cpu_data cpu[PLATFORM_CORE_COUNT];
|
||||
memory_data memory[PLAT_MAX_MEM_NODES];
|
||||
} dynamic_platform_info;
|
||||
|
||||
void sbsa_set_gic_bases(const uintptr_t gicd_base, const uintptr_t gicr_base);
|
||||
|
@ -127,6 +137,79 @@ void read_cpuinfo_from_dt(void *dtb)
|
|||
INFO("Found %d cpus\n", dynamic_platform_info.num_cpus);
|
||||
}
|
||||
|
||||
void read_meminfo_from_dt(void *dtb)
|
||||
{
|
||||
const fdt32_t *prop;
|
||||
const char *type;
|
||||
int prev, node;
|
||||
int len;
|
||||
uint32_t nodeid = 0;
|
||||
uint32_t memnode = 0;
|
||||
uint32_t higher_value, lower_value;
|
||||
uint64_t cur_base, cur_size;
|
||||
|
||||
/*
|
||||
* QEMU gives us this DeviceTree node:
|
||||
*
|
||||
* memory@100c0000000 {
|
||||
* numa-node-id = <0x01>;
|
||||
* reg = <0x100 0xc0000000 0x00 0x40000000>;
|
||||
* device_type = "memory";
|
||||
* };
|
||||
*
|
||||
* memory@10000000000 {
|
||||
* numa-node-id = <0x00>;
|
||||
* reg = <0x100 0x00 0x00 0xc0000000>;
|
||||
* device_type = "memory";
|
||||
* }
|
||||
*/
|
||||
|
||||
for (prev = 0;; prev = node) {
|
||||
node = fdt_next_node(dtb, prev, NULL);
|
||||
if (node < 0) {
|
||||
break;
|
||||
}
|
||||
|
||||
type = fdt_getprop(dtb, node, "device_type", &len);
|
||||
if (type && strncmp(type, "memory", len) == 0) {
|
||||
if (fdt_getprop(dtb, node, "numa-node-id", NULL)) {
|
||||
fdt_read_uint32(dtb, node, "numa-node-id", &nodeid);
|
||||
}
|
||||
|
||||
dynamic_platform_info.memory[memnode].nodeid = nodeid;
|
||||
|
||||
/*
|
||||
* Get the 'reg' property of this node and
|
||||
* assume two 8 bytes for base and size.
|
||||
*/
|
||||
prop = fdt_getprop(dtb, node, "reg", &len);
|
||||
if (prop != 0 && len == (2 * sizeof(int64_t))) {
|
||||
higher_value = fdt32_to_cpu(*prop);
|
||||
lower_value = fdt32_to_cpu(*(prop + 1));
|
||||
cur_base = (uint64_t)(lower_value | ((uint64_t)higher_value) << 32);
|
||||
|
||||
higher_value = fdt32_to_cpu(*(prop + 2));
|
||||
lower_value = fdt32_to_cpu(*(prop + 3));
|
||||
cur_size = (uint64_t)(lower_value | ((uint64_t)higher_value) << 32);
|
||||
|
||||
dynamic_platform_info.memory[memnode].addr_base = cur_base;
|
||||
dynamic_platform_info.memory[memnode].addr_size = cur_size;
|
||||
|
||||
INFO("RAM %d: node-id: %d, address: 0x%lx - 0x%lx\n",
|
||||
memnode,
|
||||
dynamic_platform_info.memory[memnode].nodeid,
|
||||
dynamic_platform_info.memory[memnode].addr_base,
|
||||
dynamic_platform_info.memory[memnode].addr_base +
|
||||
dynamic_platform_info.memory[memnode].addr_size - 1);
|
||||
}
|
||||
|
||||
memnode++;
|
||||
}
|
||||
}
|
||||
|
||||
dynamic_platform_info.num_memnodes = memnode;
|
||||
}
|
||||
|
||||
void read_platform_config_from_dt(void *dtb)
|
||||
{
|
||||
int node;
|
||||
|
@ -222,6 +305,7 @@ void sip_svc_init(void)
|
|||
|
||||
read_platform_config_from_dt(dtb);
|
||||
read_cpuinfo_from_dt(dtb);
|
||||
read_meminfo_from_dt(dtb);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -270,6 +354,20 @@ uintptr_t sbsa_sip_smc_handler(uint32_t smc_fid,
|
|||
SMC_RET1(handle, SMC_ARCH_CALL_INVAL_PARAM);
|
||||
}
|
||||
|
||||
case SIP_SVC_GET_MEMORY_NODE_COUNT:
|
||||
SMC_RET2(handle, NULL, dynamic_platform_info.num_memnodes);
|
||||
|
||||
case SIP_SVC_GET_MEMORY_NODE:
|
||||
index = x1;
|
||||
if (index < PLAT_MAX_MEM_NODES) {
|
||||
SMC_RET4(handle, NULL,
|
||||
dynamic_platform_info.memory[index].nodeid,
|
||||
dynamic_platform_info.memory[index].addr_base,
|
||||
dynamic_platform_info.memory[index].addr_size);
|
||||
} else {
|
||||
SMC_RET1(handle, SMC_ARCH_CALL_INVAL_PARAM);
|
||||
}
|
||||
|
||||
default:
|
||||
ERROR("%s: unhandled SMC (0x%x) (function id: %d)\n", __func__, smc_fid,
|
||||
smc_fid - SIP_FUNCTION);
|
||||
|
|
Loading…
Add table
Reference in a new issue