From 3c53ddef6de1ba5c41255da644773727fffe34cc Mon Sep 17 00:00:00 2001 From: patrick Date: Thu, 25 Feb 2021 23:55:41 +0000 Subject: [PATCH] Some newer chips have two D11/802.11 cores, and we need to reset both at the same time. --- sys/dev/ic/bwfm.c | 39 ++++++++++++++++++++++++++++++++++++--- sys/dev/pci/if_bwfm_pci.c | 4 ++-- 2 files changed, 38 insertions(+), 5 deletions(-) diff --git a/sys/dev/ic/bwfm.c b/sys/dev/ic/bwfm.c index 6c480f0178c..ff734bc92d3 100644 --- a/sys/dev/ic/bwfm.c +++ b/sys/dev/ic/bwfm.c @@ -1,4 +1,4 @@ -/* $OpenBSD: bwfm.c,v 1.81 2021/02/24 10:13:08 patrick Exp $ */ +/* $OpenBSD: bwfm.c,v 1.82 2021/02/25 23:55:41 patrick Exp $ */ /* * Copyright (c) 2010-2016 Broadcom Corporation * Copyright (c) 2016,2017 Patrick Wildt @@ -69,6 +69,7 @@ void bwfm_process_clm_blob(struct bwfm_softc *); int bwfm_chip_attach(struct bwfm_softc *); int bwfm_chip_detach(struct bwfm_softc *, int); +struct bwfm_core *bwfm_chip_get_core_idx(struct bwfm_softc *, int, int); struct bwfm_core *bwfm_chip_get_core(struct bwfm_softc *, int); struct bwfm_core *bwfm_chip_get_pmu(struct bwfm_softc *); int bwfm_chip_ai_isup(struct bwfm_softc *, struct bwfm_core *); @@ -927,18 +928,24 @@ bwfm_chip_attach(struct bwfm_softc *sc) } struct bwfm_core * -bwfm_chip_get_core(struct bwfm_softc *sc, int id) +bwfm_chip_get_core_idx(struct bwfm_softc *sc, int id, int idx) { struct bwfm_core *core; LIST_FOREACH(core, &sc->sc_chip.ch_list, co_link) { - if (core->co_id == id) + if (core->co_id == id && idx-- == 0) return core; } return NULL; } +struct bwfm_core * +bwfm_chip_get_core(struct bwfm_softc *sc, int id) +{ + return bwfm_chip_get_core_idx(sc, id, 0); +} + struct bwfm_core * bwfm_chip_get_pmu(struct bwfm_softc *sc) { @@ -1017,9 +1024,15 @@ void bwfm_chip_ai_reset(struct bwfm_softc *sc, struct bwfm_core *core, uint32_t prereset, uint32_t reset, uint32_t postreset) { + struct bwfm_core *core2 = NULL; int i; + if (core->co_id == BWFM_AGENT_CORE_80211) + core2 = bwfm_chip_get_core_idx(sc, BWFM_AGENT_CORE_80211, 1); + bwfm_chip_ai_disable(sc, core, prereset, reset); + if (core2) + bwfm_chip_ai_disable(sc, core2, prereset, reset); for (i = 50; i > 0; i--) { if ((sc->sc_buscore_ops->bc_read(sc, @@ -1032,12 +1045,32 @@ bwfm_chip_ai_reset(struct bwfm_softc *sc, struct bwfm_core *core, } if (i == 0) printf("%s: timeout on core reset\n", DEVNAME(sc)); + if (core2) { + for (i = 50; i > 0; i--) { + if ((sc->sc_buscore_ops->bc_read(sc, + core2->co_wrapbase + BWFM_AGENT_RESET_CTL) & + BWFM_AGENT_RESET_CTL_RESET) == 0) + break; + sc->sc_buscore_ops->bc_write(sc, + core2->co_wrapbase + BWFM_AGENT_RESET_CTL, 0); + delay(60); + } + if (i == 0) + printf("%s: timeout on core reset\n", DEVNAME(sc)); + } sc->sc_buscore_ops->bc_write(sc, core->co_wrapbase + BWFM_AGENT_IOCTL, postreset | BWFM_AGENT_IOCTL_CLK); sc->sc_buscore_ops->bc_read(sc, core->co_wrapbase + BWFM_AGENT_IOCTL); + if (core2) { + sc->sc_buscore_ops->bc_write(sc, + core2->co_wrapbase + BWFM_AGENT_IOCTL, + postreset | BWFM_AGENT_IOCTL_CLK); + sc->sc_buscore_ops->bc_read(sc, + core2->co_wrapbase + BWFM_AGENT_IOCTL); + } } void diff --git a/sys/dev/pci/if_bwfm_pci.c b/sys/dev/pci/if_bwfm_pci.c index 7bf723428e1..848869694b8 100644 --- a/sys/dev/pci/if_bwfm_pci.c +++ b/sys/dev/pci/if_bwfm_pci.c @@ -1,4 +1,4 @@ -/* $OpenBSD: if_bwfm_pci.c,v 1.41 2021/02/25 23:26:05 patrick Exp $ */ +/* $OpenBSD: if_bwfm_pci.c,v 1.42 2021/02/25 23:55:41 patrick Exp $ */ /* * Copyright (c) 2010-2016 Broadcom Corporation * Copyright (c) 2017 Patrick Wildt @@ -781,7 +781,7 @@ bwfm_pci_load_microcode(struct bwfm_pci_softc *sc, const u_char *ucode, size_t s } bwfm_chip_set_active(bwfm, *(uint32_t *)ucode); - for (i = 0; i < 40; i++) { + for (i = 0; i < 100; i++) { delay(50 * 1000); shared = bus_space_read_4(sc->sc_tcm_iot, sc->sc_tcm_ioh, bwfm->sc_chip.ch_rambase + bwfm->sc_chip.ch_ramsize - 4); -- 2.20.1