From: Joshua Yeong <joshua.yeong@starfivetech.com> To: paul.walmsley@sifive.com, palmer@dabbelt.com, aou@eecs.berkeley.edu, geert+renesas@glider.be, joshua.yeong@starfivetech.com, prabhakar.mahadev-lad.rj@bp.renesas.com, conor.dooley@microchip.com, alexghiti@rivosinc.com, evan@rivosinc.com, ajones@ventanamicro.com, heiko@sntech.de, guoren@kernel.org, uwu@icenowy.me, jszhang@kernel.org, conor@kernel.org, robh+dt@kernel.org, krzysztof.kozlowski+dt@linaro.org, conor+dt@kernel.org, leyfoon.tan@starfivetech.com, jeeheng.sia@starfivetech.com Cc: linux-riscv@lists.infradead.org, linux-kernel@vger.kernel.org, devicetree@vger.kernel.org Subject: [PATCH 3/4] cache: Add StarLink-500 cache management for StarFive JH8100 RISC-V core Date: Thu, 14 Mar 2024 14:12:04 +0800 [thread overview] Message-ID: <20240314061205.26143-4-joshua.yeong@starfivetech.com> (raw) In-Reply-To: <20240314061205.26143-1-joshua.yeong@starfivetech.com> Add software workaround for StarFive StarLink-500 on JH8100 SoC for CMO extension instructions. Signed-off-by: Joshua Yeong <joshua.yeong@starfivetech.com> --- drivers/cache/Kconfig | 9 ++ drivers/cache/Makefile | 1 + drivers/cache/starlink500_cache.c | 137 ++++++++++++++++++++++++++++++ 3 files changed, 147 insertions(+) create mode 100644 drivers/cache/starlink500_cache.c diff --git a/drivers/cache/Kconfig b/drivers/cache/Kconfig index 9345ce4976d7..e215379f6a73 100644 --- a/drivers/cache/Kconfig +++ b/drivers/cache/Kconfig @@ -14,4 +14,13 @@ config SIFIVE_CCACHE help Support for the composable cache controller on SiFive platforms. +config STARLINK_500_CACHE + bool "StarLink-500 Cache controller" + depends on RISCV_DMA_NONCOHERENT + depends on ERRATA_STARFIVE + select RISCV_NONSTANDARD_CACHE_OPS + default y + help + Support for the StarLink-500 cache controller on StarFive platforms. + endmenu diff --git a/drivers/cache/Makefile b/drivers/cache/Makefile index 7657cff3bd6c..c515eb5714ea 100644 --- a/drivers/cache/Makefile +++ b/drivers/cache/Makefile @@ -2,3 +2,4 @@ obj-$(CONFIG_AX45MP_L2_CACHE) += ax45mp_cache.o obj-$(CONFIG_SIFIVE_CCACHE) += sifive_ccache.o +obj-$(CONFIG_STARLINK_500_CACHE) += starlink500_cache.o diff --git a/drivers/cache/starlink500_cache.c b/drivers/cache/starlink500_cache.c new file mode 100644 index 000000000000..eaf8303cb086 --- /dev/null +++ b/drivers/cache/starlink500_cache.c @@ -0,0 +1,137 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Non-coherent cache functions for StarFive's StarLink-500 cache controller + * + * Copyright (C) 2024 Shanghai StarFive Technology Co., Ltd. + * + * Author: Joshua Yeong <joshua.yeong@starfivetech.com> + */ + +#include <linux/bitfield.h> +#include <linux/cacheflush.h> +#include <linux/cacheinfo.h> +#include <linux/delay.h> +#include <linux/dma-direction.h> +#include <linux/io.h> +#include <linux/of_address.h> +#include <linux/of_platform.h> +#include <linux/processor.h> + +#include <asm/dma-noncoherent.h> + +#define STARFIVE_SL500_CMO_FLUSH_START_ADDR 0x0 +#define STARFIVE_SL500_CMO_FLUSH_END_ADDR 0x8 +#define STARFIVE_SL500_CMO_FLUSH_CTL 0x10 +#define STARFIVE_SL500_CMO_CACHE_ALIGN 0x40 + +#define STARFIVE_SL500_ADDRESS_RANGE_MASK GENMASK(39, 0) +#define STARFIVE_SL500_FLUSH_CTL_MODE_MASK GENMASK(2, 1) +#define STARFIVE_SL500_FLUSH_CTL_ENABLE_MASK BIT(0) + +#define STARFIVE_SL500_FLUSH_CTL_CLEAN_INVALIDATE 0 +#define STARFIVE_SL500_FLUSH_CTL_MAKE_INVALIDATE 1 +#define STARFIVE_SL500_FLUSH_CTL_CLEAN_SHARED 2 + +struct starfive_sl500_cache_priv { + void __iomem *base_addr; +}; + +static struct starfive_sl500_cache_priv starfive_sl500_cache_priv; + +static void starfive_sl500_cmo_flush_complete(void) +{ + ktime_t timeout; + + volatile void __iomem *_ctl = starfive_sl500_cache_priv.base_addr + + STARFIVE_SL500_CMO_FLUSH_CTL; + timeout = ktime_add_ms(ktime_get(), 5000); + + do { + if(!(ioread64(_ctl) & STARFIVE_SL500_FLUSH_CTL_ENABLE_MASK)) + return; + msleep(50); + } while (ktime_before(ktime_get(), timeout)); + + pr_err("StarFive CMO operation timeout\n"); + dump_stack(); +} + +void starfive_sl500_dma_cache_wback(phys_addr_t paddr, unsigned long size) +{ + writeq(FIELD_PREP(STARFIVE_SL500_ADDRESS_RANGE_MASK, paddr), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_START_ADDR); + writeq(FIELD_PREP(STARFIVE_SL500_ADDRESS_RANGE_MASK, paddr + size), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_END_ADDR); + + mb(); + writeq(FIELD_PREP(STARFIVE_SL500_FLUSH_CTL_MODE_MASK, + STARFIVE_SL500_FLUSH_CTL_CLEAN_SHARED), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_CTL); + + starfive_sl500_cmo_flush_complete(); +} + +void starfive_sl500_dma_cache_invalidate(phys_addr_t paddr, unsigned long size) +{ + writeq(FIELD_PREP(STARFIVE_SL500_ADDRESS_RANGE_MASK, paddr), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_START_ADDR); + writeq(FIELD_PREP(STARFIVE_SL500_ADDRESS_RANGE_MASK, paddr + size), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_END_ADDR); + + mb(); + writeq(FIELD_PREP(STARFIVE_SL500_FLUSH_CTL_MODE_MASK, + STARFIVE_SL500_FLUSH_CTL_MAKE_INVALIDATE), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_CTL); + + starfive_sl500_cmo_flush_complete(); +} + +void starfive_sl500_dma_cache_wback_inv(phys_addr_t paddr, unsigned long size) +{ + writeq(FIELD_PREP(STARFIVE_SL500_ADDRESS_RANGE_MASK, paddr), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_START_ADDR); + writeq(FIELD_PREP(STARFIVE_SL500_ADDRESS_RANGE_MASK, paddr + size), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_END_ADDR); + + mb(); + writeq(FIELD_PREP(STARFIVE_SL500_FLUSH_CTL_MODE_MASK, + STARFIVE_SL500_FLUSH_CTL_CLEAN_INVALIDATE), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_CTL); + + starfive_sl500_cmo_flush_complete(); +} + +static const struct riscv_nonstd_cache_ops starfive_sl500_cmo_ops = { + .wback = &starfive_sl500_dma_cache_wback, + .inv = &starfive_sl500_dma_cache_invalidate, + .wback_inv = &starfive_sl500_dma_cache_wback_inv, +}; + +static const struct of_device_id starfive_sl500_cache_ids[] = { + { .compatible = "starfive,starlink-500-cache" }, + { /* sentinel */ } +}; + +static int __init starfive_sl500_cache_init(void) +{ + struct device_node *np; + struct resource res; + int ret; + + np = of_find_matching_node(NULL, starfive_sl500_cache_ids); + if (!of_device_is_available(np)) + return -ENODEV; + + ret = of_address_to_resource(np, 0, &res); + if (ret) + return ret; + + starfive_sl500_cache_priv.base_addr = ioremap(res.start, resource_size(&res)); + if (!starfive_sl500_cache_priv.base_addr) + return -ENOMEM; + + riscv_noncoherent_register_cache_ops(&starfive_sl500_cmo_ops); + + return 0; +} +early_initcall(starfive_sl500_cache_init); -- 2.25.1 _______________________________________________ linux-riscv mailing list linux-riscv@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-riscv
WARNING: multiple messages have this Message-ID (diff)
From: Joshua Yeong <joshua.yeong@starfivetech.com> To: paul.walmsley@sifive.com, palmer@dabbelt.com, aou@eecs.berkeley.edu, geert+renesas@glider.be, joshua.yeong@starfivetech.com, prabhakar.mahadev-lad.rj@bp.renesas.com, conor.dooley@microchip.com, alexghiti@rivosinc.com, evan@rivosinc.com, ajones@ventanamicro.com, heiko@sntech.de, guoren@kernel.org, uwu@icenowy.me, jszhang@kernel.org, conor@kernel.org, robh+dt@kernel.org, krzysztof.kozlowski+dt@linaro.org, conor+dt@kernel.org, leyfoon.tan@starfivetech.com, jeeheng.sia@starfivetech.com Cc: linux-riscv@lists.infradead.org, linux-kernel@vger.kernel.org, devicetree@vger.kernel.org Subject: [PATCH 3/4] cache: Add StarLink-500 cache management for StarFive JH8100 RISC-V core Date: Thu, 14 Mar 2024 14:12:04 +0800 [thread overview] Message-ID: <20240314061205.26143-4-joshua.yeong@starfivetech.com> (raw) In-Reply-To: <20240314061205.26143-1-joshua.yeong@starfivetech.com> Add software workaround for StarFive StarLink-500 on JH8100 SoC for CMO extension instructions. Signed-off-by: Joshua Yeong <joshua.yeong@starfivetech.com> --- drivers/cache/Kconfig | 9 ++ drivers/cache/Makefile | 1 + drivers/cache/starlink500_cache.c | 137 ++++++++++++++++++++++++++++++ 3 files changed, 147 insertions(+) create mode 100644 drivers/cache/starlink500_cache.c diff --git a/drivers/cache/Kconfig b/drivers/cache/Kconfig index 9345ce4976d7..e215379f6a73 100644 --- a/drivers/cache/Kconfig +++ b/drivers/cache/Kconfig @@ -14,4 +14,13 @@ config SIFIVE_CCACHE help Support for the composable cache controller on SiFive platforms. +config STARLINK_500_CACHE + bool "StarLink-500 Cache controller" + depends on RISCV_DMA_NONCOHERENT + depends on ERRATA_STARFIVE + select RISCV_NONSTANDARD_CACHE_OPS + default y + help + Support for the StarLink-500 cache controller on StarFive platforms. + endmenu diff --git a/drivers/cache/Makefile b/drivers/cache/Makefile index 7657cff3bd6c..c515eb5714ea 100644 --- a/drivers/cache/Makefile +++ b/drivers/cache/Makefile @@ -2,3 +2,4 @@ obj-$(CONFIG_AX45MP_L2_CACHE) += ax45mp_cache.o obj-$(CONFIG_SIFIVE_CCACHE) += sifive_ccache.o +obj-$(CONFIG_STARLINK_500_CACHE) += starlink500_cache.o diff --git a/drivers/cache/starlink500_cache.c b/drivers/cache/starlink500_cache.c new file mode 100644 index 000000000000..eaf8303cb086 --- /dev/null +++ b/drivers/cache/starlink500_cache.c @@ -0,0 +1,137 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Non-coherent cache functions for StarFive's StarLink-500 cache controller + * + * Copyright (C) 2024 Shanghai StarFive Technology Co., Ltd. + * + * Author: Joshua Yeong <joshua.yeong@starfivetech.com> + */ + +#include <linux/bitfield.h> +#include <linux/cacheflush.h> +#include <linux/cacheinfo.h> +#include <linux/delay.h> +#include <linux/dma-direction.h> +#include <linux/io.h> +#include <linux/of_address.h> +#include <linux/of_platform.h> +#include <linux/processor.h> + +#include <asm/dma-noncoherent.h> + +#define STARFIVE_SL500_CMO_FLUSH_START_ADDR 0x0 +#define STARFIVE_SL500_CMO_FLUSH_END_ADDR 0x8 +#define STARFIVE_SL500_CMO_FLUSH_CTL 0x10 +#define STARFIVE_SL500_CMO_CACHE_ALIGN 0x40 + +#define STARFIVE_SL500_ADDRESS_RANGE_MASK GENMASK(39, 0) +#define STARFIVE_SL500_FLUSH_CTL_MODE_MASK GENMASK(2, 1) +#define STARFIVE_SL500_FLUSH_CTL_ENABLE_MASK BIT(0) + +#define STARFIVE_SL500_FLUSH_CTL_CLEAN_INVALIDATE 0 +#define STARFIVE_SL500_FLUSH_CTL_MAKE_INVALIDATE 1 +#define STARFIVE_SL500_FLUSH_CTL_CLEAN_SHARED 2 + +struct starfive_sl500_cache_priv { + void __iomem *base_addr; +}; + +static struct starfive_sl500_cache_priv starfive_sl500_cache_priv; + +static void starfive_sl500_cmo_flush_complete(void) +{ + ktime_t timeout; + + volatile void __iomem *_ctl = starfive_sl500_cache_priv.base_addr + + STARFIVE_SL500_CMO_FLUSH_CTL; + timeout = ktime_add_ms(ktime_get(), 5000); + + do { + if(!(ioread64(_ctl) & STARFIVE_SL500_FLUSH_CTL_ENABLE_MASK)) + return; + msleep(50); + } while (ktime_before(ktime_get(), timeout)); + + pr_err("StarFive CMO operation timeout\n"); + dump_stack(); +} + +void starfive_sl500_dma_cache_wback(phys_addr_t paddr, unsigned long size) +{ + writeq(FIELD_PREP(STARFIVE_SL500_ADDRESS_RANGE_MASK, paddr), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_START_ADDR); + writeq(FIELD_PREP(STARFIVE_SL500_ADDRESS_RANGE_MASK, paddr + size), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_END_ADDR); + + mb(); + writeq(FIELD_PREP(STARFIVE_SL500_FLUSH_CTL_MODE_MASK, + STARFIVE_SL500_FLUSH_CTL_CLEAN_SHARED), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_CTL); + + starfive_sl500_cmo_flush_complete(); +} + +void starfive_sl500_dma_cache_invalidate(phys_addr_t paddr, unsigned long size) +{ + writeq(FIELD_PREP(STARFIVE_SL500_ADDRESS_RANGE_MASK, paddr), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_START_ADDR); + writeq(FIELD_PREP(STARFIVE_SL500_ADDRESS_RANGE_MASK, paddr + size), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_END_ADDR); + + mb(); + writeq(FIELD_PREP(STARFIVE_SL500_FLUSH_CTL_MODE_MASK, + STARFIVE_SL500_FLUSH_CTL_MAKE_INVALIDATE), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_CTL); + + starfive_sl500_cmo_flush_complete(); +} + +void starfive_sl500_dma_cache_wback_inv(phys_addr_t paddr, unsigned long size) +{ + writeq(FIELD_PREP(STARFIVE_SL500_ADDRESS_RANGE_MASK, paddr), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_START_ADDR); + writeq(FIELD_PREP(STARFIVE_SL500_ADDRESS_RANGE_MASK, paddr + size), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_END_ADDR); + + mb(); + writeq(FIELD_PREP(STARFIVE_SL500_FLUSH_CTL_MODE_MASK, + STARFIVE_SL500_FLUSH_CTL_CLEAN_INVALIDATE), + starfive_sl500_cache_priv.base_addr + STARFIVE_SL500_CMO_FLUSH_CTL); + + starfive_sl500_cmo_flush_complete(); +} + +static const struct riscv_nonstd_cache_ops starfive_sl500_cmo_ops = { + .wback = &starfive_sl500_dma_cache_wback, + .inv = &starfive_sl500_dma_cache_invalidate, + .wback_inv = &starfive_sl500_dma_cache_wback_inv, +}; + +static const struct of_device_id starfive_sl500_cache_ids[] = { + { .compatible = "starfive,starlink-500-cache" }, + { /* sentinel */ } +}; + +static int __init starfive_sl500_cache_init(void) +{ + struct device_node *np; + struct resource res; + int ret; + + np = of_find_matching_node(NULL, starfive_sl500_cache_ids); + if (!of_device_is_available(np)) + return -ENODEV; + + ret = of_address_to_resource(np, 0, &res); + if (ret) + return ret; + + starfive_sl500_cache_priv.base_addr = ioremap(res.start, resource_size(&res)); + if (!starfive_sl500_cache_priv.base_addr) + return -ENOMEM; + + riscv_noncoherent_register_cache_ops(&starfive_sl500_cmo_ops); + + return 0; +} +early_initcall(starfive_sl500_cache_init); -- 2.25.1
next prev parent reply other threads:[~2024-03-14 6:13 UTC|newest] Thread overview: 28+ messages / expand[flat|nested] mbox.gz Atom feed top 2024-03-14 6:12 [PATCH 0/4] Add StarFive's StarLink-500 Cache Controller Joshua Yeong 2024-03-14 6:12 ` Joshua Yeong 2024-03-14 6:12 ` [PATCH 1/4] riscv: asm: vendorid_list: Add StarFive Technology to vendors list Joshua Yeong 2024-03-14 6:12 ` Joshua Yeong 2024-03-14 6:12 ` [PATCH 2/4] riscv: errata: Add StarFive alternative ports Joshua Yeong 2024-03-14 6:12 ` Joshua Yeong 2024-03-15 23:13 ` Samuel Holland 2024-03-15 23:13 ` Samuel Holland 2024-03-17 15:04 ` Conor Dooley 2024-03-17 15:04 ` Conor Dooley 2024-03-14 6:12 ` Joshua Yeong [this message] 2024-03-14 6:12 ` [PATCH 3/4] cache: Add StarLink-500 cache management for StarFive JH8100 RISC-V core Joshua Yeong 2024-03-15 8:22 ` kernel test robot 2024-03-15 8:22 ` kernel test robot 2024-03-15 23:33 ` Samuel Holland 2024-03-15 23:33 ` Samuel Holland 2024-03-14 6:12 ` [PATCH 4/4] dt-bindings: cache: Add docs for StarFive StarLink-500 cache controller Joshua Yeong 2024-03-14 6:12 ` Joshua Yeong 2024-03-15 16:36 ` Rob Herring 2024-03-15 16:36 ` Rob Herring 2024-03-17 14:58 ` Conor Dooley 2024-03-17 14:58 ` Conor Dooley 2024-03-17 15:01 ` [PATCH 0/4] Add StarFive's StarLink-500 Cache Controller Conor Dooley 2024-03-17 15:01 ` Conor Dooley 2024-03-20 8:08 ` Conor Dooley 2024-03-20 8:08 ` Conor Dooley 2024-03-22 6:16 ` Joshua Yeong 2024-03-22 6:16 ` Joshua Yeong
Reply instructions: You may reply publicly to this message via plain-text email using any one of the following methods: * Save the following mbox file, import it into your mail client, and reply-to-all from there: mbox Avoid top-posting and favor interleaved quoting: https://en.wikipedia.org/wiki/Posting_style#Interleaved_style * Reply using the --to, --cc, and --in-reply-to switches of git-send-email(1): git send-email \ --in-reply-to=20240314061205.26143-4-joshua.yeong@starfivetech.com \ --to=joshua.yeong@starfivetech.com \ --cc=ajones@ventanamicro.com \ --cc=alexghiti@rivosinc.com \ --cc=aou@eecs.berkeley.edu \ --cc=conor+dt@kernel.org \ --cc=conor.dooley@microchip.com \ --cc=conor@kernel.org \ --cc=devicetree@vger.kernel.org \ --cc=evan@rivosinc.com \ --cc=geert+renesas@glider.be \ --cc=guoren@kernel.org \ --cc=heiko@sntech.de \ --cc=jeeheng.sia@starfivetech.com \ --cc=jszhang@kernel.org \ --cc=krzysztof.kozlowski+dt@linaro.org \ --cc=leyfoon.tan@starfivetech.com \ --cc=linux-kernel@vger.kernel.org \ --cc=linux-riscv@lists.infradead.org \ --cc=palmer@dabbelt.com \ --cc=paul.walmsley@sifive.com \ --cc=prabhakar.mahadev-lad.rj@bp.renesas.com \ --cc=robh+dt@kernel.org \ --cc=uwu@icenowy.me \ /path/to/YOUR_REPLY https://kernel.org/pub/software/scm/git/docs/git-send-email.html * If your mail client supports setting the In-Reply-To header via mailto: links, try the mailto: linkBe sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes, see mirroring instructions on how to clone and mirror all data and code used by this external index.