From 4ff40d140e2a2060ef6051800a4a9eab07624f42 Mon Sep 17 00:00:00 2001 From: Yunhao Tian <18373444@buaa.edu.cn> Date: Mon, 25 Nov 2019 20:58:32 +0800 Subject: clk: sunxi-ng: v3s: Fix incorrect number of hw_clks. The hws field of sun8i_v3s_hw_clks has only 74 members. However, the number specified by CLK_NUMBER is 77 (= CLK_I2S0 + 1). This leads to runtime segmentation fault that is not always reproducible. This patch fixes the problem by specifying correct clock number. Signed-off-by: Yunhao Tian <18373444@buaa.edu.cn> [Maxime: Also remove the CLK_NUMBER definition] Signed-off-by: Maxime Ripard --- drivers/clk/sunxi-ng/ccu-sun8i-v3s.c | 4 ++-- drivers/clk/sunxi-ng/ccu-sun8i-v3s.h | 2 -- 2 files changed, 2 insertions(+), 4 deletions(-) (limited to 'drivers') diff --git a/drivers/clk/sunxi-ng/ccu-sun8i-v3s.c b/drivers/clk/sunxi-ng/ccu-sun8i-v3s.c index 5c779eec454b..0e36ca3bf3d5 100644 --- a/drivers/clk/sunxi-ng/ccu-sun8i-v3s.c +++ b/drivers/clk/sunxi-ng/ccu-sun8i-v3s.c @@ -618,7 +618,7 @@ static struct clk_hw_onecell_data sun8i_v3s_hw_clks = { [CLK_MBUS] = &mbus_clk.common.hw, [CLK_MIPI_CSI] = &mipi_csi_clk.common.hw, }, - .num = CLK_NUMBER, + .num = CLK_PLL_DDR1 + 1, }; static struct clk_hw_onecell_data sun8i_v3_hw_clks = { @@ -700,7 +700,7 @@ static struct clk_hw_onecell_data sun8i_v3_hw_clks = { [CLK_MBUS] = &mbus_clk.common.hw, [CLK_MIPI_CSI] = &mipi_csi_clk.common.hw, }, - .num = CLK_NUMBER, + .num = CLK_I2S0 + 1, }; static struct ccu_reset_map sun8i_v3s_ccu_resets[] = { diff --git a/drivers/clk/sunxi-ng/ccu-sun8i-v3s.h b/drivers/clk/sunxi-ng/ccu-sun8i-v3s.h index b0160d305a67..108eeeedcbf7 100644 --- a/drivers/clk/sunxi-ng/ccu-sun8i-v3s.h +++ b/drivers/clk/sunxi-ng/ccu-sun8i-v3s.h @@ -51,6 +51,4 @@ #define CLK_PLL_DDR1 74 -#define CLK_NUMBER (CLK_I2S0 + 1) - #endif /* _CCU_SUN8I_H3_H_ */ -- cgit v1.2.3 From 0766d65e6afaea8b80205a468207de9f18cd7ec8 Mon Sep 17 00:00:00 2001 From: Martin Blumenstingl Date: Sat, 30 Nov 2019 15:58:20 +0100 Subject: soc: amlogic: meson-ee-pwrc: propagate PD provider registration errors of_genpd_add_provider_onecell() can return an error. Propagate the error so the driver registration fails when of_genpd_add_provider_onecell() did not work. Fixes: eef3c2ba0a42a6 ("soc: amlogic: Add support for Everything-Else power domains controller") Signed-off-by: Martin Blumenstingl Signed-off-by: Kevin Hilman --- drivers/soc/amlogic/meson-ee-pwrc.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) (limited to 'drivers') diff --git a/drivers/soc/amlogic/meson-ee-pwrc.c b/drivers/soc/amlogic/meson-ee-pwrc.c index 5823f5b67d16..df734a45da56 100644 --- a/drivers/soc/amlogic/meson-ee-pwrc.c +++ b/drivers/soc/amlogic/meson-ee-pwrc.c @@ -441,9 +441,7 @@ static int meson_ee_pwrc_probe(struct platform_device *pdev) pwrc->xlate.domains[i] = &dom->base; } - of_genpd_add_provider_onecell(pdev->dev.of_node, &pwrc->xlate); - - return 0; + return of_genpd_add_provider_onecell(pdev->dev.of_node, &pwrc->xlate); } static void meson_ee_pwrc_shutdown(struct platform_device *pdev) -- cgit v1.2.3 From c67aafd60d7e323fe74bf45fab60148f84cf9b95 Mon Sep 17 00:00:00 2001 From: Martin Blumenstingl Date: Sat, 30 Nov 2019 15:58:21 +0100 Subject: soc: amlogic: meson-ee-pwrc: propagate errors from pm_genpd_init() pm_genpd_init() can return an error. Propagate the error code to prevent the driver from indicating that it successfully probed while there were errors during pm_genpd_init(). Fixes: eef3c2ba0a42a6 ("soc: amlogic: Add support for Everything-Else power domains controller") Signed-off-by: Martin Blumenstingl Signed-off-by: Kevin Hilman --- drivers/soc/amlogic/meson-ee-pwrc.c | 20 ++++++++++++++------ 1 file changed, 14 insertions(+), 6 deletions(-) (limited to 'drivers') diff --git a/drivers/soc/amlogic/meson-ee-pwrc.c b/drivers/soc/amlogic/meson-ee-pwrc.c index df734a45da56..3f0261d53ad9 100644 --- a/drivers/soc/amlogic/meson-ee-pwrc.c +++ b/drivers/soc/amlogic/meson-ee-pwrc.c @@ -323,6 +323,8 @@ static int meson_ee_pwrc_init_domain(struct platform_device *pdev, struct meson_ee_pwrc *pwrc, struct meson_ee_pwrc_domain *dom) { + int ret; + dom->pwrc = pwrc; dom->num_rstc = dom->desc.reset_names_count; dom->num_clks = dom->desc.clk_names_count; @@ -368,15 +370,21 @@ static int meson_ee_pwrc_init_domain(struct platform_device *pdev, * prepare/enable counters won't be in sync. */ if (dom->num_clks && dom->desc.get_power && !dom->desc.get_power(dom)) { - int ret = clk_bulk_prepare_enable(dom->num_clks, dom->clks); + ret = clk_bulk_prepare_enable(dom->num_clks, dom->clks); if (ret) return ret; - pm_genpd_init(&dom->base, &pm_domain_always_on_gov, false); - } else - pm_genpd_init(&dom->base, NULL, - (dom->desc.get_power ? - dom->desc.get_power(dom) : true)); + ret = pm_genpd_init(&dom->base, &pm_domain_always_on_gov, + false); + if (ret) + return ret; + } else { + ret = pm_genpd_init(&dom->base, NULL, + (dom->desc.get_power ? + dom->desc.get_power(dom) : true)); + if (ret) + return ret; + } return 0; } -- cgit v1.2.3 From 2c81f0f6d3f52ac222a5dc07a6e5c06e1543e88b Mon Sep 17 00:00:00 2001 From: Tony Lindgren Date: Mon, 16 Dec 2019 14:41:53 -0800 Subject: bus: ti-sysc: Fix iterating over clocks Commit d878970f6ce1 ("bus: ti-sysc: Add separate functions for handling clocks") separated handling of optional clocks from the main clocks, but introduced an issue where we do not necessarily allocate a slot for both fck and ick clocks, but still assume fixed slots for enumerating over the clocks. Let's fix the issue by ensuring we always have slots for both fck and ick even if we don't use ick, and don't attempt to enumerate optional clocks if not allocated. In the long run we might want to simplify things a bit by only allocating space only for the optional clocks as we have only few devices with optional clocks. Fixes: d878970f6ce1 ("bus: ti-sysc: Add separate functions for handling clocks") Signed-off-by: Tony Lindgren --- drivers/bus/ti-sysc.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) (limited to 'drivers') diff --git a/drivers/bus/ti-sysc.c b/drivers/bus/ti-sysc.c index f4d1597df0a2..ccb44fe790a7 100644 --- a/drivers/bus/ti-sysc.c +++ b/drivers/bus/ti-sysc.c @@ -343,6 +343,12 @@ static int sysc_get_clocks(struct sysc *ddata) return -EINVAL; } + /* Always add a slot for main clocks fck and ick even if unused */ + if (!nr_fck) + ddata->nr_clocks++; + if (!nr_ick) + ddata->nr_clocks++; + ddata->clocks = devm_kcalloc(ddata->dev, ddata->nr_clocks, sizeof(*ddata->clocks), GFP_KERNEL); @@ -421,7 +427,7 @@ static int sysc_enable_opt_clocks(struct sysc *ddata) struct clk *clock; int i, error; - if (!ddata->clocks) + if (!ddata->clocks || ddata->nr_clocks < SYSC_OPTFCK0 + 1) return 0; for (i = SYSC_OPTFCK0; i < SYSC_MAX_CLOCKS; i++) { @@ -455,7 +461,7 @@ static void sysc_disable_opt_clocks(struct sysc *ddata) struct clk *clock; int i; - if (!ddata->clocks) + if (!ddata->clocks || ddata->nr_clocks < SYSC_OPTFCK0 + 1) return; for (i = SYSC_OPTFCK0; i < SYSC_MAX_CLOCKS; i++) { -- cgit v1.2.3 From 03729cfa0d543bc996bf959e762ec999afc8f3d2 Mon Sep 17 00:00:00 2001 From: Dave Gerlach Date: Wed, 11 Dec 2019 22:03:14 -0600 Subject: soc: ti: wkup_m3_ipc: Fix race condition with rproc_boot Any user of wkup_m3_ipc calls wkup_m3_ipc_get to get a handle and this checks the value of the static variable m3_ipc_state to see if the wkup_m3 is ready. Currently this is populated during probe before rproc_boot has been called, meaning there is a window of time that wkup_m3_ipc_get can return a valid handle but the wkup_m3 itself is not ready, leading to invalid IPC calls to the wkup_m3 and system instability. To avoid this, move the population of the m3_ipc_state variable until after rproc_boot has succeeded to guarantee a valid and usable handle is always returned. Reported-by: Suman Anna Signed-off-by: Dave Gerlach Acked-by: Santosh Shilimkar Signed-off-by: Tony Lindgren --- drivers/soc/ti/wkup_m3_ipc.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers') diff --git a/drivers/soc/ti/wkup_m3_ipc.c b/drivers/soc/ti/wkup_m3_ipc.c index 378369d9364a..e9ece45d7a33 100644 --- a/drivers/soc/ti/wkup_m3_ipc.c +++ b/drivers/soc/ti/wkup_m3_ipc.c @@ -419,6 +419,8 @@ static void wkup_m3_rproc_boot_thread(struct wkup_m3_ipc *m3_ipc) ret = rproc_boot(m3_ipc->rproc); if (ret) dev_err(dev, "rproc_boot failed\n"); + else + m3_ipc_state = m3_ipc; do_exit(0); } @@ -505,8 +507,6 @@ static int wkup_m3_ipc_probe(struct platform_device *pdev) goto err_put_rproc; } - m3_ipc_state = m3_ipc; - return 0; err_put_rproc: -- cgit v1.2.3 From c7b305267eb77fe47498676e9337324c9653494c Mon Sep 17 00:00:00 2001 From: Chen-Yu Tsai Date: Wed, 18 Dec 2019 11:04:31 +0800 Subject: clk: sunxi-ng: r40: Allow setting parent rate for external clock outputs One of the uses of the external clock outputs is to provide a stable 32768 Hz clock signal to WiFi and Bluetooth chips. On the R40, the RTC has an internal RC oscillator that is muxed with the external crystal. Allow setting the parent rate for the external clock outputs so that requests for 32768 Hz get passed to the RTC's clock driver to mux in the external crystal if it isn't already muxed correctly. Fixes: cd030a78f7aa ("clk: sunxi-ng: support R40 SoC") Fixes: 01a7ea763fc4 ("clk: sunxi-ng: r40: Force LOSC parent to RTC LOSC output") Cc: Signed-off-by: Chen-Yu Tsai Signed-off-by: Maxime Ripard --- drivers/clk/sunxi-ng/ccu-sun8i-r40.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'drivers') diff --git a/drivers/clk/sunxi-ng/ccu-sun8i-r40.c b/drivers/clk/sunxi-ng/ccu-sun8i-r40.c index 897490800102..23bfe1d12f21 100644 --- a/drivers/clk/sunxi-ng/ccu-sun8i-r40.c +++ b/drivers/clk/sunxi-ng/ccu-sun8i-r40.c @@ -761,7 +761,8 @@ static struct ccu_mp outa_clk = { .reg = 0x1f0, .features = CCU_FEATURE_FIXED_PREDIV, .hw.init = CLK_HW_INIT_PARENTS("outa", out_parents, - &ccu_mp_ops, 0), + &ccu_mp_ops, + CLK_SET_RATE_PARENT), } }; @@ -779,7 +780,8 @@ static struct ccu_mp outb_clk = { .reg = 0x1f4, .features = CCU_FEATURE_FIXED_PREDIV, .hw.init = CLK_HW_INIT_PARENTS("outb", out_parents, - &ccu_mp_ops, 0), + &ccu_mp_ops, + CLK_SET_RATE_PARENT), } }; -- cgit v1.2.3 From 67f96ff7c8f073648696eab50fd23ded23441067 Mon Sep 17 00:00:00 2001 From: Marek Szyprowski Date: Mon, 16 Dec 2019 14:14:07 +0100 Subject: clk: samsung: exynos5420: Keep top G3D clocks enabled In Exynos542x/5800 SoCs, the G3D leaf clocks are located in the G3D power domain. This is similar to the other hardware modules and their power domains. However there is one thing specific to G3D clocks hierarchy. Unlike other hardware modules, the G3D clocks hierarchy doesn't have any gate clock between the TOP part of the hierarchy and the part located in the power domain and some SoC internal busses are sourced directly from the TOP muxes. The consequence of this design if the fact that the TOP part of the hierarchy has to be enabled permanently to ensure proper operation of the SoC power related components (G3D power domain and Exynos Power Management Unit for system suspend/resume). This patch adds an explicit call to clk_prepare_enable() on the last MUX in the TOP part of G3D clock hierarchy to keep it enabled permanently to ensure that the internal busses get their clock regardless of the main G3D clock enablement status. This fixes following imprecise abort issue observed on Odroid XU3/XU4 after enabling Panfrost driver by commit 1a5a85c56402 "ARM: dts: exynos: Add Mali/GPU node on Exynos5420 and enable it on Odroid XU3/4"): panfrost 11800000.gpu: clock rate = 400000000 panfrost 11800000.gpu: failed to get regulator: -517 panfrost 11800000.gpu: regulator init failed -517 Power domain G3D disable failed ... panfrost 11800000.gpu: clock rate = 400000000 8<--- cut here --- Unhandled fault: imprecise external abort (0x1406) at 0x00000000 pgd = (ptrval) [00000000] *pgd=00000000 Internal error: : 1406 [#1] PREEMPT SMP ARM Modules linked in: CPU: 7 PID: 53 Comm: kworker/7:1 Not tainted 5.4.0-rc8-next-20191119-00032-g56f1001191a6 #6923 Hardware name: SAMSUNG EXYNOS (Flattened Device Tree) Workqueue: events deferred_probe_work_func PC is at panfrost_gpu_soft_reset+0x94/0x110 LR is at ___might_sleep+0x128/0x2dc ... [] (panfrost_gpu_soft_reset) from [] (panfrost_gpu_init+0x10/0x67c) [] (panfrost_gpu_init) from [] (panfrost_device_init+0x158/0x2cc) [] (panfrost_device_init) from [] (panfrost_probe+0x80/0x178) [] (panfrost_probe) from [] (platform_drv_probe+0x48/0x9c) [] (platform_drv_probe) from [] (really_probe+0x1c4/0x474) [] (really_probe) from [] (driver_probe_device+0x78/0x1bc) [] (driver_probe_device) from [] (bus_for_each_drv+0x74/0xb8) [] (bus_for_each_drv) from [] (__device_attach+0xd4/0x16c) [] (__device_attach) from [] (bus_probe_device+0x88/0x90) [] (bus_probe_device) from [] (deferred_probe_work_func+0x4c/0xd0) [] (deferred_probe_work_func) from [] (process_one_work+0x300/0x864) [] (process_one_work) from [] (worker_thread+0x58/0x5a0) [] (worker_thread) from [] (kthread+0x12c/0x160) [] (kthread) from [] (ret_from_fork+0x14/0x20) Exception stack(0xee03dfb0 to 0xee03dff8) ... Code: e594300c e5933020 e3130c01 1a00000f (ebefff50). ---[ end trace badde2b74a65a540 ]--- In the above case, the Panfrost driver disables G3D clocks after failure of getting the needed regulator and return with -EPROVE_DEFER code. This causes G3D power domain disable failure and then, during second probe an imprecise abort is triggered due to undefined power domain state. Fixes: 45f10dabb56b ("clk: samsung: exynos5420: Add SET_RATE_PARENT flag to clocks on G3D path") Fixes: c9f7567aff31 ("clk: samsung: exynos542x: Move G3D subsystem clocks to its sub-CMU") Signed-off-by: Marek Szyprowski Link: https://lkml.kernel.org/r/20191216131407.17225-1-m.szyprowski@samsung.com Acked-by: Krzysztof Kozlowski Acked-by: Chanwoo Choi Acked-by: Sylwester Nawrocki Signed-off-by: Stephen Boyd --- drivers/clk/samsung/clk-exynos5420.c | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'drivers') diff --git a/drivers/clk/samsung/clk-exynos5420.c b/drivers/clk/samsung/clk-exynos5420.c index 3a991ca1ee36..c9e5a1fb6653 100644 --- a/drivers/clk/samsung/clk-exynos5420.c +++ b/drivers/clk/samsung/clk-exynos5420.c @@ -12,6 +12,7 @@ #include #include #include +#include #include "clk.h" #include "clk-cpu.h" @@ -1646,6 +1647,13 @@ static void __init exynos5x_clk_init(struct device_node *np, exynos5x_subcmus); } + /* + * Keep top part of G3D clock path enabled permanently to ensure + * that the internal busses get their clock regardless of the + * main G3D clock enablement status. + */ + clk_prepare_enable(__clk_lookup("mout_sw_aclk_g3d")); + samsung_clk_of_add_provider(np, ctx); } -- cgit v1.2.3 From fc666936f3f0faeebe32b5f0b0fc49a6d0087c6c Mon Sep 17 00:00:00 2001 From: Dmitry Osipenko Date: Tue, 10 Dec 2019 05:05:12 +0300 Subject: clk: tegra: Fix double-free in tegra_clk_init() It's unlikely to happen in practice ever, but makes static checkers happy. Fixes: 535f296d47de ("clk: tegra: Add suspend and resume support on Tegra210") Reported-by: Stephen Boyd Signed-off-by: Dmitry Osipenko Link: https://lkml.kernel.org/r/20191210020512.6088-1-digetx@gmail.com Acked-by: Thierry Reding Signed-off-by: Stephen Boyd --- drivers/clk/tegra/clk.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'drivers') diff --git a/drivers/clk/tegra/clk.c b/drivers/clk/tegra/clk.c index e6bd6d1ea012..f6cdce441cf7 100644 --- a/drivers/clk/tegra/clk.c +++ b/drivers/clk/tegra/clk.c @@ -231,8 +231,10 @@ struct clk ** __init tegra_clk_init(void __iomem *regs, int num, int banks) periph_banks = banks; clks = kcalloc(num, sizeof(struct clk *), GFP_KERNEL); - if (!clks) + if (!clks) { kfree(periph_clk_enb_refcnt); + return NULL; + } clk_num = num; -- cgit v1.2.3 From d92b54570d24d017d2630e314b525ed792f5aa6c Mon Sep 17 00:00:00 2001 From: Arvind Sankar Date: Tue, 24 Dec 2019 14:29:07 +0100 Subject: efi/earlycon: Fix write-combine mapping on x86 On x86, until PAT is initialized, WC translates into UC-. Since we calculate and store pgprot_writecombine(PAGE_KERNEL) when earlycon is initialized, this means we actually use UC- mappings instead of WC mappings, which makes scrolling very slow. Instead store a boolean flag to indicate whether we want to use writeback or write-combine mappings, and recalculate the actual pgprot_t we need on every mapping. Once PAT is initialized, we will start using write-combine mappings, which speeds up the scrolling considerably. Signed-off-by: Arvind Sankar Signed-off-by: Ard Biesheuvel Cc: Hans de Goede Cc: Linus Torvalds Cc: Peter Zijlstra Cc: Thomas Gleixner Cc: linux-efi@vger.kernel.org Fixes: 69c1f396f25b ("efi/x86: Convert x86 EFI earlyprintk into generic earlycon implementation") Link: https://lkml.kernel.org/r/20191224132909.102540-2-ardb@kernel.org Signed-off-by: Ingo Molnar --- drivers/firmware/efi/earlycon.c | 16 +++++++--------- 1 file changed, 7 insertions(+), 9 deletions(-) (limited to 'drivers') diff --git a/drivers/firmware/efi/earlycon.c b/drivers/firmware/efi/earlycon.c index d4077db6dc97..5d4f84781aa0 100644 --- a/drivers/firmware/efi/earlycon.c +++ b/drivers/firmware/efi/earlycon.c @@ -17,7 +17,7 @@ static const struct console *earlycon_console __initdata; static const struct font_desc *font; static u32 efi_x, efi_y; static u64 fb_base; -static pgprot_t fb_prot; +static bool fb_wb; static void *efi_fb; /* @@ -33,10 +33,8 @@ static int __init efi_earlycon_remap_fb(void) if (!earlycon_console || !(earlycon_console->flags & CON_ENABLED)) return 0; - if (pgprot_val(fb_prot) == pgprot_val(PAGE_KERNEL)) - efi_fb = memremap(fb_base, screen_info.lfb_size, MEMREMAP_WB); - else - efi_fb = memremap(fb_base, screen_info.lfb_size, MEMREMAP_WC); + efi_fb = memremap(fb_base, screen_info.lfb_size, + fb_wb ? MEMREMAP_WB : MEMREMAP_WC); return efi_fb ? 0 : -ENOMEM; } @@ -53,9 +51,12 @@ late_initcall(efi_earlycon_unmap_fb); static __ref void *efi_earlycon_map(unsigned long start, unsigned long len) { + pgprot_t fb_prot; + if (efi_fb) return efi_fb + start; + fb_prot = fb_wb ? PAGE_KERNEL : pgprot_writecombine(PAGE_KERNEL); return early_memremap_prot(fb_base + start, len, pgprot_val(fb_prot)); } @@ -215,10 +216,7 @@ static int __init efi_earlycon_setup(struct earlycon_device *device, if (screen_info.capabilities & VIDEO_CAPABILITY_64BIT_BASE) fb_base |= (u64)screen_info.ext_lfb_base << 32; - if (opt && !strcmp(opt, "ram")) - fb_prot = PAGE_KERNEL; - else - fb_prot = pgprot_writecombine(PAGE_KERNEL); + fb_wb = opt && !strcmp(opt, "ram"); si = &screen_info; xres = si->lfb_width; -- cgit v1.2.3 From 818c7ce724770fbcdcd43725c81f2b3535f82b76 Mon Sep 17 00:00:00 2001 From: Hans de Goede Date: Tue, 24 Dec 2019 14:29:08 +0100 Subject: efi/libstub/random: Initialize pointer variables to zero for mixed mode Commit: 0d95981438c3 ("x86: efi/random: Invoke EFI_RNG_PROTOCOL to seed the UEFI RNG table") causes the drivers/efi/libstub/random.c code to get used on x86 for the first time. But this code was not written with EFI mixed mode in mind (running a 64 bit kernel on 32 bit EFI firmware), this causes the kernel to crash during early boot when running in mixed mode. The problem is that in mixed mode pointers are 64 bit, but when running on a 32 bit firmware, EFI calls which return a pointer value by reference only fill the lower 32 bits of the passed pointer, leaving the upper 32 bits uninitialized which leads to crashes. This commit fixes this by initializing pointers which are passed by reference to EFI calls to NULL before passing them, so that the upper 32 bits are initialized to 0. Signed-off-by: Hans de Goede Signed-off-by: Ard Biesheuvel Cc: Arvind Sankar Cc: Linus Torvalds Cc: Peter Zijlstra Cc: Thomas Gleixner Cc: linux-efi@vger.kernel.org Fixes: 0d95981438c3 ("x86: efi/random: Invoke EFI_RNG_PROTOCOL to seed the UEFI RNG table") Link: https://lkml.kernel.org/r/20191224132909.102540-3-ardb@kernel.org Signed-off-by: Ingo Molnar --- drivers/firmware/efi/libstub/random.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'drivers') diff --git a/drivers/firmware/efi/libstub/random.c b/drivers/firmware/efi/libstub/random.c index 35edd7cfb6a1..97378cf96a2e 100644 --- a/drivers/firmware/efi/libstub/random.c +++ b/drivers/firmware/efi/libstub/random.c @@ -33,7 +33,7 @@ efi_status_t efi_get_random_bytes(efi_system_table_t *sys_table_arg, { efi_guid_t rng_proto = EFI_RNG_PROTOCOL_GUID; efi_status_t status; - struct efi_rng_protocol *rng; + struct efi_rng_protocol *rng = NULL; status = efi_call_early(locate_protocol, &rng_proto, NULL, (void **)&rng); @@ -162,8 +162,8 @@ efi_status_t efi_random_get_seed(efi_system_table_t *sys_table_arg) efi_guid_t rng_proto = EFI_RNG_PROTOCOL_GUID; efi_guid_t rng_algo_raw = EFI_RNG_ALGORITHM_RAW; efi_guid_t rng_table_guid = LINUX_EFI_RANDOM_SEED_TABLE_GUID; - struct efi_rng_protocol *rng; - struct linux_efi_random_seed *seed; + struct efi_rng_protocol *rng = NULL; + struct linux_efi_random_seed *seed = NULL; efi_status_t status; status = efi_call_early(locate_protocol, &rng_proto, NULL, -- cgit v1.2.3 From 12ead77432f2ce32dea797742316d15c5800cb32 Mon Sep 17 00:00:00 2001 From: Guenter Roeck Date: Wed, 25 Dec 2019 08:34:29 -0800 Subject: clk: Don't try to enable critical clocks if prepare failed The following traceback is seen if a critical clock fails to prepare. bcm2835-clk 3f101000.cprman: plld: couldn't lock PLL ------------[ cut here ]------------ Enabling unprepared plld_per WARNING: CPU: 1 PID: 1 at drivers/clk/clk.c:1014 clk_core_enable+0xcc/0x2c0 ... Call trace: clk_core_enable+0xcc/0x2c0 __clk_register+0x5c4/0x788 devm_clk_hw_register+0x4c/0xb0 bcm2835_register_pll_divider+0xc0/0x150 bcm2835_clk_probe+0x134/0x1e8 platform_drv_probe+0x50/0xa0 really_probe+0xd4/0x308 driver_probe_device+0x54/0xe8 device_driver_attach+0x6c/0x78 __driver_attach+0x54/0xd8 ... Check return values from clk_core_prepare() and clk_core_enable() and bail out if any of those functions returns an error. Cc: Jerome Brunet Fixes: 99652a469df1 ("clk: migrate the count of orphaned clocks at init") Signed-off-by: Guenter Roeck Link: https://lkml.kernel.org/r/20191225163429.29694-1-linux@roeck-us.net Signed-off-by: Stephen Boyd --- drivers/clk/clk.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) (limited to 'drivers') diff --git a/drivers/clk/clk.c b/drivers/clk/clk.c index 6a11239ccde3..772258de2d1f 100644 --- a/drivers/clk/clk.c +++ b/drivers/clk/clk.c @@ -3426,11 +3426,17 @@ static int __clk_core_init(struct clk_core *core) if (core->flags & CLK_IS_CRITICAL) { unsigned long flags; - clk_core_prepare(core); + ret = clk_core_prepare(core); + if (ret) + goto out; flags = clk_enable_lock(); - clk_core_enable(core); + ret = clk_core_enable(core); clk_enable_unlock(flags); + if (ret) { + clk_core_unprepare(core); + goto out; + } } clk_core_reparent_orphans_nolock(); -- cgit v1.2.3 From 47d64fef1f3ffbdf960d3330b9865fc9f12fdf84 Mon Sep 17 00:00:00 2001 From: Samuel Holland Date: Sat, 28 Dec 2019 20:59:20 -0600 Subject: clk: sunxi-ng: sun8i-r: Fix divider on APB0 clock According to the BSP source code, the APB0 clock on the H3 and H5 has a normal M divider, not a power-of-two divider. This matches the hardware in the A83T (as described in both the BSP source code and the manual). Since the A83T and H3/A64 clocks are actually the same, we can merge the definitions. Signed-off-by: Samuel Holland Signed-off-by: Maxime Ripard --- drivers/clk/sunxi-ng/ccu-sun8i-r.c | 21 +++------------------ 1 file changed, 3 insertions(+), 18 deletions(-) (limited to 'drivers') diff --git a/drivers/clk/sunxi-ng/ccu-sun8i-r.c b/drivers/clk/sunxi-ng/ccu-sun8i-r.c index 4646fdc61053..4c8c491b87c2 100644 --- a/drivers/clk/sunxi-ng/ccu-sun8i-r.c +++ b/drivers/clk/sunxi-ng/ccu-sun8i-r.c @@ -51,19 +51,7 @@ static struct ccu_div ar100_clk = { static CLK_FIXED_FACTOR_HW(ahb0_clk, "ahb0", &ar100_clk.common.hw, 1, 1, 0); -static struct ccu_div apb0_clk = { - .div = _SUNXI_CCU_DIV_FLAGS(0, 2, CLK_DIVIDER_POWER_OF_TWO), - - .common = { - .reg = 0x0c, - .hw.init = CLK_HW_INIT_HW("apb0", - &ahb0_clk.hw, - &ccu_div_ops, - 0), - }, -}; - -static SUNXI_CCU_M(a83t_apb0_clk, "apb0", "ahb0", 0x0c, 0, 2, 0); +static SUNXI_CCU_M(apb0_clk, "apb0", "ahb0", 0x0c, 0, 2, 0); /* * Define the parent as an array that can be reused to save space @@ -127,7 +115,7 @@ static struct ccu_mp a83t_ir_clk = { static struct ccu_common *sun8i_a83t_r_ccu_clks[] = { &ar100_clk.common, - &a83t_apb0_clk.common, + &apb0_clk.common, &apb0_pio_clk.common, &apb0_ir_clk.common, &apb0_timer_clk.common, @@ -167,7 +155,7 @@ static struct clk_hw_onecell_data sun8i_a83t_r_hw_clks = { .hws = { [CLK_AR100] = &ar100_clk.common.hw, [CLK_AHB0] = &ahb0_clk.hw, - [CLK_APB0] = &a83t_apb0_clk.common.hw, + [CLK_APB0] = &apb0_clk.common.hw, [CLK_APB0_PIO] = &apb0_pio_clk.common.hw, [CLK_APB0_IR] = &apb0_ir_clk.common.hw, [CLK_APB0_TIMER] = &apb0_timer_clk.common.hw, @@ -282,9 +270,6 @@ static void __init sunxi_r_ccu_init(struct device_node *node, static void __init sun8i_a83t_r_ccu_setup(struct device_node *node) { - /* Fix apb0 bus gate parents here */ - apb0_gate_parent[0] = &a83t_apb0_clk.common.hw; - sunxi_r_ccu_init(node, &sun8i_a83t_r_ccu_desc); } CLK_OF_DECLARE(sun8i_a83t_r_ccu, "allwinner,sun8i-a83t-r-ccu", -- cgit v1.2.3 From 675a6d467b432c8b4a0703ded02e6ef068e0c7e9 Mon Sep 17 00:00:00 2001 From: Samuel Holland Date: Sat, 28 Dec 2019 20:59:21 -0600 Subject: clk: sunxi-ng: h6-r: Simplify R_APB1 clock definition Like the APB0 clock on previous chips, this is a simple single-parent clock with an M divider. Use the equivalent helper macro instead of writing out the whole clock description manually. Signed-off-by: Samuel Holland Signed-off-by: Maxime Ripard --- drivers/clk/sunxi-ng/ccu-sun50i-h6-r.c | 12 +----------- 1 file changed, 1 insertion(+), 11 deletions(-) (limited to 'drivers') diff --git a/drivers/clk/sunxi-ng/ccu-sun50i-h6-r.c b/drivers/clk/sunxi-ng/ccu-sun50i-h6-r.c index 45a1ed3fe674..df9c01831699 100644 --- a/drivers/clk/sunxi-ng/ccu-sun50i-h6-r.c +++ b/drivers/clk/sunxi-ng/ccu-sun50i-h6-r.c @@ -51,17 +51,7 @@ static struct ccu_div ar100_clk = { static CLK_FIXED_FACTOR_HW(r_ahb_clk, "r-ahb", &ar100_clk.common.hw, 1, 1, 0); -static struct ccu_div r_apb1_clk = { - .div = _SUNXI_CCU_DIV(0, 2), - - .common = { - .reg = 0x00c, - .hw.init = CLK_HW_INIT("r-apb1", - "r-ahb", - &ccu_div_ops, - 0), - }, -}; +static SUNXI_CCU_M(r_apb1_clk, "r-apb1", "r-ahb", 0x00c, 0, 2, 0); static struct ccu_div r_apb2_clk = { .div = _SUNXI_CCU_DIV_FLAGS(8, 2, CLK_DIVIDER_POWER_OF_TWO), -- cgit v1.2.3 From 0c545240aebc2ccb8f661dc54283a14d64659804 Mon Sep 17 00:00:00 2001 From: Samuel Holland Date: Sat, 28 Dec 2019 20:59:22 -0600 Subject: clk: sunxi-ng: h6-r: Fix AR100/R_APB2 parent order According to the BSP source code, both the AR100 and R_APB2 clocks have PLL_PERIPH0 as mux index 3, not 2 as it was on previous chips. The pre- divider used for PLL_PERIPH0 should be changed to index 3 to match. This was verified by running a rough benchmark on the AR100 with various clock settings: | mux | pre-divider | iterations/second | clock source | |=====|=============|===================|==============| | 0 | 0 | 19033 (stable) | osc24M | | 2 | 5 | 11466 (unstable) | iosc/osc16M | | 2 | 17 | 11422 (unstable) | iosc/osc16M | | 3 | 5 | 85338 (stable) | pll-periph0 | | 3 | 17 | 27167 (stable) | pll-periph0 | The relative performance numbers all match up (with pll-periph0 running at its default 600MHz). Signed-off-by: Samuel Holland Signed-off-by: Maxime Ripard --- drivers/clk/sunxi-ng/ccu-sun50i-h6-r.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers') diff --git a/drivers/clk/sunxi-ng/ccu-sun50i-h6-r.c b/drivers/clk/sunxi-ng/ccu-sun50i-h6-r.c index df9c01831699..50f8d1bc7046 100644 --- a/drivers/clk/sunxi-ng/ccu-sun50i-h6-r.c +++ b/drivers/clk/sunxi-ng/ccu-sun50i-h6-r.c @@ -23,9 +23,9 @@ */ static const char * const ar100_r_apb2_parents[] = { "osc24M", "osc32k", - "pll-periph0", "iosc" }; + "iosc", "pll-periph0" }; static const struct ccu_mux_var_prediv ar100_r_apb2_predivs[] = { - { .index = 2, .shift = 0, .width = 5 }, + { .index = 3, .shift = 0, .width = 5 }, }; static struct ccu_div ar100_clk = { -- cgit v1.2.3 From 5a769f6ff439cedc547395a6dc78faa26108f741 Mon Sep 17 00:00:00 2001 From: Sumit Garg Date: Mon, 30 Dec 2019 18:52:40 +0530 Subject: optee: Fix multi page dynamic shm pool alloc optee_shm_register() expected pages to be passed as an array of page pointers rather than as an array of contiguous pages. So fix that via correctly passing pages as per expectation. Fixes: a249dd200d03 ("tee: optee: Fix dynamic shm pool allocations") Reported-by: Vincent Cao Signed-off-by: Sumit Garg Tested-by: Vincent Cao Signed-off-by: Jens Wiklander --- drivers/tee/optee/shm_pool.c | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) (limited to 'drivers') diff --git a/drivers/tee/optee/shm_pool.c b/drivers/tee/optee/shm_pool.c index 0332a5301d61..d767eebf30bd 100644 --- a/drivers/tee/optee/shm_pool.c +++ b/drivers/tee/optee/shm_pool.c @@ -28,9 +28,22 @@ static int pool_op_alloc(struct tee_shm_pool_mgr *poolm, shm->size = PAGE_SIZE << order; if (shm->flags & TEE_SHM_DMA_BUF) { + unsigned int nr_pages = 1 << order, i; + struct page **pages; + + pages = kcalloc(nr_pages, sizeof(pages), GFP_KERNEL); + if (!pages) + return -ENOMEM; + + for (i = 0; i < nr_pages; i++) { + pages[i] = page; + page++; + } + shm->flags |= TEE_SHM_REGISTER; - rc = optee_shm_register(shm->ctx, shm, &page, 1 << order, + rc = optee_shm_register(shm->ctx, shm, pages, nr_pages, (unsigned long)shm->kaddr); + kfree(pages); } return rc; -- cgit v1.2.3 From 5e82548e26ef62e257dc2ff37c11acb5eb72728e Mon Sep 17 00:00:00 2001 From: Georgi Djakov Date: Tue, 26 Nov 2019 17:34:37 +0200 Subject: clk: qcom: gcc-sdm845: Add missing flag to votable GDSCs On sdm845 devices, during boot we see the following warnings (unless we have added 'pd_ignore_unused' to the kernel command line): hlos1_vote_mmnoc_mmu_tbu_sf_gdsc status stuck at 'on' hlos1_vote_mmnoc_mmu_tbu_hf1_gdsc status stuck at 'on' hlos1_vote_mmnoc_mmu_tbu_hf0_gdsc status stuck at 'on' hlos1_vote_aggre_noc_mmu_tbu2_gdsc status stuck at 'on' hlos1_vote_aggre_noc_mmu_tbu1_gdsc status stuck at 'on' hlos1_vote_aggre_noc_mmu_pcie_tbu_gdsc status stuck at 'on' hlos1_vote_aggre_noc_mmu_audio_tbu_gdsc status stuck at 'on' As the name of these GDSCs suggests, they are "votable" and in downstream DT, they all have the property "qcom,no-status-check-on-disable", which means that we should not poll the status bit when we disable them. Luckily the VOTABLE flag already exists and it does exactly what we need, so let's make use of it to make the warnings disappear. Fixes: 06391eddb60a ("clk: qcom: Add Global Clock controller (GCC) driver for SDM845") Reported-by: Rob Clark Signed-off-by: Georgi Djakov Link: https://lkml.kernel.org/r/20191126153437.11808-1-georgi.djakov@linaro.org Tested-by: Rob Clark Signed-off-by: Stephen Boyd --- drivers/clk/qcom/gcc-sdm845.c | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'drivers') diff --git a/drivers/clk/qcom/gcc-sdm845.c b/drivers/clk/qcom/gcc-sdm845.c index f7b370f3acef..f6ce888098be 100644 --- a/drivers/clk/qcom/gcc-sdm845.c +++ b/drivers/clk/qcom/gcc-sdm845.c @@ -3255,6 +3255,7 @@ static struct gdsc hlos1_vote_aggre_noc_mmu_audio_tbu_gdsc = { .name = "hlos1_vote_aggre_noc_mmu_audio_tbu_gdsc", }, .pwrsts = PWRSTS_OFF_ON, + .flags = VOTABLE, }; static struct gdsc hlos1_vote_aggre_noc_mmu_pcie_tbu_gdsc = { @@ -3263,6 +3264,7 @@ static struct gdsc hlos1_vote_aggre_noc_mmu_pcie_tbu_gdsc = { .name = "hlos1_vote_aggre_noc_mmu_pcie_tbu_gdsc", }, .pwrsts = PWRSTS_OFF_ON, + .flags = VOTABLE, }; static struct gdsc hlos1_vote_aggre_noc_mmu_tbu1_gdsc = { @@ -3271,6 +3273,7 @@ static struct gdsc hlos1_vote_aggre_noc_mmu_tbu1_gdsc = { .name = "hlos1_vote_aggre_noc_mmu_tbu1_gdsc", }, .pwrsts = PWRSTS_OFF_ON, + .flags = VOTABLE, }; static struct gdsc hlos1_vote_aggre_noc_mmu_tbu2_gdsc = { @@ -3279,6 +3282,7 @@ static struct gdsc hlos1_vote_aggre_noc_mmu_tbu2_gdsc = { .name = "hlos1_vote_aggre_noc_mmu_tbu2_gdsc", }, .pwrsts = PWRSTS_OFF_ON, + .flags = VOTABLE, }; static struct gdsc hlos1_vote_mmnoc_mmu_tbu_hf0_gdsc = { @@ -3287,6 +3291,7 @@ static struct gdsc hlos1_vote_mmnoc_mmu_tbu_hf0_gdsc = { .name = "hlos1_vote_mmnoc_mmu_tbu_hf0_gdsc", }, .pwrsts = PWRSTS_OFF_ON, + .flags = VOTABLE, }; static struct gdsc hlos1_vote_mmnoc_mmu_tbu_hf1_gdsc = { @@ -3295,6 +3300,7 @@ static struct gdsc hlos1_vote_mmnoc_mmu_tbu_hf1_gdsc = { .name = "hlos1_vote_mmnoc_mmu_tbu_hf1_gdsc", }, .pwrsts = PWRSTS_OFF_ON, + .flags = VOTABLE, }; static struct gdsc hlos1_vote_mmnoc_mmu_tbu_sf_gdsc = { @@ -3303,6 +3309,7 @@ static struct gdsc hlos1_vote_mmnoc_mmu_tbu_sf_gdsc = { .name = "hlos1_vote_mmnoc_mmu_tbu_sf_gdsc", }, .pwrsts = PWRSTS_OFF_ON, + .flags = VOTABLE, }; static struct clk_regmap *gcc_sdm845_clocks[] = { -- cgit v1.2.3 From ad931a2d56e35ff69902f5d7299775e80c35c322 Mon Sep 17 00:00:00 2001 From: Peter Ujfalusi Date: Thu, 14 Nov 2019 12:17:18 +0200 Subject: clk: ti: dra7-atl: Remove pm_runtime_irq_safe() This is not needed for anything, and prevents proper PM transitions for parent devices which is bad in case of ti-sysc; this effectively kills PM completely. Thus, remove the flag. Suggested-by: Tony Lindgren Signed-off-by: Peter Ujfalusi Link: https://lkml.kernel.org/r/20191114101718.20619-1-peter.ujfalusi@ti.com Reviewed-by: Tony Lindgren Signed-off-by: Stephen Boyd --- drivers/clk/ti/clk-dra7-atl.c | 1 - 1 file changed, 1 deletion(-) (limited to 'drivers') diff --git a/drivers/clk/ti/clk-dra7-atl.c b/drivers/clk/ti/clk-dra7-atl.c index f65e16c4f3c4..8d4c08b034bd 100644 --- a/drivers/clk/ti/clk-dra7-atl.c +++ b/drivers/clk/ti/clk-dra7-atl.c @@ -233,7 +233,6 @@ static int of_dra7_atl_clk_probe(struct platform_device *pdev) cinfo->iobase = of_iomap(node, 0); cinfo->dev = &pdev->dev; pm_runtime_enable(cinfo->dev); - pm_runtime_irq_safe(cinfo->dev); pm_runtime_get_sync(cinfo->dev); atl_write(cinfo, DRA7_ATL_PCLKMUX_REG(0), DRA7_ATL_PCLKMUX); -- cgit v1.2.3 From 8bea5ac0fbc5b2103f8779ddff216122e3c2e1ad Mon Sep 17 00:00:00 2001 From: Lubomir Rintel Date: Wed, 18 Dec 2019 20:04:54 +0100 Subject: clk: mmp2: Fix the order of timer mux parents Determined empirically, no documentation is available. The OLPC XO-1.75 laptop used parent 1, that one being VCTCXO/4 (65MHz), but thought it's a VCTCXO/2 (130MHz). The mmp2 timer driver, not knowing what is going on, ended up just dividing the rate as of commit f36797ee4380 ("ARM: mmp/mmp2: dt: enable the clock")' Link: https://lore.kernel.org/r/20191218190454.420358-3-lkundrak@v3.sk Signed-off-by: Lubomir Rintel Acked-by: Stephen Boyd Signed-off-by: Olof Johansson --- drivers/clk/mmp/clk-of-mmp2.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers') diff --git a/drivers/clk/mmp/clk-of-mmp2.c b/drivers/clk/mmp/clk-of-mmp2.c index a60a1be937ad..b4a95cbbda98 100644 --- a/drivers/clk/mmp/clk-of-mmp2.c +++ b/drivers/clk/mmp/clk-of-mmp2.c @@ -134,7 +134,7 @@ static DEFINE_SPINLOCK(ssp3_lock); static const char *ssp_parent_names[] = {"vctcxo_4", "vctcxo_2", "vctcxo", "pll1_16"}; static DEFINE_SPINLOCK(timer_lock); -static const char *timer_parent_names[] = {"clk32", "vctcxo_2", "vctcxo_4", "vctcxo"}; +static const char *timer_parent_names[] = {"clk32", "vctcxo_4", "vctcxo_2", "vctcxo"}; static DEFINE_SPINLOCK(reset_lock); -- cgit v1.2.3 From cb1eeb75cf3dd84ced81333967200583993dfd73 Mon Sep 17 00:00:00 2001 From: Arnd Bergmann Date: Tue, 7 Jan 2020 21:08:58 +0100 Subject: crypto: hisilicon/sec2 - Use atomics instead of __sync The use of __sync functions for atomic memory access is not supported in the kernel, and can result in a link error depending on configuration: ERROR: "__tsan_atomic32_compare_exchange_strong" [drivers/crypto/hisilicon/sec2/hisi_sec2.ko] undefined! ERROR: "__tsan_atomic64_fetch_add" [drivers/crypto/hisilicon/sec2/hisi_sec2.ko] undefined! Use the kernel's own atomic interfaces instead. This way the debugfs interface actually reads the counter atomically. Fixes: 416d82204df4 ("crypto: hisilicon - add HiSilicon SEC V2 driver") Signed-off-by: Arnd Bergmann Signed-off-by: Herbert Xu --- drivers/crypto/hisilicon/sec2/sec.h | 6 +++--- drivers/crypto/hisilicon/sec2/sec_crypto.c | 12 ++++++------ drivers/crypto/hisilicon/sec2/sec_main.c | 14 ++++++++++++-- 3 files changed, 21 insertions(+), 11 deletions(-) (limited to 'drivers') diff --git a/drivers/crypto/hisilicon/sec2/sec.h b/drivers/crypto/hisilicon/sec2/sec.h index 26754d0570ba..b846d73d9a85 100644 --- a/drivers/crypto/hisilicon/sec2/sec.h +++ b/drivers/crypto/hisilicon/sec2/sec.h @@ -40,7 +40,7 @@ struct sec_req { int req_id; /* Status of the SEC request */ - int fake_busy; + atomic_t fake_busy; }; /** @@ -132,8 +132,8 @@ struct sec_debug_file { }; struct sec_dfx { - u64 send_cnt; - u64 recv_cnt; + atomic64_t send_cnt; + atomic64_t recv_cnt; }; struct sec_debug { diff --git a/drivers/crypto/hisilicon/sec2/sec_crypto.c b/drivers/crypto/hisilicon/sec2/sec_crypto.c index 62b04e19067c..0a5391fff485 100644 --- a/drivers/crypto/hisilicon/sec2/sec_crypto.c +++ b/drivers/crypto/hisilicon/sec2/sec_crypto.c @@ -120,7 +120,7 @@ static void sec_req_cb(struct hisi_qp *qp, void *resp) return; } - __sync_add_and_fetch(&req->ctx->sec->debug.dfx.recv_cnt, 1); + atomic64_inc(&req->ctx->sec->debug.dfx.recv_cnt); req->ctx->req_op->buf_unmap(req->ctx, req); @@ -135,13 +135,13 @@ static int sec_bd_send(struct sec_ctx *ctx, struct sec_req *req) mutex_lock(&qp_ctx->req_lock); ret = hisi_qp_send(qp_ctx->qp, &req->sec_sqe); mutex_unlock(&qp_ctx->req_lock); - __sync_add_and_fetch(&ctx->sec->debug.dfx.send_cnt, 1); + atomic64_inc(&ctx->sec->debug.dfx.send_cnt); if (ret == -EBUSY) return -ENOBUFS; if (!ret) { - if (req->fake_busy) + if (atomic_read(&req->fake_busy)) ret = -EBUSY; else ret = -EINPROGRESS; @@ -641,7 +641,7 @@ static void sec_skcipher_callback(struct sec_ctx *ctx, struct sec_req *req) if (ctx->c_ctx.c_mode == SEC_CMODE_CBC && req->c_req.encrypt) sec_update_iv(req); - if (__sync_bool_compare_and_swap(&req->fake_busy, 1, 0)) + if (atomic_cmpxchg(&req->fake_busy, 1, 0) != 1) sk_req->base.complete(&sk_req->base, -EINPROGRESS); sk_req->base.complete(&sk_req->base, req->err_type); @@ -672,9 +672,9 @@ static int sec_request_init(struct sec_ctx *ctx, struct sec_req *req) } if (ctx->fake_req_limit <= atomic_inc_return(&qp_ctx->pending_reqs)) - req->fake_busy = 1; + atomic_set(&req->fake_busy, 1); else - req->fake_busy = 0; + atomic_set(&req->fake_busy, 0); ret = ctx->req_op->get_res(ctx, req); if (ret) { diff --git a/drivers/crypto/hisilicon/sec2/sec_main.c b/drivers/crypto/hisilicon/sec2/sec_main.c index 74f0654028c9..ab742dfbab99 100644 --- a/drivers/crypto/hisilicon/sec2/sec_main.c +++ b/drivers/crypto/hisilicon/sec2/sec_main.c @@ -608,6 +608,14 @@ static const struct file_operations sec_dbg_fops = { .write = sec_debug_write, }; +static int debugfs_atomic64_t_get(void *data, u64 *val) +{ + *val = atomic64_read((atomic64_t *)data); + return 0; +} +DEFINE_DEBUGFS_ATTRIBUTE(fops_atomic64_t_ro, debugfs_atomic64_t_get, NULL, + "%lld\n"); + static int sec_core_debug_init(struct sec_dev *sec) { struct hisi_qm *qm = &sec->qm; @@ -628,9 +636,11 @@ static int sec_core_debug_init(struct sec_dev *sec) debugfs_create_regset32("regs", 0444, tmp_d, regset); - debugfs_create_u64("send_cnt", 0444, tmp_d, &dfx->send_cnt); + debugfs_create_file("send_cnt", 0444, tmp_d, &dfx->send_cnt, + &fops_atomic64_t_ro); - debugfs_create_u64("recv_cnt", 0444, tmp_d, &dfx->recv_cnt); + debugfs_create_file("recv_cnt", 0444, tmp_d, &dfx->recv_cnt, + &fops_atomic64_t_ro); return 0; } -- cgit v1.2.3 From bc8a76a152c5f9ef3b48104154a65a68a8b76946 Mon Sep 17 00:00:00 2001 From: Akeem G Abodunrin Date: Wed, 8 Jan 2020 09:25:00 -0800 Subject: drm/i915/gen9: Clear residual context state on context switch Intel ID: PSIRT-TA-201910-001 CVEID: CVE-2019-14615 Intel GPU Hardware prior to Gen11 does not clear EU state during a context switch. This can result in information leakage between contexts. For Gen8 and Gen9, hardware provides a mechanism for fast cleardown of the EU state, by issuing a PIPE_CONTROL with bit 27 set. We can use this in a context batch buffer to explicitly cleardown the state on every context switch. As this workaround is already in place for gen8, we can borrow the code verbatim for Gen9. Signed-off-by: Mika Kuoppala Signed-off-by: Akeem G Abodunrin Cc: Kumar Valsan Prathap Cc: Chris Wilson Cc: Balestrieri Francesco Cc: Bloomfield Jon Cc: Dutt Sudeep --- drivers/gpu/drm/i915/gt/intel_lrc.c | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'drivers') diff --git a/drivers/gpu/drm/i915/gt/intel_lrc.c b/drivers/gpu/drm/i915/gt/intel_lrc.c index 75dd0e0367b7..f0485784afbe 100644 --- a/drivers/gpu/drm/i915/gt/intel_lrc.c +++ b/drivers/gpu/drm/i915/gt/intel_lrc.c @@ -2664,6 +2664,14 @@ static u32 *gen9_init_indirectctx_bb(struct intel_engine_cs *engine, u32 *batch) /* WaFlushCoherentL3CacheLinesAtContextSwitch:skl,bxt,glk */ batch = gen8_emit_flush_coherentl3_wa(engine, batch); + /* WaClearSlmSpaceAtContextSwitch:skl,bxt,kbl,glk,cfl */ + batch = gen8_emit_pipe_control(batch, + PIPE_CONTROL_FLUSH_L3 | + PIPE_CONTROL_STORE_DATA_INDEX | + PIPE_CONTROL_CS_STALL | + PIPE_CONTROL_QW_WRITE, + LRC_PPHWSP_SCRATCH_ADDR); + batch = emit_lri(batch, lri, ARRAY_SIZE(lri)); /* WaMediaPoolStateCmdInWABB:bxt,glk */ -- cgit v1.2.3 From 94dd3bada53ee77b80d0aeee5571eeb83654d156 Mon Sep 17 00:00:00 2001 From: Harald Freudenberger Date: Fri, 20 Dec 2019 09:06:09 +0100 Subject: s390/zcrypt: Fix CCA cipher key gen with clear key value function Regression tests showed that the CCA cipher key function which generates an CCA cipher key with given clear key value does not work correctly. At parsing the reply CPRB two limits are wrong calculated resulting in rejecting the reply as invalid with s390dbf message "_ip_cprb_helper reply with invalid or unknown key block". Fixes: f2bbc96e7cfa ("s390/pkey: add CCA AES cipher key support") Cc: Stable Signed-off-by: Harald Freudenberger Signed-off-by: Vasily Gorbik --- drivers/s390/crypto/zcrypt_ccamisc.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers') diff --git a/drivers/s390/crypto/zcrypt_ccamisc.c b/drivers/s390/crypto/zcrypt_ccamisc.c index c1db64a2db21..110fe9d0cb91 100644 --- a/drivers/s390/crypto/zcrypt_ccamisc.c +++ b/drivers/s390/crypto/zcrypt_ccamisc.c @@ -1037,8 +1037,8 @@ static int _ip_cprb_helper(u16 cardnr, u16 domain, prepparm = (struct iprepparm *) prepcblk->rpl_parmb; /* do some plausibility checks on the key block */ - if (prepparm->kb.len < 120 + 5 * sizeof(uint16_t) || - prepparm->kb.len > 136 + 5 * sizeof(uint16_t)) { + if (prepparm->kb.len < 120 + 3 * sizeof(uint16_t) || + prepparm->kb.len > 136 + 3 * sizeof(uint16_t)) { DEBUG_ERR("%s reply with invalid or unknown key block\n", __func__); rc = -EIO; -- cgit v1.2.3 From 0c874cd04292c7ee22d70eefc341fa2648f41f46 Mon Sep 17 00:00:00 2001 From: Harald Freudenberger Date: Fri, 22 Nov 2019 16:30:06 +0100 Subject: s390/zcrypt: move ap device reset from bus to driver code This patch moves the reset invocation of an ap device when fresh detected from the ap bus to the probe() function of the driver responsible for this device. The virtualisation of ap devices makes it necessary to remove unconditioned resets on fresh appearing apqn devices. It may be that such a device is already enabled for guest usage. So there may be a race condition between host ap bus and guest ap bus doing the reset. This patch moves the reset from the ap bus to the zcrypt drivers. So if there is no zcrypt driver bound to an ap device - for example the ap device is bound to the vfio device driver - the ap device is untouched passed to the vfio device driver. Signed-off-by: Harald Freudenberger Signed-off-by: Vasily Gorbik --- drivers/s390/crypto/ap_bus.c | 2 -- drivers/s390/crypto/ap_bus.h | 2 +- drivers/s390/crypto/ap_queue.c | 5 +++-- drivers/s390/crypto/zcrypt_cex2a.c | 1 + drivers/s390/crypto/zcrypt_cex2c.c | 2 ++ drivers/s390/crypto/zcrypt_cex4.c | 1 + 6 files changed, 8 insertions(+), 5 deletions(-) (limited to 'drivers') diff --git a/drivers/s390/crypto/ap_bus.c b/drivers/s390/crypto/ap_bus.c index a1915061932e..5256e3ce84e5 100644 --- a/drivers/s390/crypto/ap_bus.c +++ b/drivers/s390/crypto/ap_bus.c @@ -793,8 +793,6 @@ static int ap_device_probe(struct device *dev) drvres = ap_drv->flags & AP_DRIVER_FLAG_DEFAULT; if (!!devres != !!drvres) return -ENODEV; - /* (re-)init queue's state machine */ - ap_queue_reinit_state(to_ap_queue(dev)); } /* Add queue/card to list of active queues/cards */ diff --git a/drivers/s390/crypto/ap_bus.h b/drivers/s390/crypto/ap_bus.h index 433b7b64368d..bb35ba4a8d24 100644 --- a/drivers/s390/crypto/ap_bus.h +++ b/drivers/s390/crypto/ap_bus.h @@ -261,7 +261,7 @@ void ap_queue_prepare_remove(struct ap_queue *aq); void ap_queue_remove(struct ap_queue *aq); void ap_queue_suspend(struct ap_device *ap_dev); void ap_queue_resume(struct ap_device *ap_dev); -void ap_queue_reinit_state(struct ap_queue *aq); +void ap_queue_init_state(struct ap_queue *aq); struct ap_card *ap_card_create(int id, int queue_depth, int raw_device_type, int comp_device_type, unsigned int functions); diff --git a/drivers/s390/crypto/ap_queue.c b/drivers/s390/crypto/ap_queue.c index dad2be333d82..37c3bdc3642d 100644 --- a/drivers/s390/crypto/ap_queue.c +++ b/drivers/s390/crypto/ap_queue.c @@ -638,7 +638,7 @@ struct ap_queue *ap_queue_create(ap_qid_t qid, int device_type) aq->ap_dev.device.type = &ap_queue_type; aq->ap_dev.device_type = device_type; aq->qid = qid; - aq->state = AP_STATE_RESET_START; + aq->state = AP_STATE_UNBOUND; aq->interrupt = AP_INTR_DISABLED; spin_lock_init(&aq->lock); INIT_LIST_HEAD(&aq->list); @@ -771,10 +771,11 @@ void ap_queue_remove(struct ap_queue *aq) spin_unlock_bh(&aq->lock); } -void ap_queue_reinit_state(struct ap_queue *aq) +void ap_queue_init_state(struct ap_queue *aq) { spin_lock_bh(&aq->lock); aq->state = AP_STATE_RESET_START; ap_wait(ap_sm_event(aq, AP_EVENT_POLL)); spin_unlock_bh(&aq->lock); } +EXPORT_SYMBOL(ap_queue_init_state); diff --git a/drivers/s390/crypto/zcrypt_cex2a.c b/drivers/s390/crypto/zcrypt_cex2a.c index c50f3e86cc74..7cbb384ec535 100644 --- a/drivers/s390/crypto/zcrypt_cex2a.c +++ b/drivers/s390/crypto/zcrypt_cex2a.c @@ -175,6 +175,7 @@ static int zcrypt_cex2a_queue_probe(struct ap_device *ap_dev) zq->queue = aq; zq->online = 1; atomic_set(&zq->load, 0); + ap_queue_init_state(aq); ap_queue_init_reply(aq, &zq->reply); aq->request_timeout = CEX2A_CLEANUP_TIME, aq->private = zq; diff --git a/drivers/s390/crypto/zcrypt_cex2c.c b/drivers/s390/crypto/zcrypt_cex2c.c index 35c7c6672713..c78c0d119806 100644 --- a/drivers/s390/crypto/zcrypt_cex2c.c +++ b/drivers/s390/crypto/zcrypt_cex2c.c @@ -220,6 +220,7 @@ static int zcrypt_cex2c_queue_probe(struct ap_device *ap_dev) zq->queue = aq; zq->online = 1; atomic_set(&zq->load, 0); + ap_rapq(aq->qid); rc = zcrypt_cex2c_rng_supported(aq); if (rc < 0) { zcrypt_queue_free(zq); @@ -231,6 +232,7 @@ static int zcrypt_cex2c_queue_probe(struct ap_device *ap_dev) else zq->ops = zcrypt_msgtype(MSGTYPE06_NAME, MSGTYPE06_VARIANT_NORNG); + ap_queue_init_state(aq); ap_queue_init_reply(aq, &zq->reply); aq->request_timeout = CEX2C_CLEANUP_TIME; aq->private = zq; diff --git a/drivers/s390/crypto/zcrypt_cex4.c b/drivers/s390/crypto/zcrypt_cex4.c index 442e3d6162f7..6fabc906114c 100644 --- a/drivers/s390/crypto/zcrypt_cex4.c +++ b/drivers/s390/crypto/zcrypt_cex4.c @@ -381,6 +381,7 @@ static int zcrypt_cex4_queue_probe(struct ap_device *ap_dev) zq->queue = aq; zq->online = 1; atomic_set(&zq->load, 0); + ap_queue_init_state(aq); ap_queue_init_reply(aq, &zq->reply); aq->request_timeout = CEX4_CLEANUP_TIME, aq->private = zq; -- cgit v1.2.3 From d9d6a9aed3f66f8ce5fa3ca6ca26007d75032296 Mon Sep 17 00:00:00 2001 From: Brett Creeley Date: Wed, 13 Nov 2019 11:28:17 -0800 Subject: i40e: Fix virtchnl_queue_select bitmap validation Currently in i40e_vc_disable_queues_msg() we are incorrectly validating the virtchnl queue select bitmaps. The virtchnl_queue_select rx_queues and tx_queue bitmap is being compared against ICE_MAX_VF_QUEUES, but the problem is that these bitmaps can have a value greater than I40E_MAX_VF_QUEUES. Fix this by comparing the bitmaps against BIT(I40E_MAX_VF_QUEUES). Also, add the function i40e_vc_validate_vqs_bitmaps() that checks to see if both virtchnl_queue_select bitmaps are empty along with checking that the bitmaps only have valid bits set. This function can then be used in both the queue enable and disable flows. Suggested-by: Arkady Gilinksky Signed-off-by: Brett Creeley Tested-by: Andrew Bowers Signed-off-by: Jeff Kirsher --- drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c | 22 ++++++++++++++++++---- 1 file changed, 18 insertions(+), 4 deletions(-) (limited to 'drivers') diff --git a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c index 6a3f0fc56c3b..69523ac85639 100644 --- a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c +++ b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c @@ -2321,6 +2321,22 @@ static int i40e_ctrl_vf_rx_rings(struct i40e_vsi *vsi, unsigned long q_map, return ret; } +/** + * i40e_vc_validate_vqs_bitmaps - validate Rx/Tx queue bitmaps from VIRTHCHNL + * @vqs: virtchnl_queue_select structure containing bitmaps to validate + * + * Returns true if validation was successful, else false. + */ +static bool i40e_vc_validate_vqs_bitmaps(struct virtchnl_queue_select *vqs) +{ + if ((!vqs->rx_queues && !vqs->tx_queues) || + vqs->rx_queues >= BIT(I40E_MAX_VF_QUEUES) || + vqs->tx_queues >= BIT(I40E_MAX_VF_QUEUES)) + return false; + + return true; +} + /** * i40e_vc_enable_queues_msg * @vf: pointer to the VF info @@ -2346,7 +2362,7 @@ static int i40e_vc_enable_queues_msg(struct i40e_vf *vf, u8 *msg) goto error_param; } - if ((0 == vqs->rx_queues) && (0 == vqs->tx_queues)) { + if (i40e_vc_validate_vqs_bitmaps(vqs)) { aq_ret = I40E_ERR_PARAM; goto error_param; } @@ -2408,9 +2424,7 @@ static int i40e_vc_disable_queues_msg(struct i40e_vf *vf, u8 *msg) goto error_param; } - if ((vqs->rx_queues == 0 && vqs->tx_queues == 0) || - vqs->rx_queues > I40E_MAX_VF_QUEUES || - vqs->tx_queues > I40E_MAX_VF_QUEUES) { + if (i40e_vc_validate_vqs_bitmaps(vqs)) { aq_ret = I40E_ERR_PARAM; goto error_param; } -- cgit v1.2.3 From aa604651d523b1493988d0bf6710339f3ee60272 Mon Sep 17 00:00:00 2001 From: Radoslaw Tyl Date: Mon, 25 Nov 2019 15:24:52 +0100 Subject: ixgbevf: Remove limit of 10 entries for unicast filter list Currently, though the FDB entry is added to VF, it does not appear in RAR filters. VF driver only allows to add 10 entries. Attempting to add another causes an error. This patch removes limitation and allows use of all free RAR entries for the FDB if needed. Fixes: 46ec20ff7d ("ixgbevf: Add macvlan support in the set rx mode op") Signed-off-by: Radoslaw Tyl Acked-by: Paul Menzel Signed-off-by: Jeff Kirsher --- drivers/net/ethernet/intel/ixgbevf/ixgbevf_main.c | 5 ----- 1 file changed, 5 deletions(-) (limited to 'drivers') diff --git a/drivers/net/ethernet/intel/ixgbevf/ixgbevf_main.c b/drivers/net/ethernet/intel/ixgbevf/ixgbevf_main.c index 076f2da36f27..64ec0e7c64b4 100644 --- a/drivers/net/ethernet/intel/ixgbevf/ixgbevf_main.c +++ b/drivers/net/ethernet/intel/ixgbevf/ixgbevf_main.c @@ -2081,11 +2081,6 @@ static int ixgbevf_write_uc_addr_list(struct net_device *netdev) struct ixgbe_hw *hw = &adapter->hw; int count = 0; - if ((netdev_uc_count(netdev)) > 10) { - pr_err("Too many unicast filters - No Space\n"); - return -ENOSPC; - } - if (!netdev_uc_empty(netdev)) { struct netdev_hw_addr *ha; -- cgit v1.2.3 From 4fad78ad6422d9bca62135bbed8b6abc4cbb85b8 Mon Sep 17 00:00:00 2001 From: Cambda Zhu Date: Wed, 27 Nov 2019 17:03:55 +0800 Subject: ixgbe: Fix calculation of queue with VFs and flow director on interface flap This patch fixes the calculation of queue when we restore flow director filters after resetting adapter. In ixgbe_fdir_filter_restore(), filter's vf may be zero which makes the queue outside of the rx_ring array. The calculation is changed to the same as ixgbe_add_ethtool_fdir_entry(). Signed-off-by: Cambda Zhu Tested-by: Andrew Bowers Signed-off-by: Jeff Kirsher --- drivers/net/ethernet/intel/ixgbe/ixgbe_main.c | 37 +++++++++++++++++++-------- 1 file changed, 27 insertions(+), 10 deletions(-) (limited to 'drivers') diff --git a/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c b/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c index 82a30b597cf9..a2b2ad1f60b1 100644 --- a/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c +++ b/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c @@ -5239,7 +5239,7 @@ static void ixgbe_fdir_filter_restore(struct ixgbe_adapter *adapter) struct ixgbe_hw *hw = &adapter->hw; struct hlist_node *node2; struct ixgbe_fdir_filter *filter; - u64 action; + u8 queue; spin_lock(&adapter->fdir_perfect_lock); @@ -5248,17 +5248,34 @@ static void ixgbe_fdir_filter_restore(struct ixgbe_adapter *adapter) hlist_for_each_entry_safe(filter, node2, &adapter->fdir_filter_list, fdir_node) { - action = filter->action; - if (action != IXGBE_FDIR_DROP_QUEUE && action != 0) - action = - (action >> ETHTOOL_RX_FLOW_SPEC_RING_VF_OFF) - 1; + if (filter->action == IXGBE_FDIR_DROP_QUEUE) { + queue = IXGBE_FDIR_DROP_QUEUE; + } else { + u32 ring = ethtool_get_flow_spec_ring(filter->action); + u8 vf = ethtool_get_flow_spec_ring_vf(filter->action); + + if (!vf && (ring >= adapter->num_rx_queues)) { + e_err(drv, "FDIR restore failed without VF, ring: %u\n", + ring); + continue; + } else if (vf && + ((vf > adapter->num_vfs) || + ring >= adapter->num_rx_queues_per_pool)) { + e_err(drv, "FDIR restore failed with VF, vf: %hhu, ring: %u\n", + vf, ring); + continue; + } + + /* Map the ring onto the absolute queue index */ + if (!vf) + queue = adapter->rx_ring[ring]->reg_idx; + else + queue = ((vf - 1) * + adapter->num_rx_queues_per_pool) + ring; + } ixgbe_fdir_write_perfect_filter_82599(hw, - &filter->filter, - filter->sw_idx, - (action == IXGBE_FDIR_DROP_QUEUE) ? - IXGBE_FDIR_DROP_QUEUE : - adapter->rx_ring[action]->reg_idx); + &filter->filter, filter->sw_idx, queue); } spin_unlock(&adapter->fdir_perfect_lock); -- cgit v1.2.3 From 5365ec1aeff5b9f2962a9c9b31d63f9dad7e0e2d Mon Sep 17 00:00:00 2001 From: Manfred Rudigier Date: Wed, 4 Dec 2019 11:40:26 +0100 Subject: igb: Fix SGMII SFP module discovery for 100FX/LX. Changing the link mode should also be done for 100BaseFX SGMII modules, otherwise they just don't work when the default link mode in CTRL_EXT coming from the EEPROM is SERDES. Additionally 100Base-LX SGMII SFP modules are also supported now, which was not the case before. Tested with an i210 using Flexoptix S.1303.2M.G 100FX and S.1303.10.G 100LX SGMII SFP modules. Signed-off-by: Manfred Rudigier Tested-by: Aaron Brown Signed-off-by: Jeff Kirsher --- drivers/net/ethernet/intel/igb/e1000_82575.c | 8 ++------ drivers/net/ethernet/intel/igb/igb_ethtool.c | 2 +- 2 files changed, 3 insertions(+), 7 deletions(-) (limited to 'drivers') diff --git a/drivers/net/ethernet/intel/igb/e1000_82575.c b/drivers/net/ethernet/intel/igb/e1000_82575.c index 8a6ef3514129..438b42ce2cd9 100644 --- a/drivers/net/ethernet/intel/igb/e1000_82575.c +++ b/drivers/net/ethernet/intel/igb/e1000_82575.c @@ -530,7 +530,7 @@ static s32 igb_set_sfp_media_type_82575(struct e1000_hw *hw) dev_spec->module_plugged = true; if (eth_flags->e1000_base_lx || eth_flags->e1000_base_sx) { hw->phy.media_type = e1000_media_type_internal_serdes; - } else if (eth_flags->e100_base_fx) { + } else if (eth_flags->e100_base_fx || eth_flags->e100_base_lx) { dev_spec->sgmii_active = true; hw->phy.media_type = e1000_media_type_internal_serdes; } else if (eth_flags->e1000_base_t) { @@ -657,14 +657,10 @@ static s32 igb_get_invariants_82575(struct e1000_hw *hw) break; } - /* do not change link mode for 100BaseFX */ - if (dev_spec->eth_flags.e100_base_fx) - break; - /* change current link mode setting */ ctrl_ext &= ~E1000_CTRL_EXT_LINK_MODE_MASK; - if (hw->phy.media_type == e1000_media_type_copper) + if (dev_spec->sgmii_active) ctrl_ext |= E1000_CTRL_EXT_LINK_MODE_SGMII; else ctrl_ext |= E1000_CTRL_EXT_LINK_MODE_PCIE_SERDES; diff --git a/drivers/net/ethernet/intel/igb/igb_ethtool.c b/drivers/net/ethernet/intel/igb/igb_ethtool.c index 4690d6c87f39..445fbdce3e25 100644 --- a/drivers/net/ethernet/intel/igb/igb_ethtool.c +++ b/drivers/net/ethernet/intel/igb/igb_ethtool.c @@ -181,7 +181,7 @@ static int igb_get_link_ksettings(struct net_device *netdev, advertising &= ~ADVERTISED_1000baseKX_Full; } } - if (eth_flags->e100_base_fx) { + if (eth_flags->e100_base_fx || eth_flags->e100_base_lx) { supported |= SUPPORTED_100baseT_Full; advertising |= ADVERTISED_100baseT_Full; } -- cgit v1.2.3 From 9e05229190380f6b8f702da39aaeb97a0fc80dc3 Mon Sep 17 00:00:00 2001 From: Stefan Assmann Date: Tue, 17 Dec 2019 11:29:23 +0100 Subject: iavf: remove current MAC address filter on VF reset Currently MAC filters are not altered during a VF reset event. This may lead to a stale filter when an administratively set MAC is forced by the PF. For an administratively set MAC the PF driver deletes the VFs filters, overwrites the VFs MAC address and triggers a VF reset. However the VF driver itself is not aware of the filter removal, which is what the VF reset is for. The VF reset queues all filters present in the VF driver to be re-added to the PF filter list (including the filter for the now stale VF MAC address) and triggers a VIRTCHNL_OP_GET_VF_RESOURCES event, which provides the new MAC address to the VF. When this happens i40e will complain and reject the stale MAC filter, at least in the untrusted VF case. i40e 0000:08:00.0: Setting MAC 3c:fa:fa:fa:fa:01 on VF 0 iavf 0000:08:02.0: Reset warning received from the PF iavf 0000:08:02.0: Scheduling reset task i40e 0000:08:00.0: Bring down and up the VF interface to make this change effective. i40e 0000:08:00.0: VF attempting to override administratively set MAC address, bring down and up the VF interface to resume normal operation i40e 0000:08:00.0: VF 0 failed opcode 10, retval: -1 iavf 0000:08:02.0: Failed to add MAC filter, error IAVF_ERR_NVM To avoid re-adding the stale MAC filter it needs to be removed from the VF driver's filter list before queuing the existing filters. Then during the VIRTCHNL_OP_GET_VF_RESOURCES event the correct filter needs to be added again, at which point the MAC address has been updated. As a bonus this change makes bringing the VF down and up again superfluous for the administratively set MAC case. Signed-off-by: Stefan Assmann Tested-by: Andrew Bowers Signed-off-by: Jeff Kirsher --- drivers/net/ethernet/intel/iavf/iavf.h | 2 ++ drivers/net/ethernet/intel/iavf/iavf_main.c | 17 +++++++++++++---- drivers/net/ethernet/intel/iavf/iavf_virtchnl.c | 3 +++ 3 files changed, 18 insertions(+), 4 deletions(-) (limited to 'drivers') diff --git a/drivers/net/ethernet/intel/iavf/iavf.h b/drivers/net/ethernet/intel/iavf/iavf.h index 29de3ae96ef2..bd1b1ed323f4 100644 --- a/drivers/net/ethernet/intel/iavf/iavf.h +++ b/drivers/net/ethernet/intel/iavf/iavf.h @@ -415,4 +415,6 @@ void iavf_enable_channels(struct iavf_adapter *adapter); void iavf_disable_channels(struct iavf_adapter *adapter); void iavf_add_cloud_filter(struct iavf_adapter *adapter); void iavf_del_cloud_filter(struct iavf_adapter *adapter); +struct iavf_mac_filter *iavf_add_filter(struct iavf_adapter *adapter, + const u8 *macaddr); #endif /* _IAVF_H_ */ diff --git a/drivers/net/ethernet/intel/iavf/iavf_main.c b/drivers/net/ethernet/intel/iavf/iavf_main.c index 821987da5698..8e16be960e96 100644 --- a/drivers/net/ethernet/intel/iavf/iavf_main.c +++ b/drivers/net/ethernet/intel/iavf/iavf_main.c @@ -743,9 +743,8 @@ iavf_mac_filter *iavf_find_filter(struct iavf_adapter *adapter, * * Returns ptr to the filter object or NULL when no memory available. **/ -static struct -iavf_mac_filter *iavf_add_filter(struct iavf_adapter *adapter, - const u8 *macaddr)