From patchwork Thu Jun 25 12:25:40 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sagar Shrikant Kadam X-Patchwork-Id: 1316870 X-Patchwork-Delegate: uboot@andestech.com Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=lists.denx.de (client-ip=85.214.62.61; helo=phobos.denx.de; envelope-from=u-boot-bounces@lists.denx.de; receiver=) Authentication-Results: ozlabs.org; dmarc=none (p=none dis=none) header.from=sifive.com Authentication-Results: ozlabs.org; dkim=pass (1024-bit key; unprotected) header.d=sifive.com header.i=@sifive.com header.a=rsa-sha256 header.s=selector1 header.b=tKm7uPZa; dkim-atps=neutral Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 49szlw0bMKz9sRW for ; Thu, 25 Jun 2020 22:26:51 +1000 (AEST) Received: from h2850616.stratoserver.net (localhost [IPv6:::1]) by phobos.denx.de (Postfix) with ESMTP id D042D82142; Thu, 25 Jun 2020 14:26:37 +0200 (CEST) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=sifive.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=u-boot-bounces@lists.denx.de Authentication-Results: phobos.denx.de; dkim=pass (1024-bit key; unprotected) header.d=sifive.com header.i=@sifive.com header.b="tKm7uPZa"; dkim-atps=neutral Received: by phobos.denx.de (Postfix, from userid 109) id 7876E82142; Thu, 25 Jun 2020 14:26:15 +0200 (CEST) X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on phobos.denx.de X-Spam-Level: X-Spam-Status: No, score=-1.0 required=5.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FORGED_SPF_HELO,MSGID_FROM_MTA_HEADER, SPF_HELO_PASS,URIBL_BLOCKED autolearn=no autolearn_force=no version=3.4.2 Received: from NAM12-BN8-obe.outbound.protection.outlook.com (mail-bn8nam12on20621.outbound.protection.outlook.com [IPv6:2a01:111:f400:fe5b::621]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by phobos.denx.de (Postfix) with ESMTPS id 3F0FF81F8F for ; Thu, 25 Jun 2020 14:26:09 +0200 (CEST) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=sifive.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=sagar.kadam@sifive.com ARC-Seal: i=1; a=rsa-sha256; s=arcselector9901; d=microsoft.com; cv=none; b=cgc43TtlnnGQSPRDVeMRtZ7UxrEG68fXkN6RZTBw0iP2o9ixvbri7iytXlZGjcQy1Ov6Vx2Z/9VWOMcfB/mBzyFDeed8Qf+CI+Ehh9qp4kAsaP+dueoVzSiN6y9P/dfQNeAah/6j3tednCrsnj6rf5bFRvIMd2FvHltWMYx9O2pH2PwSPiKYz75/XcT0yZhr6IdpyU/0KzOpLmobA2hwBix8ap75HY39HJpVyVj+jt8B0I49kXr0iSYD/i3EVDP0qEsLJvZlbKBSAuX6h2JxIhrHGxHZ/19PjOEXJHZZ/ljg+6A+hEc+vYnW/x9jQUiBuI0vDnTuNIMVb7RkNe2E5w== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector9901; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=ZCZ8R1B407Ar4JgQNZ3+wPindQx8D+k5wGb0+OPqWh8=; b=eTQvUTGx72WzhIR2Zv9D+zy2N5fQln5P0DP0QDIkKcvmQPlvQHLfQIw9E26AvZ8AaMC1Ocg5LBU7869Cf+jTXsnc9iLl3sGLjLcSfRcjaVZRv7InkkCm7bqHU8D4NBcS7/dQFlOUxEs14OnqBqEHu+gfEddNUXLGUxQ3UM0/uwwVoDuqJ6h7kJg1+v06wVMhk6wYGFMlPzBzus5ge993XVZyQGS3toAJcV013j0Dnc7qSXPC9j3TVMYjV6moFhqHa50L/aGxCWPNZ69ApZmN61nTpOJ4j5nCKuv4EP2fOj4T6y6dlpLR6mX/n+GhSrTZLggos3+2HrTO9EeSk5cHvQ== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass smtp.mailfrom=sifive.com; dmarc=pass action=none header.from=sifive.com; dkim=pass header.d=sifive.com; arc=none DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=sifive.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=ZCZ8R1B407Ar4JgQNZ3+wPindQx8D+k5wGb0+OPqWh8=; b=tKm7uPZayhtOaXfj8dRJb6IRHvOzx7i6eEG3UJ4tHTLUGqmmvOazUowEjo/9MjSzAA/3Yrudye83FQOabyk7wXO9iFkOt8MVaZTjhr24GdAeo8DBfYDKFuBCfKew1iuT8uo/mdJmR1sdarHtFT8KQ0MMcK3dBcddYZhLQrXdlIE= Authentication-Results: lists.denx.de; dkim=none (message not signed) header.d=none;lists.denx.de; dmarc=none action=none header.from=sifive.com; Received: from BN8PR13MB2611.namprd13.prod.outlook.com (2603:10b6:408:81::17) by BN8PR13MB2770.namprd13.prod.outlook.com (2603:10b6:408:8b::31) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.3153.12; Thu, 25 Jun 2020 12:26:07 +0000 Received: from BN8PR13MB2611.namprd13.prod.outlook.com ([fe80::c1d9:f4ee:80ab:de83]) by BN8PR13MB2611.namprd13.prod.outlook.com ([fe80::c1d9:f4ee:80ab:de83%6]) with mapi id 15.20.3153.010; Thu, 25 Jun 2020 12:26:07 +0000 From: Sagar Shrikant Kadam To: u-boot@lists.denx.de Cc: rick@andestech.com, paul.walmsley@sifive.com, palmer@dabbelt.com, anup.patel@wdc.com, atish.patra@wdc.com, lukma@denx.de, pragnesh.patel@sifive.com, bin.meng@windriver.com, jagan@amarulasolutions.com, sjg@chromium.org, twoerner@gmail.com, Eugeniy.Paltsev@synopsys.com, patrick@blueri.se, weijie.gao@mediatek.com, festevam@gmail.com, Sagar Shrikant Kadam Subject: [PATCH v2 4/5] sifive: reset: add DM based reset driver for SiFive SoC's Date: Thu, 25 Jun 2020 05:25:40 -0700 Message-Id: <1593087941-16872-5-git-send-email-sagar.kadam@sifive.com> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1593087941-16872-1-git-send-email-sagar.kadam@sifive.com> References: <1593087941-16872-1-git-send-email-sagar.kadam@sifive.com> X-ClientProxiedBy: BYAPR11CA0090.namprd11.prod.outlook.com (2603:10b6:a03:f4::31) To BN8PR13MB2611.namprd13.prod.outlook.com (2603:10b6:408:81::17) MIME-Version: 1.0 X-MS-Exchange-MessageSentRepresentingType: 1 Received: from gamma07.internal.sifive.com (64.62.193.194) by BYAPR11CA0090.namprd11.prod.outlook.com (2603:10b6:a03:f4::31) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256) id 15.20.3131.21 via Frontend Transport; Thu, 25 Jun 2020 12:26:05 +0000 X-Mailer: git-send-email 2.7.4 X-Originating-IP: [64.62.193.194] X-MS-PublicTrafficType: Email X-MS-Office365-Filtering-Correlation-Id: 5b11a9c0-5755-44c8-6cd1-08d81902ef77 X-MS-TrafficTypeDiagnostic: BN8PR13MB2770: X-LD-Processed: 22f88e9d-ae0d-4ed9-b984-cdc9be1529f1,ExtAddr X-MS-Exchange-Transport-Forked: True X-Microsoft-Antispam-PRVS: X-MS-Oob-TLC-OOBClassifiers: OLM:345; X-Forefront-PRVS: 0445A82F82 X-MS-Exchange-SenderADCheck: 1 X-Microsoft-Antispam: BCL:0; X-Microsoft-Antispam-Message-Info: ReMYDXhgquI2AOfx77qqDPfkk8kCQ43kkewxjIBGfnqJz9ONA5mc9oDCUKIIKgDPUe/bJJETpZWvDlxDdd91/B8AXMQY+97m50Iy8Az4YVuGf2AkTj7T+WGDWZf7mKJj/C7yfzp7smSqnUR8CGuBxJWtRxuz5P7yQ+S8d4s3WmtLNsA4pNU1TgGgXZ5r0S18VgmS0hffsm7FW87ioHGPqlpd2rvwKGzY8nh2rppCdCy/Y0586QOczQxn3ZAoM8UOdYKiCOteiaTgzGbVDEzeaekGbo9DGZgvQw+aZcZpcPdpG3MQ/QYOEGyRdEF8U3W8f2VddsKuLaq5sixOEMDMAA== X-Forefront-Antispam-Report: CIP:255.255.255.255; CTRY:; LANG:en; SCL:1; SRV:; IPV:NLI; SFV:NSPM; H:BN8PR13MB2611.namprd13.prod.outlook.com; PTR:; CAT:NONE; SFTY:; SFS:(6029001)(396003)(136003)(346002)(366004)(39850400004)(376002)(7416002)(316002)(4326008)(6486002)(52116002)(7696005)(36756003)(8676002)(66476007)(66556008)(66946007)(478600001)(6916009)(86362001)(6666004)(2906002)(83380400001)(5660300002)(8936002)(26005)(956004)(186003)(107886003)(2616005)(16526019); DIR:OUT; SFP:1101; X-MS-Exchange-AntiSpam-MessageData: 8An8vsblhGWrJ3rHR3a0NJhEQpO8XobJC274nzI3Vl1qy+4RisvLmHsnA5nE3ofQgfjk0xp+Ub9/++w+GBCrSlY6hwQLBvEoEvDr6eIJbrlbpUbdp/hGrc9ouUOpJ238NfuPBQMk6s2zWI/NeZrPP4zD6z97DrA7SLnQwOhnm4550/CWLnx5SaHdQKWtKwpcW3uoEUn5GPNkP1oEFlRaH9x2tfLi6uVWfujExNlxAoFgxVBUKBpqdqYPdfR/HIJm4T0By/PbNvSVq9GFclrnbUJMo9pWd7lDNp3sCSWhKAI/W8ofIsZ1q+024/98qXviPrHJNStljPYLP5exckGtqLXYLGgNek1b4q8dh8oyvwFW7/e6Gg7XfNd+xdeDI64zv/yRLHIM2DWGXeTwgYlguUzlpku1W70mKIRuZT6W0Wq/bMg17z+a2s4aqplJ02jEAK1j2EO0uYGA5PbC5rYa27M22UC9En2Quha1o4FOAAcharQFvwRe/VEiPGuP8wZv X-OriginatorOrg: sifive.com X-MS-Exchange-CrossTenant-Network-Message-Id: 5b11a9c0-5755-44c8-6cd1-08d81902ef77 X-MS-Exchange-CrossTenant-AuthSource: BN8PR13MB2611.namprd13.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Internal X-MS-Exchange-CrossTenant-OriginalArrivalTime: 25 Jun 2020 12:26:07.3584 (UTC) X-MS-Exchange-CrossTenant-FromEntityHeader: Hosted X-MS-Exchange-CrossTenant-Id: 22f88e9d-ae0d-4ed9-b984-cdc9be1529f1 X-MS-Exchange-CrossTenant-MailboxType: HOSTED X-MS-Exchange-CrossTenant-UserPrincipalName: /rVCMuJ8l5TmU0f5TwzFHMVOBRJ9ZY8827c9h4F7LIE4LbVuu/dVCF9nvFQ14iudcE1O9zckYGXNrzmGkQnCWw== X-MS-Exchange-Transport-CrossTenantHeadersStamped: BN8PR13MB2770 X-BeenThere: u-boot@lists.denx.de X-Mailman-Version: 2.1.30rc1 Precedence: list List-Id: U-Boot discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: u-boot-bounces@lists.denx.de Sender: "U-Boot" X-Virus-Scanned: clamav-milter 0.102.2 at phobos.denx.de X-Virus-Status: Clean PRCI module within SiFive SoC's has register with which we can reset the sub-systems within the SoC. The resets to DDR and ethernet sub systems within FU540-C000 SoC are active low, and are hold low by default on power-up. Currently these are directly asserted within prci driver via register read/write. With the DM based reset driver support here, we bind the reset driver with clock (prci) driver and assert the reset signals of both sub-system's appropriately. Signed-off-by: Sagar Shrikant Kadam Reviewed-by: Pragnesh Patel Reviewed-by: Bin Meng Tested-by: Bin Meng --- arch/riscv/include/asm/arch-fu540/reset.h | 13 ++++ drivers/clk/sifive/fu540-prci.c | 73 ++++++++++++++---- drivers/reset/reset-sifive.c | 118 ++++++++++++++++++++++++++++++ 3 files changed, 189 insertions(+), 15 deletions(-) create mode 100644 arch/riscv/include/asm/arch-fu540/reset.h create mode 100644 drivers/reset/reset-sifive.c diff --git a/arch/riscv/include/asm/arch-fu540/reset.h b/arch/riscv/include/asm/arch-fu540/reset.h new file mode 100644 index 0000000..e42797a --- /dev/null +++ b/arch/riscv/include/asm/arch-fu540/reset.h @@ -0,0 +1,13 @@ +/* SPDX-License-Identifier: GPL-2.0+ */ +/* + * Copyright (c) 2020 SiFive, Inc. + * + * Author: Sagar Kadam + */ + +#ifndef __RESET_SIFIVE_H +#define __RESET_SIFIVE_H + +int sifive_reset_bind(struct udevice *dev, ulong count); + +#endif diff --git a/drivers/clk/sifive/fu540-prci.c b/drivers/clk/sifive/fu540-prci.c index 57d811e..675b508 100644 --- a/drivers/clk/sifive/fu540-prci.c +++ b/drivers/clk/sifive/fu540-prci.c @@ -30,11 +30,15 @@ #include #include +#include #include #include #include #include #include +#include +#include +#include #include #include @@ -131,6 +135,7 @@ /* DEVICESRESETREG */ #define PRCI_DEVICESRESETREG_OFFSET 0x28 +#define PRCI_DEVICERESETCNT 5 #define PRCI_DEVICESRESETREG_DDR_CTRL_RST_N_MASK \ (0x1 << PRCI_RST_DDR_CTRL_N) @@ -524,6 +529,41 @@ static const struct __prci_clock_ops sifive_fu540_prci_tlclksel_clk_ops = { .recalc_rate = sifive_fu540_prci_tlclksel_recalc_rate, }; +static int __prci_consumer_reset(const char *rst_name, bool trigger) +{ + struct udevice *dev; + struct reset_ctl rst_sig; + int ret; + + ret = uclass_get_device_by_driver(UCLASS_RESET, + DM_GET_DRIVER(sifive_reset), + &dev); + if (ret) { + dev_err(dev, "Reset driver not found: %d\n", ret); + return ret; + } + + ret = reset_get_by_name(dev, rst_name, &rst_sig); + if (ret) { + dev_err(dev, "failed to get %s reset\n", rst_name); + return ret; + } + + if (reset_valid(&rst_sig)) { + if (trigger) + ret = reset_deassert(&rst_sig); + else + ret = reset_assert(&rst_sig); + if (ret) { + dev_err(dev, "failed to trigger reset id = %ld\n", + rst_sig.id); + return ret; + } + } + + return ret; +} + /** * __prci_ddr_release_reset() - Release DDR reset * @pd: struct __prci_data * for the PRCI containing the DDRCLK mux reg @@ -531,19 +571,20 @@ static const struct __prci_clock_ops sifive_fu540_prci_tlclksel_clk_ops = { */ static void __prci_ddr_release_reset(struct __prci_data *pd) { - u32 v; - - v = __prci_readl(pd, PRCI_DEVICESRESETREG_OFFSET); - v |= PRCI_DEVICESRESETREG_DDR_CTRL_RST_N_MASK; - __prci_writel(v, PRCI_DEVICESRESETREG_OFFSET, pd); + /* Release DDR ctrl reset */ + __prci_consumer_reset("ddr_ctrl", true); /* HACK to get the '1 full controller clock cycle'. */ asm volatile ("fence"); - v = __prci_readl(pd, PRCI_DEVICESRESETREG_OFFSET); - v |= (PRCI_DEVICESRESETREG_DDR_AXI_RST_N_MASK | - PRCI_DEVICESRESETREG_DDR_AHB_RST_N_MASK | - PRCI_DEVICESRESETREG_DDR_PHY_RST_N_MASK); - __prci_writel(v, PRCI_DEVICESRESETREG_OFFSET, pd); + + /* Release DDR AXI reset */ + __prci_consumer_reset("ddr_axi", true); + + /* Release DDR AHB reset */ + __prci_consumer_reset("ddr_ahb", true); + + /* Release DDR PHY reset */ + __prci_consumer_reset("ddr_phy", true); /* HACK to get the '1 full controller clock cycle'. */ asm volatile ("fence"); @@ -563,12 +604,8 @@ static void __prci_ddr_release_reset(struct __prci_data *pd) */ static void __prci_ethernet_release_reset(struct __prci_data *pd) { - u32 v; - /* Release GEMGXL reset */ - v = __prci_readl(pd, PRCI_DEVICESRESETREG_OFFSET); - v |= PRCI_DEVICESRESETREG_GEMGXL_RST_N_MASK; - __prci_writel(v, PRCI_DEVICESRESETREG_OFFSET, pd); + __prci_consumer_reset("gemgxl_reset", true); /* Procmon => core clock */ __prci_writel(PRCI_PROCMONCFG_CORE_CLOCK_MASK, PRCI_PROCMONCFG_OFFSET, @@ -753,6 +790,11 @@ static struct clk_ops sifive_fu540_prci_ops = { .disable = sifive_fu540_prci_disable, }; +static int sifive_fu540_clk_bind(struct udevice *dev) +{ + return sifive_reset_bind(dev, PRCI_DEVICERESETCNT); +} + static const struct udevice_id sifive_fu540_prci_ids[] = { { .compatible = "sifive,fu540-c000-prci" }, { } @@ -765,4 +807,5 @@ U_BOOT_DRIVER(sifive_fu540_prci) = { .probe = sifive_fu540_prci_probe, .ops = &sifive_fu540_prci_ops, .priv_auto_alloc_size = sizeof(struct __prci_data), + .bind = sifive_fu540_clk_bind, }; diff --git a/drivers/reset/reset-sifive.c b/drivers/reset/reset-sifive.c new file mode 100644 index 0000000..527757f --- /dev/null +++ b/drivers/reset/reset-sifive.c @@ -0,0 +1,118 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Copyright (C) 2020 Sifive, Inc. + * Author: Sagar Kadam + */ + +#include +#include +#include +#include +#include +#include +#include + +#define PRCI_RESETREG_OFFSET 0x28 + +struct sifive_reset_priv { + void *base; + /* number of reset signals */ + int nr_reset; +}; + +static int sifive_rst_trigger(struct reset_ctl *rst, bool level) +{ + struct sifive_reset_priv *priv = dev_get_priv(rst->dev); + int id = rst->id; + int regval = readl(priv->base + PRCI_RESETREG_OFFSET); + + /* Derive bitposition from rst id */ + if (level) + /* Reset deassert */ + regval |= BIT(id); + else + /* Reset assert */ + regval &= ~BIT(id); + + writel(regval, priv->base + PRCI_RESETREG_OFFSET); + + return 0; +} + +static int sifive_reset_assert(struct reset_ctl *rst) +{ + return sifive_rst_trigger(rst, false); +} + +static int sifive_reset_deassert(struct reset_ctl *rst) +{ + return sifive_rst_trigger(rst, true); +} + +static int sifive_reset_request(struct reset_ctl *rst) +{ + struct sifive_reset_priv *priv = dev_get_priv(rst->dev); + + debug("%s(rst=%p) (dev=%p, id=%lu) (nr_reset=%d)\n", __func__, + rst, rst->dev, rst->id, priv->nr_reset); + + if (rst->id > priv->nr_reset) + return -EINVAL; + + return 0; +} + +static int sifive_reset_free(struct reset_ctl *rst) +{ + struct sifive_reset_priv *priv = dev_get_priv(rst->dev); + + debug("%s(rst=%p) (dev=%p, id=%lu) (nr_reset=%d)\n", __func__, + rst, rst->dev, rst->id, priv->nr_reset); + + return 0; +} + +static int sifive_reset_probe(struct udevice *dev) +{ + struct sifive_reset_priv *priv = dev_get_priv(dev); + + priv->base = dev_remap_addr(dev); + if (!priv->base) + return -ENOMEM; + + return 0; +} + +int sifive_reset_bind(struct udevice *dev, ulong count) +{ + struct udevice *rst_dev; + struct sifive_reset_priv *priv; + int ret; + + ret = device_bind_driver_to_node(dev, "sifive-reset", "reset", + dev_ofnode(dev), &rst_dev); + if (ret) { + dev_err(dev, "failed to bind sifive_reset driver (ret=%d)\n", ret); + return ret; + } + priv = malloc(sizeof(struct sifive_reset_priv)); + priv->nr_reset = count; + rst_dev->priv = priv; + + return 0; +} + +const struct reset_ops sifive_reset_ops = { + .request = sifive_reset_request, + .rfree = sifive_reset_free, + .rst_assert = sifive_reset_assert, + .rst_deassert = sifive_reset_deassert, +}; + +U_BOOT_DRIVER(sifive_reset) = { + .name = "sifive-reset", + .id = UCLASS_RESET, + .ops = &sifive_reset_ops, + .probe = sifive_reset_probe, + .priv_auto_alloc_size = sizeof(struct sifive_reset_priv), +};