[PATCH qemu 25/38] aspeed/sdmc: rework the locking register of the memory controller
Andrew Jeffery
andrew at aj.id.au
Mon Nov 28 12:55:55 AEDT 2016
On Fri, 2016-11-18 at 15:22 +0100, Cédric Le Goater wrote:
> The lock register is unlocked with a write of a special value and
> locked with a write of any other value. When unlocked, reads return
> one and when locked a zero.
>
> > Signed-off-by: Cédric Le Goater <clg at kaod.org>
> ---
> hw/misc/aspeed_sdmc.c | 28 +++++++++++++++++++---------
> include/hw/misc/aspeed_sdmc.h | 1 +
> 2 files changed, 20 insertions(+), 9 deletions(-)
>
> diff --git a/hw/misc/aspeed_sdmc.c b/hw/misc/aspeed_sdmc.c
> index 5f3ac0b6f608..867caa2d64dc 100644
> --- a/hw/misc/aspeed_sdmc.c
> +++ b/hw/misc/aspeed_sdmc.c
> @@ -83,17 +83,22 @@
> static uint64_t aspeed_sdmc_read(void *opaque, hwaddr addr, unsigned size)
> {
> AspeedSDMCState *s = ASPEED_SDMC(opaque);
> + uint64_t val = 0;
>
> addr >>= 2;
>
> - if (addr >= ARRAY_SIZE(s->regs)) {
> + switch (addr) {
> + case R_PROT:
> + val = s->unlocked;
> + break;
> + default:
> qemu_log_mask(LOG_GUEST_ERROR,
> "%s: Out-of-bounds read at offset 0x%" HWADDR_PRIx "\n",
> __func__, addr);
> - return 0;
> + break;
> }
>
> - return s->regs[addr];
> + return val;
This suggests we only care about R_PROT - the change returns 0 for the
value of other registers. That doesn't seem right.
Andrew
> }
>
> static void aspeed_sdmc_write(void *opaque, hwaddr addr, uint64_t data,
> @@ -103,19 +108,18 @@ static void aspeed_sdmc_write(void *opaque, hwaddr addr, uint64_t data,
>
> addr >>= 2;
>
> - if (addr >= ARRAY_SIZE(s->regs)) {
> - qemu_log_mask(LOG_GUEST_ERROR,
> - "%s: Out-of-bounds write at offset 0x%" HWADDR_PRIx "\n",
> - __func__, addr);
> + if (addr == R_PROT) {
> + s->unlocked = (data == PROT_KEY_UNLOCK);
> return;
> }
>
> - if (addr != R_PROT && s->regs[R_PROT] != PROT_KEY_UNLOCK) {
> + if (!s->unlocked) { /* TODO protect : MCR04 ∼ MCR7C */
> qemu_log_mask(LOG_GUEST_ERROR, "%s: SDMC is locked!\n", __func__);
> return;
> }
>
> - if (addr == R_CONF) {
> + switch (addr) {
> + case R_CONF:
> /* Make sure readonly bits are kept */
> switch (s->silicon_rev) {
> case AST2400_A0_SILICON_REV:
> @@ -128,6 +132,12 @@ static void aspeed_sdmc_write(void *opaque, hwaddr addr, uint64_t data,
> default:
> g_assert_not_reached();
> }
> + break;
> + default:
> + qemu_log_mask(LOG_GUEST_ERROR,
> + "%s: Out-of-bounds write at offset 0x%" HWADDR_PRIx "\n",
> + __func__, addr << 2);
> + return;
> }
>
> s->regs[addr] = data;
> diff --git a/include/hw/misc/aspeed_sdmc.h b/include/hw/misc/aspeed_sdmc.h
> index 551c8afdf4be..a4415d9efc2f 100644
> --- a/include/hw/misc/aspeed_sdmc.h
> +++ b/include/hw/misc/aspeed_sdmc.h
> @@ -28,6 +28,7 @@ typedef struct AspeedSDMCState {
> uint32_t ram_bits;
> uint64_t ram_size;
>
> + bool unlocked;
> } AspeedSDMCState;
>
> #endif /* ASPEED_SDMC_H */
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 801 bytes
Desc: This is a digitally signed message part
URL: <http://lists.ozlabs.org/pipermail/openbmc/attachments/20161128/32be6c9f/attachment.sig>
More information about the openbmc
mailing list