From nobody Wed Feb 11 04:21:50 2026 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=fail header.i=@wdc.com; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=wdc.com ARC-Seal: i=1; a=rsa-sha256; t=1599762498; cv=none; d=zohomail.com; s=zohoarc; b=S/UVIz+0wJOaFy9wvJlTcWW8tPls2ZLatzlU/1XulkVOwzh7+gc+obppe2NELViq8htQFTJeU3POYjeA4UhEBqXXnnG/8sppa1hCcrZGyVlqcrpJXX1yo1x8aZWE+vMEeg3Fq3mrl16YB81mWLlfjloL+5b3qrD50XNYLu1YmRw= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1599762498; h=Content-Type:Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:To; bh=Fu4smwv6EeFYOX+dWzOl/wRfr0StbyoUclAyLaVvY3w=; b=SJbv7zLJXAnNqWG0nNSYGtDCePP/4m5gwB9BaAhLM7yuJvpNOk+Jt72ll9aE0+uZx5yamsP++cnWYFlmw7RtAoSkRiiKaJtOY+KISWkLioUVvZubqCXTSzdBsYYg/yHKmK5vtvhErdoiWfOjXXDR+YIL3UIf2flifm67p9e3MYA= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=fail header.i=@wdc.com; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail header.from= (p=none dis=none) header.from= Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1599762498254583.5216118128101; Thu, 10 Sep 2020 11:28:18 -0700 (PDT) Received: from localhost ([::1]:50726 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1kGRIu-0007Ue-Rx for importer@patchew.org; Thu, 10 Sep 2020 14:28:16 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]:57126) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1kGRBQ-0003tu-0Y for qemu-devel@nongnu.org; Thu, 10 Sep 2020 14:20:32 -0400 Received: from esa4.hgst.iphmx.com ([216.71.154.42]:28245) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1kGRBM-0002iJ-Nt for qemu-devel@nongnu.org; Thu, 10 Sep 2020 14:20:31 -0400 Received: from h199-255-45-14.hgst.com (HELO uls-op-cesaep01.wdc.com) ([199.255.45.14]) by ob1.hgst.iphmx.com with ESMTP; 11 Sep 2020 02:20:16 +0800 Received: from uls-op-cesaip01.wdc.com ([10.248.3.36]) by uls-op-cesaep01.wdc.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 10 Sep 2020 11:07:33 -0700 Received: from fwvkpc2.ad.shared (HELO risc6-mainframe.hgst.com) ([10.86.59.152]) by uls-op-cesaip01.wdc.com with ESMTP; 10 Sep 2020 11:20:17 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=wdc.com; i=@wdc.com; q=dns/txt; s=dkim.wdc.com; t=1599762028; x=1631298028; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=jl1QY3CZyppQuWzflLHAKCho7h0VBeksQL78FFZEPhc=; b=jk+JCmZMCpIAb8KSkiFmor1syeIxQopHH3+RN828uIzcL9hWtxf5PGJt 0e5jpoZdX052raW/M3uGVNdY1nun+FDYG2wYpQrJ4sS7vlda9v2bTepWX fFS2aTrXN7qOaBaN83ZE9imRKZKgbXZuY17weuhHXYjBDHmSYKNRPIOTX ywDFZAJDnkJ1aBfQKb+83FKZ7UdbIahVoSwGLemYxVoUD6D+xCINjCft5 D4BX+J1VkhmIFDD/jCNLTejiby3v4HuLPFPfoNBgijX1CLEs8tGKs00IN wYwmDeGik2tSezmLGGlg2m7FtOHQVbHZP7WUthuD3Ovsgq8MsghNKVanE g==; IronPort-SDR: wwNtq3LRTxhGO/eAvtw7MRv0to+4KIhoQ+dEoNGvbeC+oTy28aXRaQc9ISVSeJ9ibkM9qBieZp oRtRN33aR6sQGnNXzJjkmqeaebvZYjbxGlikxWk5FDbJaBeieRU1yCVg74z0FSj7StzF2jIeS6 jyqR6siqPPcvaCc5aaaUMWOlgp3SgX0d3seERWWMWX0jLNn/uLpR3siRs1EKkFFtncQKn/OHpE zBjqK612/z2RmUZHsYexeZMKcp2xXJV5GxboPk3cT4Ouiqv3gIQvDsAte6jOA9eoRRVdpCHvuG TFg= X-IronPort-AV: E=Sophos;i="5.76,413,1592841600"; d="scan'208";a="146979222" IronPort-SDR: HUC0UHjwb8FBYb6LJfbA/XHU27WcwTPlbAuzuy0IrAgisU8+uMbffg/Z+DnA6/+lVbeWnKj/lN H270KsYQ9brw== IronPort-SDR: 1sVVeGVzZmhzIo1kVIEOtxWEYjBTPS5becA99sQVXX5y9AzrqfWg6eyuZdiD5L2KoaI/+dRMsg dtENCRcBdctQ== WDCIronportException: Internal From: Alistair Francis To: peter.maydell@linaro.org, qemu-devel@nongnu.org Subject: [PULL 09/30] hw/sd: Add Cadence SDHCI emulation Date: Thu, 10 Sep 2020 11:09:17 -0700 Message-Id: <20200910180938.584205-10-alistair.francis@wdc.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20200910180938.584205-1-alistair.francis@wdc.com> References: <20200910180938.584205-1-alistair.francis@wdc.com> MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Received-SPF: pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Received-SPF: pass client-ip=216.71.154.42; envelope-from=prvs=515d47f05=alistair.francis@wdc.com; helo=esa4.hgst.iphmx.com X-detected-operating-system: by eggs.gnu.org: First seen = 2020/09/10 14:20:04 X-ACL-Warn: Detected OS = FreeBSD 9.x or newer [fuzzy] X-Spam_score_int: -43 X-Spam_score: -4.4 X-Spam_bar: ---- X-Spam_report: (-4.4 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, RCVD_IN_DNSWL_MED=-2.3, SPF_HELO_PASS=-0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: alistair23@gmail.com, Bin Meng , Alistair Francis , =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) From: Bin Meng Cadence SD/SDIO/eMMC Host Controller (SD4HC) is an SDHCI compatible controller. The SDHCI compatible registers start from offset 0x200, which are called Slot Register Set (SRS) in its datasheet. This creates a Cadence SDHCI model built on top of the existing generic SDHCI model. Cadence specific Host Register Set (HRS) is implemented to make guest software happy. Signed-off-by: Bin Meng Acked-by: Philippe Mathieu-Daud=C3=A9 Acked-by: Alistair Francis Message-Id: <1598924352-89526-8-git-send-email-bmeng.cn@gmail.com> Signed-off-by: Alistair Francis --- include/hw/sd/cadence_sdhci.h | 47 +++++++++ hw/sd/cadence_sdhci.c | 193 ++++++++++++++++++++++++++++++++++ hw/sd/Kconfig | 4 + hw/sd/meson.build | 1 + 4 files changed, 245 insertions(+) create mode 100644 include/hw/sd/cadence_sdhci.h create mode 100644 hw/sd/cadence_sdhci.c diff --git a/include/hw/sd/cadence_sdhci.h b/include/hw/sd/cadence_sdhci.h new file mode 100644 index 0000000000..cd8288b7d8 --- /dev/null +++ b/include/hw/sd/cadence_sdhci.h @@ -0,0 +1,47 @@ +/* + * Cadence SDHCI emulation + * + * Copyright (c) 2020 Wind River Systems, Inc. + * + * Author: + * Bin Meng + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation; either version 2 or + * (at your option) version 3 of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, see . + */ + +#ifndef CADENCE_SDHCI_H +#define CADENCE_SDHCI_H + +#include "hw/sd/sdhci.h" + +#define CADENCE_SDHCI_REG_SIZE 0x100 +#define CADENCE_SDHCI_NUM_REGS (CADENCE_SDHCI_REG_SIZE / sizeof(uint32_t)) + +typedef struct CadenceSDHCIState { + SysBusDevice parent; + + MemoryRegion container; + MemoryRegion iomem; + BusState *bus; + + uint32_t regs[CADENCE_SDHCI_NUM_REGS]; + + SDHCIState sdhci; +} CadenceSDHCIState; + +#define TYPE_CADENCE_SDHCI "cadence.sdhci" +#define CADENCE_SDHCI(obj) OBJECT_CHECK(CadenceSDHCIState, (obj), \ + TYPE_CADENCE_SDHCI) + +#endif /* CADENCE_SDHCI_H */ diff --git a/hw/sd/cadence_sdhci.c b/hw/sd/cadence_sdhci.c new file mode 100644 index 0000000000..0b371c843d --- /dev/null +++ b/hw/sd/cadence_sdhci.c @@ -0,0 +1,193 @@ +/* + * Cadence SDHCI emulation + * + * Copyright (c) 2020 Wind River Systems, Inc. + * + * Author: + * Bin Meng + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation; either version 2 or + * (at your option) version 3 of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, see . + */ + +#include "qemu/osdep.h" +#include "qemu/bitops.h" +#include "qemu/error-report.h" +#include "qemu/log.h" +#include "qapi/error.h" +#include "migration/vmstate.h" +#include "hw/irq.h" +#include "hw/sd/cadence_sdhci.h" +#include "sdhci-internal.h" + +/* HRS - Host Register Set (specific to Cadence) */ + +#define CADENCE_SDHCI_HRS00 0x00 /* general information */ +#define CADENCE_SDHCI_HRS00_SWR BIT(0) +#define CADENCE_SDHCI_HRS00_POR_VAL 0x00010000 + +#define CADENCE_SDHCI_HRS04 0x10 /* PHY access port */ +#define CADENCE_SDHCI_HRS04_WR BIT(24) +#define CADENCE_SDHCI_HRS04_RD BIT(25) +#define CADENCE_SDHCI_HRS04_ACK BIT(26) + +#define CADENCE_SDHCI_HRS06 0x18 /* eMMC control */ +#define CADENCE_SDHCI_HRS06_TUNE_UP BIT(15) + +/* SRS - Slot Register Set (SDHCI-compatible) */ + +#define CADENCE_SDHCI_SRS_BASE 0x200 + +#define TO_REG(addr) ((addr) / sizeof(uint32_t)) + +static void cadence_sdhci_instance_init(Object *obj) +{ + CadenceSDHCIState *s =3D CADENCE_SDHCI(obj); + + object_initialize_child(OBJECT(s), "generic-sdhci", + &s->sdhci, TYPE_SYSBUS_SDHCI); +} + +static void cadence_sdhci_reset(DeviceState *dev) +{ + CadenceSDHCIState *s =3D CADENCE_SDHCI(dev); + + memset(s->regs, 0, CADENCE_SDHCI_REG_SIZE); + s->regs[TO_REG(CADENCE_SDHCI_HRS00)] =3D CADENCE_SDHCI_HRS00_POR_VAL; + + device_cold_reset(DEVICE(&s->sdhci)); +} + +static uint64_t cadence_sdhci_read(void *opaque, hwaddr addr, unsigned int= size) +{ + CadenceSDHCIState *s =3D opaque; + uint32_t val; + + val =3D s->regs[TO_REG(addr)]; + + return (uint64_t)val; +} + +static void cadence_sdhci_write(void *opaque, hwaddr addr, uint64_t val, + unsigned int size) +{ + CadenceSDHCIState *s =3D opaque; + uint32_t val32 =3D (uint32_t)val; + + switch (addr) { + case CADENCE_SDHCI_HRS00: + /* + * The only writable bit is SWR (software reset) and it automatica= lly + * clears to zero, so essentially this register remains unchanged. + */ + if (val32 & CADENCE_SDHCI_HRS00_SWR) { + cadence_sdhci_reset(DEVICE(s)); + } + + break; + case CADENCE_SDHCI_HRS04: + /* + * Only emulate the ACK bit behavior when read or write transaction + * are requested. + */ + if (val32 & (CADENCE_SDHCI_HRS04_WR | CADENCE_SDHCI_HRS04_RD)) { + val32 |=3D CADENCE_SDHCI_HRS04_ACK; + } else { + val32 &=3D ~CADENCE_SDHCI_HRS04_ACK; + } + + s->regs[TO_REG(addr)] =3D val32; + break; + case CADENCE_SDHCI_HRS06: + if (val32 & CADENCE_SDHCI_HRS06_TUNE_UP) { + val32 &=3D ~CADENCE_SDHCI_HRS06_TUNE_UP; + } + + s->regs[TO_REG(addr)] =3D val32; + break; + default: + s->regs[TO_REG(addr)] =3D val32; + break; + } +} + +static const MemoryRegionOps cadence_sdhci_ops =3D { + .read =3D cadence_sdhci_read, + .write =3D cadence_sdhci_write, + .endianness =3D DEVICE_NATIVE_ENDIAN, + .impl =3D { + .min_access_size =3D 4, + .max_access_size =3D 4, + }, + .valid =3D { + .min_access_size =3D 4, + .max_access_size =3D 4, + } +}; + +static void cadence_sdhci_realize(DeviceState *dev, Error **errp) +{ + CadenceSDHCIState *s =3D CADENCE_SDHCI(dev); + SysBusDevice *sbd =3D SYS_BUS_DEVICE(dev); + SysBusDevice *sbd_sdhci =3D SYS_BUS_DEVICE(&s->sdhci); + + memory_region_init(&s->container, OBJECT(s), + "cadence.sdhci-container", 0x1000); + sysbus_init_mmio(sbd, &s->container); + + memory_region_init_io(&s->iomem, OBJECT(s), &cadence_sdhci_ops, + s, TYPE_CADENCE_SDHCI, CADENCE_SDHCI_REG_SIZE); + memory_region_add_subregion(&s->container, 0, &s->iomem); + + sysbus_realize(sbd_sdhci, errp); + memory_region_add_subregion(&s->container, CADENCE_SDHCI_SRS_BASE, + sysbus_mmio_get_region(sbd_sdhci, 0)); + + /* propagate irq and "sd-bus" from generic-sdhci */ + sysbus_pass_irq(sbd, sbd_sdhci); + s->bus =3D qdev_get_child_bus(DEVICE(sbd_sdhci), "sd-bus"); +} + +static const VMStateDescription vmstate_cadence_sdhci =3D { + .name =3D TYPE_CADENCE_SDHCI, + .version_id =3D 1, + .fields =3D (VMStateField[]) { + VMSTATE_UINT32_ARRAY(regs, CadenceSDHCIState, CADENCE_SDHCI_NUM_RE= GS), + VMSTATE_END_OF_LIST(), + }, +}; + +static void cadence_sdhci_class_init(ObjectClass *classp, void *data) +{ + DeviceClass *dc =3D DEVICE_CLASS(classp); + + dc->desc =3D "Cadence SD/SDIO/eMMC Host Controller (SD4HC)"; + dc->realize =3D cadence_sdhci_realize; + dc->reset =3D cadence_sdhci_reset; + dc->vmsd =3D &vmstate_cadence_sdhci; +} + +static TypeInfo cadence_sdhci_info =3D { + .name =3D TYPE_CADENCE_SDHCI, + .parent =3D TYPE_SYS_BUS_DEVICE, + .instance_size =3D sizeof(CadenceSDHCIState), + .instance_init =3D cadence_sdhci_instance_init, + .class_init =3D cadence_sdhci_class_init, +}; + +static void cadence_sdhci_register_types(void) +{ + type_register_static(&cadence_sdhci_info); +} + +type_init(cadence_sdhci_register_types) diff --git a/hw/sd/Kconfig b/hw/sd/Kconfig index c5e1e5581c..633b9afec9 100644 --- a/hw/sd/Kconfig +++ b/hw/sd/Kconfig @@ -19,3 +19,7 @@ config SDHCI_PCI default y if PCI_DEVICES depends on PCI select SDHCI + +config CADENCE_SDHCI + bool + select SDHCI diff --git a/hw/sd/meson.build b/hw/sd/meson.build index b43e59bd00..9c29691e13 100644 --- a/hw/sd/meson.build +++ b/hw/sd/meson.build @@ -10,3 +10,4 @@ softmmu_ss.add(when: 'CONFIG_PXA2XX', if_true: files('pxa= 2xx_mmci.c')) softmmu_ss.add(when: 'CONFIG_RASPI', if_true: files('bcm2835_sdhost.c')) softmmu_ss.add(when: 'CONFIG_ASPEED_SOC', if_true: files('aspeed_sdhci.c')) softmmu_ss.add(when: 'CONFIG_ALLWINNER_H3', if_true: files('allwinner-sdho= st.c')) +softmmu_ss.add(when: 'CONFIG_CADENCE_SDHCI', if_true: files('cadence_sdhci= .c')) --=20 2.28.0