From owner-svn-src-stable-12@freebsd.org Thu Nov 28 17:52:27 2019 Return-Path: Delivered-To: svn-src-stable-12@mailman.nyi.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2610:1c1:1:606c::19:1]) by mailman.nyi.freebsd.org (Postfix) with ESMTP id 806B01B10A9; Thu, 28 Nov 2019 17:52:27 +0000 (UTC) (envelope-from manu@FreeBSD.org) Received: from mxrelay.nyi.freebsd.org (mxrelay.nyi.freebsd.org [IPv6:2610:1c1:1:606c::19:3]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) server-signature RSA-PSS (4096 bits) client-signature RSA-PSS (4096 bits) client-digest SHA256) (Client CN "mxrelay.nyi.freebsd.org", Issuer "Let's Encrypt Authority X3" (verified OK)) by mx1.freebsd.org (Postfix) with ESMTPS id 47P4wW3f0Wz3MRy; Thu, 28 Nov 2019 17:52:27 +0000 (UTC) (envelope-from manu@FreeBSD.org) Received: from repo.freebsd.org (repo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:0]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by mxrelay.nyi.freebsd.org (Postfix) with ESMTPS id 5FFC41710; Thu, 28 Nov 2019 17:52:27 +0000 (UTC) (envelope-from manu@FreeBSD.org) Received: from repo.freebsd.org ([127.0.1.37]) by repo.freebsd.org (8.15.2/8.15.2) with ESMTP id xASHqRhl072490; Thu, 28 Nov 2019 17:52:27 GMT (envelope-from manu@FreeBSD.org) Received: (from manu@localhost) by repo.freebsd.org (8.15.2/8.15.2/Submit) id xASHqPpe072482; Thu, 28 Nov 2019 17:52:25 GMT (envelope-from manu@FreeBSD.org) Message-Id: <201911281752.xASHqPpe072482@repo.freebsd.org> X-Authentication-Warning: repo.freebsd.org: manu set sender to manu@FreeBSD.org using -f From: Emmanuel Vadot Date: Thu, 28 Nov 2019 17:52:25 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-12@freebsd.org Subject: svn commit: r355178 - in stable/12/sys: arm/allwinner arm64/conf arm64/rockchip conf dev/usb/controller X-SVN-Group: stable-12 X-SVN-Commit-Author: manu X-SVN-Commit-Paths: in stable/12/sys: arm/allwinner arm64/conf arm64/rockchip conf dev/usb/controller X-SVN-Commit-Revision: 355178 X-SVN-Commit-Repository: base MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-BeenThere: svn-src-stable-12@freebsd.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: SVN commit messages for only the 12-stable src tree List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Thu, 28 Nov 2019 17:52:27 -0000 Author: manu Date: Thu Nov 28 17:52:25 2019 New Revision: 355178 URL: https://svnweb.freebsd.org/changeset/base/355178 Log: MFC r352940-r352941, r352943-r352944, r353062-r353063, r353125 r352940: generic_ohci: Look for the phy based on the id phy-names was never in the bindings schema even if it was present in some DTS. Get the optional phy based on its ID. r352941: arm: allwinner: a10_ehci: Look for the phy based on the id phy-names was never in the bindings schema even if it was present in some DTS. Get the optional phy based on its ID. PR: 240978 r352943: arm: allwinner: a10_ehci: Enable all phys Even if there should be only one phy enable all the ones declared in the dts just to be sure. r352944: generic_ehci: Enable all phys and resets The number of phys and resets is not defined and it controller dependent so enable/disable every one of them. r353062: Split out the attachment from the generic-ehci driver Create an attachment file for the existing ACPI attachment, and create a new FDT attachment for the generic-ehci driver. Submitted by: andrew (Original version) Differential Revision: https://reviews.freebsd.org/D19389 r353063: allwinner: Remove a10_ehci driver We have generic-ehci since r353062 so use it. X-MFC-With: r353062 r353125: arm64: rockchip: usb2phy: Add set/get mode We only support host mode so those functions are just added so we won't panic when generic-{e,o}hci will set the phy to host mode. X-MFC-With: r353062 Added: stable/12/sys/dev/usb/controller/generic_ehci.h - copied unchanged from r353063, head/sys/dev/usb/controller/generic_ehci.h stable/12/sys/dev/usb/controller/generic_ehci_acpi.c - copied unchanged from r353063, head/sys/dev/usb/controller/generic_ehci_acpi.c stable/12/sys/dev/usb/controller/generic_ehci_fdt.c - copied unchanged from r353063, head/sys/dev/usb/controller/generic_ehci_fdt.c Deleted: stable/12/sys/arm/allwinner/a10_ehci.c Modified: stable/12/sys/arm/allwinner/files.allwinner stable/12/sys/arm64/conf/GENERIC stable/12/sys/arm64/rockchip/rk_usb2phy.c stable/12/sys/conf/files.arm64 stable/12/sys/dev/usb/controller/generic_ehci.c stable/12/sys/dev/usb/controller/generic_ohci.c Directory Properties: stable/12/ (props changed) Modified: stable/12/sys/arm/allwinner/files.allwinner ============================================================================== --- stable/12/sys/arm/allwinner/files.allwinner Thu Nov 28 17:45:57 2019 (r355177) +++ stable/12/sys/arm/allwinner/files.allwinner Thu Nov 28 17:52:25 2019 (r355178) @@ -4,7 +4,6 @@ arm/allwinner/a10_ahci.c optional ahci arm/allwinner/a10_codec.c optional sound arm/allwinner/a10_dmac.c optional a10_dmac arm/allwinner/a31_dmac.c optional a31_dmac -arm/allwinner/a10_ehci.c optional ehci arm/allwinner/a10_sramc.c optional SOC_ALLWINNER_A10 arm/allwinner/aw_gpio.c optional gpio arm/allwinner/aw_if_dwc.c optional dwc @@ -26,6 +25,8 @@ arm/allwinner/sunxi_dma_if.m optional a10_dmac | a31_ dev/iicbus/twsi/a10_twsi.c optional twsi dev/usb/controller/generic_ohci.c optional ohci dev/usb/controller/generic_usb_if.m optional ohci +dev/usb/controller/generic_ehci.c optional ehci +dev/usb/controller/generic_ehci_fdt.c optional ehci arm/allwinner/aw_sid.c optional aw_sid arm/allwinner/aw_thermal.c optional aw_thermal arm/allwinner/aw_cir.c optional aw_cir evdev Modified: stable/12/sys/arm64/conf/GENERIC ============================================================================== --- stable/12/sys/arm64/conf/GENERIC Thu Nov 28 17:45:57 2019 (r355177) +++ stable/12/sys/arm64/conf/GENERIC Thu Nov 28 17:52:25 2019 (r355178) @@ -176,7 +176,6 @@ device uart_snps device pl011 # USB support -device aw_ehci # Allwinner EHCI USB interface (USB 2.0) device aw_usbphy # Allwinner USB PHY device rk_usb2phy # Rockchip USB2PHY device dwcotg # DWC OTG controller Modified: stable/12/sys/arm64/rockchip/rk_usb2phy.c ============================================================================== --- stable/12/sys/arm64/rockchip/rk_usb2phy.c Thu Nov 28 17:45:57 2019 (r355177) +++ stable/12/sys/arm64/rockchip/rk_usb2phy.c Thu Nov 28 17:52:25 2019 (r355178) @@ -87,12 +87,17 @@ struct rk_usb2phy_softc { struct syscon *grf; regulator_t phy_supply; clk_t clk; + int mode; }; /* Phy class and methods. */ static int rk_usb2phy_enable(struct phynode *phynode, bool enable); +static int rk_usb2phy_get_mode(struct phynode *phy, int *mode); +static int rk_usb2phy_set_mode(struct phynode *phy, int mode); static phynode_method_t rk_usb2phy_phynode_methods[] = { - PHYNODEMETHOD(phynode_enable, rk_usb2phy_enable), + PHYNODEMETHOD(phynode_enable, rk_usb2phy_enable), + PHYNODEMETHOD(phynode_usb_get_mode, rk_usb2phy_get_mode), + PHYNODEMETHOD(phynode_usb_set_mode, rk_usb2phy_set_mode), PHYNODEMETHOD_END }; @@ -136,6 +141,44 @@ rk_usb2phy_enable(struct phynode *phynode, bool enable return (0); fail: return (ENXIO); +} + +static int +rk_usb2phy_get_mode(struct phynode *phynode, int *mode) +{ + struct rk_usb2phy_softc *sc; + intptr_t phy; + device_t dev; + + dev = phynode_get_device(phynode); + phy = phynode_get_id(phynode); + sc = device_get_softc(dev); + + if (phy != RK3399_USBPHY_HOST) + return (ERANGE); + + *mode = sc->mode; + + return (0); +} + +static int +rk_usb2phy_set_mode(struct phynode *phynode, int mode) +{ + struct rk_usb2phy_softc *sc; + intptr_t phy; + device_t dev; + + dev = phynode_get_device(phynode); + phy = phynode_get_id(phynode); + sc = device_get_softc(dev); + + if (phy != RK3399_USBPHY_HOST) + return (ERANGE); + + sc->mode = mode; + + return (0); } /* Clock class and method */ Modified: stable/12/sys/conf/files.arm64 ============================================================================== --- stable/12/sys/conf/files.arm64 Thu Nov 28 17:45:57 2019 (r355177) +++ stable/12/sys/conf/files.arm64 Thu Nov 28 17:52:25 2019 (r355178) @@ -25,7 +25,6 @@ cloudabi64_vdso_blob.o optional compat_cloudabi64 \ # # Allwinner common files -arm/allwinner/a10_ehci.c optional ehci aw_ehci fdt arm/allwinner/a10_timer.c optional a10_timer fdt arm/allwinner/a10_codec.c optional sound a10_codec arm/allwinner/a31_dmac.c optional a31_dmac @@ -239,7 +238,9 @@ dev/uart/uart_dev_mu.c optional uart uart_mu dev/uart/uart_dev_pl011.c optional uart pl011 dev/usb/controller/dwc_otg_hisi.c optional dwcotg fdt soc_hisi_hi6220 dev/usb/controller/ehci_mv.c optional ehci_mv fdt -dev/usb/controller/generic_ehci.c optional ehci acpi +dev/usb/controller/generic_ehci.c optional ehci +dev/usb/controller/generic_ehci_acpi.c optional ehci acpi +dev/usb/controller/generic_ehci_fdt.c optional ehci fdt dev/usb/controller/generic_ohci.c optional ohci fdt dev/usb/controller/generic_usb_if.m optional ohci fdt dev/usb/controller/usb_nop_xceiv.c optional fdt ext_resources Modified: stable/12/sys/dev/usb/controller/generic_ehci.c ============================================================================== --- stable/12/sys/dev/usb/controller/generic_ehci.c Thu Nov 28 17:45:57 2019 (r355177) +++ stable/12/sys/dev/usb/controller/generic_ehci.c Thu Nov 28 17:52:25 2019 (r355178) @@ -60,27 +60,9 @@ __FBSDID("$FreeBSD$"); #include #include -#include -#include -#include +#include "generic_ehci.h" -static device_attach_t generic_ehci_attach; -static device_detach_t generic_ehci_detach; - -static int -generic_ehci_probe(device_t self) -{ - ACPI_HANDLE h; - - if ((h = acpi_get_handle(self)) == NULL || - !acpi_MatchHid(h, "PNP0D20")) - return (ENXIO); - - device_set_desc(self, "Generic EHCI Controller"); - return (BUS_PROBE_DEFAULT); -} - -static int +int generic_ehci_attach(device_t self) { ehci_softc_t *sc = device_get_softc(self); @@ -152,7 +134,7 @@ error: return (ENXIO); } -static int +int generic_ehci_detach(device_t self) { ehci_softc_t *sc = device_get_softc(self); @@ -192,7 +174,6 @@ generic_ehci_detach(device_t self) static device_method_t ehci_methods[] = { /* Device interface */ - DEVMETHOD(device_probe, generic_ehci_probe), DEVMETHOD(device_attach, generic_ehci_attach), DEVMETHOD(device_detach, generic_ehci_detach), DEVMETHOD(device_suspend, bus_generic_suspend), @@ -202,13 +183,8 @@ static device_method_t ehci_methods[] = { DEVMETHOD_END }; -static driver_t ehci_driver = { +driver_t generic_ehci_driver = { .name = "ehci", .methods = ehci_methods, .size = sizeof(ehci_softc_t), }; - -static devclass_t ehci_devclass; - -DRIVER_MODULE(ehci, acpi, ehci_driver, ehci_devclass, 0, 0); -MODULE_DEPEND(ehci, usb, 1, 1, 1); Copied: stable/12/sys/dev/usb/controller/generic_ehci.h (from r353063, head/sys/dev/usb/controller/generic_ehci.h) ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ stable/12/sys/dev/usb/controller/generic_ehci.h Thu Nov 28 17:52:25 2019 (r355178, copy of r353063, head/sys/dev/usb/controller/generic_ehci.h) @@ -0,0 +1,42 @@ +/*- + * Copyright (c) 2012 Ganbold Tsagaankhuu + * Copyright (c) 2016 The FreeBSD Foundation + * Copyright (c) 2019 Andrew Turner + * All rights reserved. + * + * This software was developed by Andrew Turner under + * sponsorship from the FreeBSD Foundation. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * $FreeBSD$ + */ + +#ifndef _GENERIC_EHCI_H_ +#define _GENERIC_EHCI_H_ + +extern driver_t generic_ehci_driver; + +device_attach_t generic_ehci_attach; +device_detach_t generic_ehci_detach; + +#endif /* !_GENERIC_EHCI_H_ */ Copied: stable/12/sys/dev/usb/controller/generic_ehci_acpi.c (from r353063, head/sys/dev/usb/controller/generic_ehci_acpi.c) ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ stable/12/sys/dev/usb/controller/generic_ehci_acpi.c Thu Nov 28 17:52:25 2019 (r355178, copy of r353063, head/sys/dev/usb/controller/generic_ehci_acpi.c) @@ -0,0 +1,86 @@ +/*- + * Copyright (c) 2012 Ganbold Tsagaankhuu + * Copyright (c) 2016 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Andrew Turner under + * sponsorship from the FreeBSD Foundation. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include +__FBSDID("$FreeBSD$"); + +#include "opt_bus.h" + +#include +#include +#include +#include +#include +#include + +#include +#include + +#include +#include +#include + +#include +#include +#include + +#include +#include +#include + +#include "generic_ehci.h" + +static int +generic_ehci_acpi_probe(device_t self) +{ + ACPI_HANDLE h; + + if ((h = acpi_get_handle(self)) == NULL || + !acpi_MatchHid(h, "PNP0D20")) + return (ENXIO); + + device_set_desc(self, "Generic EHCI Controller"); + return (BUS_PROBE_DEFAULT); +} + +static device_method_t ehci_acpi_methods[] = { + /* Device interface */ + DEVMETHOD(device_probe, generic_ehci_acpi_probe), + + DEVMETHOD_END +}; + +DEFINE_CLASS_1(ehci, ehci_acpi_driver, ehci_acpi_methods, + sizeof(ehci_softc_t), generic_ehci_driver); + +static devclass_t ehci_acpi_devclass; + +DRIVER_MODULE(ehci, acpi, ehci_acpi_driver, ehci_acpi_devclass, 0, 0); +MODULE_DEPEND(ehci, usb, 1, 1, 1); Copied: stable/12/sys/dev/usb/controller/generic_ehci_fdt.c (from r353063, head/sys/dev/usb/controller/generic_ehci_fdt.c) ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ stable/12/sys/dev/usb/controller/generic_ehci_fdt.c Thu Nov 28 17:52:25 2019 (r355178, copy of r353063, head/sys/dev/usb/controller/generic_ehci_fdt.c) @@ -0,0 +1,255 @@ +/*- + * Copyright (c) 2012 Ganbold Tsagaankhuu + * Copyright (c) 2016 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Andrew Turner under + * sponsorship from the FreeBSD Foundation. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include +__FBSDID("$FreeBSD$"); + +#include "opt_bus.h" + +#include +#include +#include +#include +#include +#include + +#include +#include + +#include +#include +#include + +#include +#include +#include + +#include +#include +#include +#include + +#ifdef EXT_RESOURCES +#include +#include +#include +#include +#endif + +#include "generic_ehci.h" + +#ifdef EXT_RESOURCES +struct clk_list { + TAILQ_ENTRY(clk_list) next; + clk_t clk; +}; + + +struct hwrst_list { + TAILQ_ENTRY(hwrst_list) next; + hwreset_t rst; +}; + +struct phy_list { + TAILQ_ENTRY(phy_list) next; + phy_t phy; +}; +#endif + +struct generic_ehci_fdt_softc { + ehci_softc_t ehci_sc; + +#ifdef EXT_RESOURCES + TAILQ_HEAD(, clk_list) clk_list; + TAILQ_HEAD(, hwrst_list) rst_list; + TAILQ_HEAD(, phy_list) phy_list; +#endif +}; + +static device_probe_t generic_ehci_fdt_probe; +static device_attach_t generic_ehci_fdt_attach; +static device_detach_t generic_ehci_fdt_detach; + +static int +generic_ehci_fdt_probe(device_t self) +{ + + if (!ofw_bus_status_okay(self)) + return (ENXIO); + + if (!ofw_bus_is_compatible(self, "generic-ehci")) + return (ENXIO); + + device_set_desc(self, "Generic EHCI Controller"); + return (BUS_PROBE_DEFAULT); +} + +static int +generic_ehci_fdt_attach(device_t dev) +{ +#ifdef EXT_RESOURCES + struct generic_ehci_fdt_softc *sc; + struct clk_list *clkp; + clk_t clk; + struct hwrst_list *rstp; + hwreset_t rst; + struct phy_list *phyp; + phy_t phy; + int err, off; + + sc = device_get_softc(dev); + + TAILQ_INIT(&sc->clk_list); + /* Enable clock */ + for (off = 0; clk_get_by_ofw_index(dev, 0, off, &clk) == 0; off++) { + err = clk_enable(clk); + if (err != 0) { + device_printf(dev, "Could not enable clock %s\n", + clk_get_name(clk)); + goto error; + } + clkp = malloc(sizeof(*clkp), M_DEVBUF, M_WAITOK | M_ZERO); + clkp->clk = clk; + TAILQ_INSERT_TAIL(&sc->clk_list, clkp, next); + } + + /* De-assert reset */ + TAILQ_INIT(&sc->rst_list); + for (off = 0; hwreset_get_by_ofw_idx(dev, 0, off, &rst) == 0; off++) { + err = hwreset_deassert(rst); + if (err != 0) { + device_printf(dev, "Could not de-assert reset\n"); + goto error; + } + rstp = malloc(sizeof(*rstp), M_DEVBUF, M_WAITOK | M_ZERO); + rstp->rst = rst; + TAILQ_INSERT_TAIL(&sc->rst_list, rstp, next); + } + + /* Enable USB PHY */ + TAILQ_INIT(&sc->phy_list); + for (off = 0; phy_get_by_ofw_idx(dev, 0, off, &phy) == 0; off++) { + err = phy_usb_set_mode(phy, PHY_USB_MODE_HOST); + if (err != 0) { + device_printf(dev, "Could not set phy to host mode\n"); + goto error; + } + err = phy_enable(phy); + if (err != 0) { + device_printf(dev, "Could not enable phy\n"); + goto error; + } + phyp = malloc(sizeof(*phyp), M_DEVBUF, M_WAITOK | M_ZERO); + phyp->phy = phy; + TAILQ_INSERT_TAIL(&sc->phy_list, phyp, next); + } +#endif + + err = generic_ehci_attach(dev); + if (err != 0) + goto error; + + return (0); + +error: + generic_ehci_fdt_detach(dev); + return (err); +} + +static int +generic_ehci_fdt_detach(device_t dev) +{ +#ifdef EXT_RESOURCES + struct generic_ehci_fdt_softc *sc; + struct clk_list *clk, *clk_tmp; + struct hwrst_list *rst, *rst_tmp; + struct phy_list *phy, *phy_tmp; +#endif + int err; + + err = generic_ehci_detach(dev); + if (err != 0) + return (err); + +#ifdef EXT_RESOURCES + sc = device_get_softc(dev); + + /* Disable clock */ + TAILQ_FOREACH_SAFE(clk, &sc->clk_list, next, clk_tmp) { + err = clk_disable(clk->clk); + if (err != 0) + device_printf(dev, "Could not disable clock %s\n", + clk_get_name(clk->clk)); + err = clk_release(clk->clk); + if (err != 0) + device_printf(dev, "Could not release clock %s\n", + clk_get_name(clk->clk)); + TAILQ_REMOVE(&sc->clk_list, clk, next); + free(clk, M_DEVBUF); + } + + /* Assert reset */ + TAILQ_FOREACH_SAFE(rst, &sc->rst_list, next, rst_tmp) { + hwreset_assert(rst->rst); + hwreset_release(rst->rst); + TAILQ_REMOVE(&sc->rst_list, rst, next); + free(rst, M_DEVBUF); + } + + /* Disable phys */ + TAILQ_FOREACH_SAFE(phy, &sc->phy_list, next, phy_tmp) { + err = phy_disable(phy->phy); + if (err != 0) + device_printf(dev, "Could not disable phy\n"); + phy_release(phy->phy); + TAILQ_REMOVE(&sc->phy_list, phy, next); + free(phy, M_DEVBUF); + } +#endif + + return (0); +} + +static device_method_t ehci_fdt_methods[] = { + /* Device interface */ + DEVMETHOD(device_probe, generic_ehci_fdt_probe), + DEVMETHOD(device_attach, generic_ehci_fdt_attach), + DEVMETHOD(device_detach, generic_ehci_fdt_detach), + + DEVMETHOD_END +}; + +DEFINE_CLASS_1(ehci, ehci_fdt_driver, ehci_fdt_methods, + sizeof(ehci_softc_t), generic_ehci_driver); + +static devclass_t ehci_fdt_devclass; + +DRIVER_MODULE(ehci, simplebus, ehci_fdt_driver, ehci_fdt_devclass, 0, 0); +MODULE_DEPEND(ehci, usb, 1, 1, 1); Modified: stable/12/sys/dev/usb/controller/generic_ohci.c ============================================================================== --- stable/12/sys/dev/usb/controller/generic_ohci.c Thu Nov 28 17:45:57 2019 (r355177) +++ stable/12/sys/dev/usb/controller/generic_ohci.c Thu Nov 28 17:52:25 2019 (r355178) @@ -61,6 +61,7 @@ __FBSDID("$FreeBSD$"); #include #include #include +#include #endif #include "generic_usb_if.h" @@ -70,15 +71,23 @@ struct clk_list { TAILQ_ENTRY(clk_list) next; clk_t clk; }; +struct phy_list { + TAILQ_ENTRY(phy_list) next; + phy_t phy; +}; +struct hwrst_list { + TAILQ_ENTRY(hwrst_list) next; + hwreset_t rst; +}; #endif struct generic_ohci_softc { ohci_softc_t ohci_sc; #ifdef EXT_RESOURCES - hwreset_t rst; - phy_t phy; - TAILQ_HEAD(, clk_list) clk_list; + TAILQ_HEAD(, clk_list) clk_list; + TAILQ_HEAD(, phy_list) phy_list; + TAILQ_HEAD(, hwrst_list) rst_list; #endif }; @@ -107,7 +116,11 @@ generic_ohci_attach(device_t dev) #ifdef EXT_RESOURCES int off; struct clk_list *clkp; + struct phy_list *phyp; + struct hwrst_list *rstp; clk_t clk; + phy_t phy; + hwreset_t rst; #endif sc->ohci_sc.sc_bus.parent = dev; @@ -174,22 +187,34 @@ generic_ohci_attach(device_t dev) } /* De-assert reset */ - if (hwreset_get_by_ofw_idx(dev, 0, 0, &sc->rst) == 0) { - err = hwreset_deassert(sc->rst); + TAILQ_INIT(&sc->rst_list); + for (off = 0; hwreset_get_by_ofw_idx(dev, 0, off, &rst) == 0; off++) { + err = hwreset_deassert(rst); if (err != 0) { - device_printf(dev, "Could not de-assert reset %d\n", - off); + device_printf(dev, "Could not de-assert reset\n"); goto error; } + rstp = malloc(sizeof(*rstp), M_DEVBUF, M_WAITOK | M_ZERO); + rstp->rst = rst; + TAILQ_INSERT_TAIL(&sc->rst_list, rstp, next); } /* Enable phy */ - if (phy_get_by_ofw_name(dev, 0, "usb", &sc->phy) == 0) { - err = phy_enable(sc->phy); + TAILQ_INIT(&sc->phy_list); + for (off = 0; phy_get_by_ofw_idx(dev, 0, off, &phy) == 0; off++) { + err = phy_usb_set_mode(phy, PHY_USB_MODE_HOST); if (err != 0) { + device_printf(dev, "Could not set phy to host mode\n"); + goto error; + } + err = phy_enable(phy); + if (err != 0) { device_printf(dev, "Could not enable phy\n"); goto error; } + phyp = malloc(sizeof(*phyp), M_DEVBUF, M_WAITOK | M_ZERO); + phyp->phy = phy; + TAILQ_INSERT_TAIL(&sc->phy_list, phyp, next); } #endif @@ -217,6 +242,8 @@ generic_ohci_detach(device_t dev) int err; #ifdef EXT_RESOURCES struct clk_list *clk, *clk_tmp; + struct phy_list *phy, *phy_tmp; + struct hwrst_list *rst, *rst_tmp; #endif /* during module unload there are lots of children leftover */ @@ -258,13 +285,23 @@ generic_ohci_detach(device_t dev) #ifdef EXT_RESOURCES /* Disable phy */ - if (sc->phy) { - err = phy_disable(sc->phy); + TAILQ_FOREACH_SAFE(phy, &sc->phy_list, next, phy_tmp) { + err = phy_disable(phy->phy); if (err != 0) device_printf(dev, "Could not disable phy\n"); - phy_release(sc->phy); + phy_release(phy->phy); + TAILQ_REMOVE(&sc->phy_list, phy, next); + free(phy, M_DEVBUF); } + /* Assert reset */ + TAILQ_FOREACH_SAFE(rst, &sc->rst_list, next, rst_tmp) { + hwreset_assert(rst->rst); + hwreset_release(rst->rst); + TAILQ_REMOVE(&sc->rst_list, rst, next); + free(rst, M_DEVBUF); + } + /* Disable clock */ TAILQ_FOREACH_SAFE(clk, &sc->clk_list, next, clk_tmp) { err = clk_disable(clk->clk); @@ -277,14 +314,6 @@ generic_ohci_detach(device_t dev) clk_get_name(clk->clk)); TAILQ_REMOVE(&sc->clk_list, clk, next); free(clk, M_DEVBUF); - } - - /* De-assert reset */ - if (sc->rst) { - err = hwreset_assert(sc->rst); - if (err != 0) - device_printf(dev, "Could not assert reset\n"); - hwreset_release(sc->rst); } #endif