PR 60404: Beaglebone Black: nonfunctional usb wifi
Yuri Honegger <[email protected]> Sat, 11 Jul 2026 11:05:16 +0200
| Newsgroups | gmane.os.netbsd.current |
|---|---|
| Message-ID | <[email protected]> |
> Am 10.07.2026 um 16:23 schrieb Brook Milligan = <[email protected]>: >=20 >=20 >> On Jul 10, 2026, at 05:10, Yuri Honegger <[email protected]> = wrote: >>=20 >> I missed the IRC conversation about figuring out how to get whether = we are usb0/1 for the BBB usb controller. >=20 > No worries. As you said, IRC has its advantages and disadvantages. >=20 >> We cannot go by the attach order of the driver. There is no guarantee = that usb0 and usb1 always attach in the same order (in practice, it is = deterministic, but the order is undefined and could change). >=20 > I understand that probe order is undefined. For the moment, I ended = up keying off the faa_name part of the attach arguments. I=E2=80=99m = not sure how it gets there, but it relates to the node name in the = device tree, so I expect it to be relatively stable. It is stable until it isn=E2=80=99t. Names are only cosmetic. In the = past, linux has changed names of properties to standardize them a bit. >=20 > Please take a look at my current solution, verbose as it is for the = moment [1]. Also see the follow-ups. Without knowing what I=E2=80=99m = talking about or what that entails, I like the idea of adding a phy = driver as being the cleanest solution. Done right, though, it would = have to include some conditional for whether the address base is in the = tree with a fallback if not, at least if we want to interact with Linux = dts and until they add the address base. I have no idea how to do any = of that. Adding a phy driver doesn=E2=80=99t make it much more cleaner imo. The = phy driver would have to attach on "ti,am335x-usb-phy" so we can use = fdt_phy. It also doesn=E2=80=99t help with the issue of determining the = usb controller instance. I=E2=80=99m also not sure if the amount of = boilerplate a new driver adds compared to how much work it does is worth = it. That said, the approach with a phy driver is not wrong. I=E2=80=99m = fine with either. As for how to do it: This commit contains all changes required to add a = usb controller including a phy driver: = https://github.com/recursivetree/netbsd-src/commit/94182f2117e75b21e36b57f= 282ea8248e1d6c4b9 Perhaps it helps you to figure out what is needed. = Your configuration is GENERIC, not GENERIC_V5. >=20 > Any thoughts are welcome. I really appreciate your interest. >=20 > Additionally, if you have thoughts on the follow-on problems with wifi = (ioctl invalid argument and panic) mentioned in PR 60404 [2], please let = me know. No, I haven=E2=80=99t got around to look at it yet. >=20 > Cheers, > Brook >=20 > [1] = https://mail-index.netbsd.org/current-users/2026/07/10/msg047718.html > [2] https://gnats.netbsd.org/cgi-bin/query-pr-single.pl?number=3D60404 >=20 Index: ti_motg.c =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D RCS file: /cvsroot/src/sys/arch/arm/ti/ti_motg.c,v retrieving revision 1.5 diff -u -r1.5 ti_motg.c --- ti_motg.c 2 Feb 2024 22:14:04 -0000 1.5 +++ ti_motg.c 10 Jul 2026 02:36:15 -0000 @@ -165,6 +165,79 @@ aprint_normal_dev(self, "interrupting on %s\n", intrstr); +/* + * XXX - some of these constants should be read from the device tree + */ + +/* + * control module + * + * see Spruh TRM Table 2-2. L4_WKUP Peripheral Memory Map, page 180 and + * sys/external/gpl2/dts/dist/arch/arm/boot/dts/am33xx-l4.dtsi, line = 281 + * segment@200000:target-module@10000 + */ +#define CTRL_MODULE_BASE 0x44e10000 + +/* see sys/external/gpl2/dts/dist/arch/arm/boot/dts/am33xx-l4.dtsi, = line 327: usb_ctrl_mod:control@620 */ +#define USB_CTRL_MOD_PHY_CTRL_BASE 0x620 +#define USB_CTRL_MOD_PHY_CTRL_SIZE 0x10=20 The #define for a registers should go to ti_otgreg.h + +/* + * control register bits + * see Spruh TRM section 9.3.1.20, pages 1483-1484 and section = 9.3.1.22, pages 1486-1487 + */ +#define USBPHY_CM_PWRDN (1 << 0) +#define USBPHY_OTG_PWRDN (1 << 1) +#define USBPHY_OTG_VDET_EN (1 << 19) +#define USBPHY_OTG_SESSENDEN (1 << 20) same as above + +/* + * names based on USB control registers + * see Spruh TRM Table 2-1, page 178 + */ +#define USB0_BASE "usb@47401000" +#define USB1_BASE "usb@47401800" + + int usb_index =3D strcmp(faa->faa_name, USB0_BASE) =3D=3D 0 ? 0 + : strcmp(faa->faa_name, USB1_BASE) =3D=3D 0 ? 1 + : -1; + if (usb_index < 0) { + return; + } No chance anything like this could get it. The idea behind the device = tree is that it is the sole, authoritative source about the memory map = so that drivers work even if addresses change, like for example if they = release a new variant of the same SoC. If you really want to work with a = usb_index, go the linux route with the alias. + + aprint_normal("\n"); + aprint_normal("=3D=3D=3D> ti_motg::attach(): %s (usb%d)\n", = faa->faa_name, usb_index); + + bus_space_handle_t handle; + bus_addr_t ctrl_base_addr =3D CTRL_MODULE_BASE + = USB_CTRL_MOD_PHY_CTRL_BASE; /* control registers base address */ + bus_size_t ctrl_size =3D USB_CTRL_MOD_PHY_CTRL_SIZE; /* control = registers size */ You should get this from the device tree. A while ago, I provided the = skeleton for this: phy_phandle =3D fdtbus_get_phandle(phandle, "phys"); cm_phandle =3D fdtbus_get_phandle(phy_phandle, "ti,ctrl_mod"); fdtbus_get_reg_byname(cm_phandle, "phy_ctrl", &addr, &size); Have you tried that? + bus_size_t ctrl_offset =3D ctrl_base_addr + usb_index * 2 * = sizeof(uint32_t); /* control register offset */ usually you do something like usb_index * USB_CTRL_SIZE; where = USB_CTRL_SIZE is a #define. (The name is just an example) + + if (bus_space_map(faa->faa_bst, ctrl_base_addr, ctrl_size, 0, &handle) = !=3D 0) { + aprint_error(": couldn't map USB control registers\n"); + return; + } + + uint32_t usb_ctrl =3D bus_space_read_4(faa->faa_bst, handle, = ctrl_offset - ctrl_base_addr); + aprint_normal("0x%08x: usb_ctrl%d: 0x%08x (upper 8 bits=3D0x3c)\n", = (uint32_t)ctrl_offset, usb_index, usb_ctrl); + aprint_normal(" 0: %x (0?)\n", (usb_ctrl & USBPHY_CM_PWRDN) !=3D 0); + aprint_normal(" 1: %x (0?)\n", (usb_ctrl & USBPHY_OTG_PWRDN) !=3D 0); + aprint_normal(" 19: %x (1?)\n", (usb_ctrl & USBPHY_OTG_VDET_EN) !=3D = 0); + aprint_normal(" 20: %x (1?)\n", (usb_ctrl & USBPHY_OTG_SESSENDEN) !=3D = 0); + + aprint_normal("=3D=3D=3D> ti_motg::attach(): writing usb_ctrl%d\n", = usb_index); + usb_ctrl &=3D ~(USBPHY_CM_PWRDN | USBPHY_OTG_PWRDN); + usb_ctrl |=3D (USBPHY_OTG_VDET_EN | USBPHY_OTG_SESSENDEN); + bus_space_write_4(faa->faa_bst, handle, ctrl_offset - ctrl_base_addr, = usb_ctrl); + + usb_ctrl =3D bus_space_read_4(faa->faa_bst, handle, ctrl_offset - = ctrl_base_addr); + aprint_normal("0x%08x: usb_ctrl%d: 0x%08x (upper 8 bits=3D0x3c)\n", = (uint32_t)ctrl_offset, usb_index, usb_ctrl); + aprint_normal(" 0: %x (0?)\n", (usb_ctrl & USBPHY_CM_PWRDN) !=3D 0); + aprint_normal(" 1: %x (0?)\n", (usb_ctrl & USBPHY_OTG_PWRDN) !=3D 0); + aprint_normal(" 19: %x (1?)\n", (usb_ctrl & USBPHY_OTG_VDET_EN) !=3D = 0); + aprint_normal(" 20: %x (1?)\n", (usb_ctrl & USBPHY_OTG_SESSENDEN) !=3D = 0); + aprint_normal("\n"); + sc->sc_motg.sc_iot =3D faa->faa_bst; if (bus_space_map(sc->sc_motg.sc_iot, addr[0], size[0], 0, &sc->sc_motg.sc_ioh) !=3D 0) {