From patchwork Sun Aug 28 16:56:56 2011 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 3741 Return-Path: X-Original-To: patchwork@peony.canonical.com Delivered-To: patchwork@peony.canonical.com Received: from fiordland.canonical.com (fiordland.canonical.com [91.189.94.145]) by peony.canonical.com (Postfix) with ESMTP id 5DF5023FB0 for ; Sun, 28 Aug 2011 16:57:21 +0000 (UTC) Received: from mail-fx0-f52.google.com (mail-fx0-f52.google.com [209.85.161.52]) by fiordland.canonical.com (Postfix) with ESMTP id 4BCD1A18191 for ; Sun, 28 Aug 2011 16:57:21 +0000 (UTC) Received: by mail-fx0-f52.google.com with SMTP id 18so5671092fxd.11 for ; Sun, 28 Aug 2011 09:57:21 -0700 (PDT) Received: by 10.223.76.137 with SMTP id c9mr3263619fak.62.1314550641133; Sun, 28 Aug 2011 09:57:21 -0700 (PDT) X-Forwarded-To: linaro-patchwork@canonical.com X-Forwarded-For: patch@linaro.org linaro-patchwork@canonical.com Delivered-To: patches@linaro.org Received: by 10.152.11.8 with SMTP id m8cs69786lab; Sun, 28 Aug 2011 09:57:20 -0700 (PDT) Received: by 10.227.55.137 with SMTP id u9mr2901840wbg.43.1314550640603; Sun, 28 Aug 2011 09:57:20 -0700 (PDT) Received: from mnementh.archaic.org.uk (mnementh.archaic.org.uk [81.2.115.146]) by mx.google.com with ESMTPS id ft20si8962861wbb.93.2011.08.28.09.57.20 (version=TLSv1/SSLv3 cipher=OTHER); Sun, 28 Aug 2011 09:57:20 -0700 (PDT) Received-SPF: pass (google.com: best guess record for domain of pm215@archaic.org.uk designates 81.2.115.146 as permitted sender) client-ip=81.2.115.146; Authentication-Results: mx.google.com; spf=pass (google.com: best guess record for domain of pm215@archaic.org.uk designates 81.2.115.146 as permitted sender) smtp.mail=pm215@archaic.org.uk Received: from pm215 by mnementh.archaic.org.uk with local (Exim 4.72) (envelope-from ) id 1QxifU-000702-N2; Sun, 28 Aug 2011 17:57:08 +0100 From: Peter Maydell To: qemu-devel@nongnu.org Cc: Andrzej Zaborowski , "Edgar E. Iglesias" , patches@linaro.org Subject: [PATCH v2 06/18] omap_gpmc: Refactor omap_gpmc_cs_map and omap_gpmc_cs_unmap Date: Sun, 28 Aug 2011 17:56:56 +0100 Message-Id: <1314550628-26869-8-git-send-email-peter.maydell@linaro.org> X-Mailer: git-send-email 1.7.2.5 In-Reply-To: <1314550628-26869-1-git-send-email-peter.maydell@linaro.org> References: <1314550628-26869-1-git-send-email-peter.maydell@linaro.org> Refactor the omap_gpmc_cs_map/unmap functions: * take the omap_gpmc_s* and a chipselect id rather than the omap_gpmc_cs_file_s*, so they have access to the general gpmc member fields * extract the base and mask from the config registers in the functions rather than at every callsite * check for CSVALID in the functions rather than at every callsite Signed-off-by: Peter Maydell --- hw/omap_gpmc.c | 56 +++++++++++++++++++++++++++++++++++--------------------- 1 files changed, 35 insertions(+), 21 deletions(-) diff --git a/hw/omap_gpmc.c b/hw/omap_gpmc.c index 19f246c..d16b28b 100644 --- a/hw/omap_gpmc.c +++ b/hw/omap_gpmc.c @@ -54,18 +54,25 @@ static void omap_gpmc_int_update(struct omap_gpmc_s *s) qemu_set_irq(s->irq, s->irqen & s->irqst); } -static void omap_gpmc_cs_map(struct omap_gpmc_cs_file_s *f, int base, int mask) +static void omap_gpmc_cs_map(struct omap_gpmc_s *s, int cs) { + struct omap_gpmc_cs_file_s *f = &s->cs_file[cs]; + uint32_t mask = (f->config[6] >> 8) & 0xf; + uint32_t base = f->config[6] & 0x3f; uint32_t size; if (!f->iomem) { return; } + if (!(f->config[6] & (1 << 6))) { + /* Do nothing unless CSVALID */ + return; + } + /* TODO: check for overlapping regions and report access errors */ if ((mask != 0x8 && mask != 0xc && mask != 0xe && mask != 0xf) || - (base < 0 || base >= 0x40) || - (base & 0x0f & ~mask)) { + (base & 0x0f & ~mask)) { fprintf(stderr, "%s: wrong cs address mapping/decoding!\n", __FUNCTION__); return; @@ -83,8 +90,13 @@ static void omap_gpmc_cs_map(struct omap_gpmc_cs_file_s *f, int base, int mask) &f->container); } -static void omap_gpmc_cs_unmap(struct omap_gpmc_cs_file_s *f) +static void omap_gpmc_cs_unmap(struct omap_gpmc_s *s, int cs) { + struct omap_gpmc_cs_file_s *f = &s->cs_file[cs]; + if (!(f->config[6] & (1 << 6))) { + /* Do nothing unless CSVALID */ + return; + } if (!f->iomem) { return; } @@ -110,19 +122,26 @@ void omap_gpmc_reset(struct omap_gpmc_s *s) s->preffifo = 0; s->prefcount = 0; for (i = 0; i < 8; i ++) { - if (s->cs_file[i].config[6] & (1 << 6)) /* CSVALID */ - omap_gpmc_cs_unmap(s->cs_file + i); - s->cs_file[i].config[0] = i ? 1 << 12 : 0; + omap_gpmc_cs_unmap(s, i); s->cs_file[i].config[1] = 0x101001; s->cs_file[i].config[2] = 0x020201; s->cs_file[i].config[3] = 0x10031003; s->cs_file[i].config[4] = 0x10f1111; s->cs_file[i].config[5] = 0; s->cs_file[i].config[6] = 0xf00 | (i ? 0 : 1 << 6); - if (s->cs_file[i].config[6] & (1 << 6)) /* CSVALID */ - omap_gpmc_cs_map(&s->cs_file[i], - s->cs_file[i].config[6] & 0x1f, /* MASKADDR */ - (s->cs_file[i].config[6] >> 8 & 0xf)); /* BASEADDR */ + + s->cs_file[i].config[6] = 0xf00; + /* In theory we could probe attached devices for some CFG1 + * bits here, but we just retain them across resets as they + * were set initially by omap_gpmc_attach(). + */ + if (i == 0) { + s->cs_file[i].config[0] &= 0x00433e00; + s->cs_file[i].config[6] |= 1 << 6; /* CSVALID */ + omap_gpmc_cs_map(s, i); + } else { + s->cs_file[i].config[0] &= 0x00403c00; + } } s->ecc_cs = 0; s->ecc_ptr = 0; @@ -311,13 +330,10 @@ static void omap_gpmc_write(void *opaque, target_phys_addr_t addr, break; case 0x78: /* GPMC_CONFIG7 */ if ((f->config[6] ^ value) & 0xf7f) { - if (f->config[6] & (1 << 6)) /* CSVALID */ - omap_gpmc_cs_unmap(f); - if (value & (1 << 6)) /* CSVALID */ - omap_gpmc_cs_map(f, value & 0x1f, /* MASKADDR */ - (value >> 8 & 0xf)); /* BASEADDR */ + omap_gpmc_cs_unmap(s, cs); + f->config[6] = value & 0x00000f7f; + omap_gpmc_cs_map(s, cs); } - f->config[6] = value & 0x00000f7f; break; case 0x7c: /* GPMC_NAND_COMMAND */ case 0x80: /* GPMC_NAND_ADDRESS */ @@ -407,9 +423,7 @@ void omap_gpmc_attach(struct omap_gpmc_s *s, int cs, MemoryRegion *iomem) } f = &s->cs_file[cs]; + omap_gpmc_cs_unmap(s, cs); f->iomem = iomem; - - if (f->config[6] & (1 << 6)) /* CSVALID */ - omap_gpmc_cs_map(f, f->config[6] & 0x1f, /* MASKADDR */ - (f->config[6] >> 8 & 0xf)); /* BASEADDR */ + omap_gpmc_cs_map(s, cs); }