533eb415df
It's supposed that SOC will check if "-m" provided RAM size is valid by setting "ram-size" property and then board would read back valid (possibly corrected value) to map RAM MemoryReging with valid size. It isn't doing so, since check is called only indirectly from aspeed_sdmc_reset()->asc->compute_conf() or much later when guest writes to configuration register. So depending on "-m" value QEMU end-ups with a warning and an invalid MemoryRegion size allocated and mapped. (examples: -M ast2500-evb -m 1M 0000000080000000-000000017ffffffe (prio 0, i/o): aspeed-ram-container 0000000080000000-00000000800fffff (prio 0, ram): ram 0000000080100000-00000000bfffffff (prio 0, i/o): max_ram -M ast2500-evb -m 3G 0000000080000000-000000017ffffffe (prio 0, i/o): aspeed-ram-container 0000000080000000-000000013fffffff (prio 0, ram): ram [DETECTED OVERFLOW!] 0000000140000000-00000000bfffffff (prio 0, i/o): max_ram ) On top of that sdmc falls back and reports to guest "default" size, it thinks machine should have. This patch makes ram-size check actually work and changes behavior from a warning later on during machine reset to error_fatal at the moment SOC.ram-size is set so user will have to fix RAM size on CLI to start machine. It also gets out of the way mutable ram-size logic, so we could consolidate RAM allocation logic around pre-allocated hostmem backend (supplied by user or auto created by generic machine code depending on supplied -m/mem-path/mem-prealloc options. Signed-off-by: Igor Mammedov <imammedo@redhat.com> Reviewed-by: Cédric Le Goater <clg@kaod.org> Reviewed-by: Richard Henderson <richard.henderson@linaro.org> Message-Id: <20200219160953.13771-10-imammedo@redhat.com>
49 lines
1.3 KiB
C
49 lines
1.3 KiB
C
/*
|
|
* ASPEED SDRAM Memory Controller
|
|
*
|
|
* Copyright (C) 2016 IBM Corp.
|
|
*
|
|
* This code is licensed under the GPL version 2 or later. See the
|
|
* COPYING file in the top-level directory.
|
|
*/
|
|
#ifndef ASPEED_SDMC_H
|
|
#define ASPEED_SDMC_H
|
|
|
|
#include "hw/sysbus.h"
|
|
|
|
#define TYPE_ASPEED_SDMC "aspeed.sdmc"
|
|
#define ASPEED_SDMC(obj) OBJECT_CHECK(AspeedSDMCState, (obj), TYPE_ASPEED_SDMC)
|
|
#define TYPE_ASPEED_2400_SDMC TYPE_ASPEED_SDMC "-ast2400"
|
|
#define TYPE_ASPEED_2500_SDMC TYPE_ASPEED_SDMC "-ast2500"
|
|
#define TYPE_ASPEED_2600_SDMC TYPE_ASPEED_SDMC "-ast2600"
|
|
|
|
#define ASPEED_SDMC_NR_REGS (0x174 >> 2)
|
|
|
|
typedef struct AspeedSDMCState {
|
|
/*< private >*/
|
|
SysBusDevice parent_obj;
|
|
|
|
/*< public >*/
|
|
MemoryRegion iomem;
|
|
|
|
uint32_t regs[ASPEED_SDMC_NR_REGS];
|
|
uint64_t ram_size;
|
|
uint64_t max_ram_size;
|
|
} AspeedSDMCState;
|
|
|
|
#define ASPEED_SDMC_CLASS(klass) \
|
|
OBJECT_CLASS_CHECK(AspeedSDMCClass, (klass), TYPE_ASPEED_SDMC)
|
|
#define ASPEED_SDMC_GET_CLASS(obj) \
|
|
OBJECT_GET_CLASS(AspeedSDMCClass, (obj), TYPE_ASPEED_SDMC)
|
|
|
|
typedef struct AspeedSDMCClass {
|
|
SysBusDeviceClass parent_class;
|
|
|
|
uint64_t max_ram_size;
|
|
const uint64_t *valid_ram_sizes;
|
|
uint32_t (*compute_conf)(AspeedSDMCState *s, uint32_t data);
|
|
void (*write)(AspeedSDMCState *s, uint32_t reg, uint32_t data);
|
|
} AspeedSDMCClass;
|
|
|
|
#endif /* ASPEED_SDMC_H */
|