BeaglePlay mikroBUS ugly UART access hack

Just saving off a hack today because this continues to be harder than it has to be based on topics like:

Below is just another hack and not the way we should solve this problem. Someone was bugging me for this and I honestly don’t a lot of the fuss, because I hack on device-tree at least a little bit every week. I know I shouldn’t expect other people to just know this stuff.

Anyway, I didn’t find a suitable overlay in the repository super-quickly and it is easier just to hack the base tree than to debug syntax on an overlay. So, the below yuck ensude…

jkridner@slotcar:~$ ssh debian@
debian@BeaglePlay:~$ cd /opt/source/dtb-5.10-ti/
debian@BeaglePlay:/opt/source/dtb-5.10-ti$ wget
debian@BeaglePlay:/opt/source/dtb-5.10-ti$ git apply 1310703
debian@BeaglePlay:/opt/source/dtb-5.10-ti$ make
  DTC     src/arm64/k3-am625-beagleplay.dtb
debian@BeaglePlay:/opt/source/dtb-5.10-ti$ sudo make install
debian@BeaglePlay:/opt/source/dtb-5.10-ti$ sudo shutdown -r now
Connection to closed by remote host.
Connection to closed.
jkridner@slotcar:~$ ssh debian@
debian@BeaglePlay:~$ ls -l /dev/play/mikrobus/uart
lrwxrwxrwx 1 root root 11 Jun 18  2023 /dev/play/mikrobus/uart -> ../../ttyS3
debian@BeaglePlay:~$ gpioinfo | grep MB_
line   7:    "MB_CIPO"       unused  output  active-high
line   8:    "MB_COPI"       unused  output  active-high
line   9:     "MB_INT"       unused   input  active-high
line  10:      "MB_AN"       unused  output  active-high
line  11:     "MB_PWM"       unused  output  active-high
line  12:     "MB_RST"       unused  output  active-high
line  13:     "MMB_CS"       unused  output  active-high
line  14:     "MB_SCK"       unused  output  active-high
line  22:     "MB_SCL"       unused  output  active-high
line  23:     "MB_SDA"       unused  output  active-high
line  24:      "MB_RX"       unused  output  active-high
line  25:      "MB_TX"       unused  output  active-high 

And, for reference, this was the device-tree hack:

diff --git a/src/arm64/k3-am625-beagleplay.dts b/src/arm64/k3-am625-beagleplay.dts
index b36764a..903ee33 100644
--- a/src/arm64/k3-am625-beagleplay.dts
+++ b/src/arm64/k3-am625-beagleplay.dts
@@ -286,7 +286,7 @@
 		pinctrl-names = "default", "pwm_default", "pwm_gpio",
 				"uart_default", "uart_gpio", "i2c_default",
 				"i2c_gpio", "spi_default", "spi_gpio";
-		pinctrl-0 = <&mikrobus_gpio_pins_default>;
+		pinctrl-0 = <&mikrobus_uart_pins_default>;
 		pinctrl-1 = <&mikrobus_pwm_pins_default>;
 		pinctrl-2 = <&mikrobus_pwm_pins_gpio>;
 		pinctrl-3 = <&mikrobus_uart_pins_default>;
@@ -574,6 +574,14 @@
 		pinctrl-single,pins = <
 			AM62X_IOPAD(0x01d8, PIN_INPUT, 1) /* (C15) MCAN0_TX.UART5_RXD */
 			AM62X_IOPAD(0x01dc, PIN_OUTPUT, 1) /* (E15) MCAN0_RX.UART5_TXD */
+			AM62X_IOPAD(0x019c, PIN_INPUT, 7) /* (B18) MCASP0_AXR1.GPIO1_9 */
+			AM62X_IOPAD(0x01a0, PIN_INPUT, 7) /* (E18) MCASP0_AXR0.GPIO1_10 */
+			AM62X_IOPAD(0x01a4, PIN_INPUT, 7) /* (B20) MCASP0_ACLKX.GPIO1_11 */
+			AM62X_IOPAD(0x01a8, PIN_INPUT, 7) /* (D20) MCASP0_AFSX.GPIO1_12 */
+			AM62X_IOPAD(0x01d0, PIN_INPUT, 7) /* (A15) UART0_CTSn.GPIO1_22 */
+			AM62X_IOPAD(0x01d8, PIN_INPUT, 7) /* (C15) MCAN0_TX.GPIO1_24 */
+			AM62X_IOPAD(0x01dc, PIN_INPUT, 7) /* (E15) MCAN0_RX.GPIO1_25 */
+			AM62X_IOPAD(0x01d4, PIN_INPUT, 7) /* (B15) UART0_RTSn.GPIO1_23 */
@@ -880,14 +888,14 @@
 &main_gpio1 {
 	gpio-line-names = "", "", "", "", "",			/* 0-4 */
-		"SPE_RSTN", "SPE_INTN", "MIKROBUS_GPIO1_7",	/* 5-7 */
-		"MIKROBUS_GPIO1_8", "MIKROBUS_GPIO1_9",		/* 8-9 */
-		"MIKROBUS_GPIO1_10", "MIKROBUS_GPIO1_11",	/* 10-11 */
-		"MIKROBUS_GPIO1_12", "MIKROBUS_W1_GPIO0",	/* 12-13 */
-		"MIKROBUS_GPIO1_14",				/* 14 */
+		"SPE_RSTN", "SPE_INTN", "MB_CIPO",	/* 5-7 */
+		"MB_COPI", "MB_INT",		/* 8-9 */
+		"MB_AN", "MB_PWM",	/* 10-11 */
+		"MB_RST", "MMB_CS",	/* 12-13 */
+		"MB_SCK",				/* 14 */
 		"", "", "", "", "VDD_3V3_SD", "", "",		/* 15-21 */
-		"MIKROBUS_GPIO1_22", "MIKROBUS_GPIO1_23",	/* 22-23 */
-		"MIKROBUS_GPIO1_24", "MIKROBUS_GPIO1_25",	/* 24-25 */
+		"MB_SCL", "MB_SDA",	/* 22-23 */
+		"MB_RX", "MB_TX",	/* 24-25 */
 		"", "", "", "", "", "", "", "", "", "", "", "",	/* 26-37 */
 		"", "", "", "", "", "", "", "", "", "",		/* 38-47 */
 		"SD_CD", "SD_VOLT_SEL", "", "", "", "", "", "",	/* 48-55 */
@@ -1194,8 +1202,9 @@
 &main_uart5 {
+	symlink = "play/mikrobus/uart";
 	status = "okay";
-	force-empty-serdev-controller;
+	//force-empty-serdev-controller;
 &main_uart6 {

This pointed out several problems to me and I feel like we need to attack this problem from multiple angles.

  1. We need to document dynamic pinmuxing. There are a number of states that the mikrobus driver is smart enough to use within the kernel, but I have no idea how to make use of that stuff from user-space. It is very much worth taking some time to put a tutorial together specifically on this low-pin-count, very-normalized interface.

  2. We need to enable and document dynamic device-tree overlays and find some way that upstream will take it. If we can disable these drivers from user-space, then it becomes a lot easier to explain how to do some user-space hacking to build some understanding before committing things to the booted device-tree or kernel code.

  3. The device-tree needs a big overhaul clean-up. The names where not useful for the GPIO pins. I mean “MIKROBUS_GPIO1_11”? Which header pin is that on? If you have to go back to the schematic, we are missing the point of what Linux has to offer. We have this nice silkscreen on the board with names for every pin. Now, should I have renamed “MIRKOBUS_” to “MB_”? I don’t know. Just seems like a lot of letters that may or may not answer the question users are asking themselves.

  4. We need to push all these update upstream.

  5. We need to tie the solution into a tool like bb-config which both provides an easy mechanism as well as codifies the approach we use as reference. I applaud new efforts like beagle-kversion… I found that tool very helpful to get back to the default 5.10 kernel from the mainline kernel I was running on this board, but looking around for several tools feels like a real pain. We need a single front-end that acts as documentation for how to use what should be in the upstream kernel+device-tree+udev-customizations.

Hi, thank you for this hack, this is exactly what I needed. But, even after following these instructions, I was still unable to access UART5.
I’m writing down steps how I solved it, in case anybody has same issues as me.

1. issue: I have a different version of k3-am625-beagleplay.dts, so I was unable to apply the patch cleanly. Instead, I manually changed each line in the dts file following the patch provided.
Image I am using is 12.2, with kernel 5.10.168-ti-arm64-r111. I suppose having different OS versions could cause dts to be different, as the old image I was using didn’t even have this file installed (version 11.6).

2. issue: Even after changing the dts, recompiling it and installing using make and make install, it still didn’t work. It turned out that although the new dtb was generated, it wasn’t distributed everywhere it needed to go. I needed to copy my new dtb and replace old ones in these 2 locations:

After replacing these files, /dev/play/mikrobus/uart appeared as expected :slight_smile:

I hope this helps.

Best regards,

1 Like

But, even though /dev/play/mikrobus/uart has appeared, I am still unable to use UART5. I’ve tried enabling it in extlinux.conf file in /boot/firmware/extlinux, by editing BeaglePlay eMMc entry, like this:

label BeaglePlay eMMC (default)
kernel /Image
append root=/dev/mmcblk0p2 rw rootfstype=ext4 rootwait net.ifnames=0 quiet console=tty1 console=ttyS3,115200n8
fdtdir /
#fdtoverlays /overlays/.dtbo
initrd /initrd.img

@jkridner Do you have any ideas why this still isn’t working? Am I doing this right, or is something else required to enable uart5 usage?

Thanks in advance!

1 Like

I have the same issue. Any updates on this topic ? @jkridner