The new Raspberry Pi 3 released on 29 Feb 2016 has issues with its UART port as the pinout GPIO 14/15 on the pin header is now based on a low throughput mini-UART.
To understand the issue better than reading the wall of text below, you can see the talk I gave on this issue.
The actual hardware UART on the BCM2837 SoC has now been assigned to handle Bluetooth with the BCM43438 Wifi/Bluetooth chip. More details can be found here and here.
This mini-UART does not produce a stable baud rate as it fluctuates based on the Core clock speed whenever it rises or falls. The result is that the serial debug output is practically unusable. On Raspbian you may see garbage or nothing at all. The solution is simple, add core_freq=250
to /boot/config.txt
to cap the core frequency to a constant value. This option is soon to be discouraged in favour of enable_uart=1
which Arch Linux already supports.
A "pi-bluetooth" package that exists in Raspbian is also not available in Arch Linux (yet) so Bluetooth support is not ready although an AUR package exists to enable BT.
In this gist, I will detail out all the steps required to enable the debug console on the miniUART and install Bluetooth support. At the same time, I have alternative instructions should you want to swap the Bluetooth to use the mini-UART and the debug console to use hardware UART instead.
- Raspberry Pi 3 Model B
- 3.3V USB-TTL cable like this from Adafruit or HDMI screen with keyboard or SSH.
- Network connection to download packages
- Copy the partition image to your microSD Card based on the installation guide here.
- Open the boot partition of the microSD card which should be the small 100MB partition.
- Open config.txt
- Add the following lines to the end of the file
enable_uart=1
The enable_uart=1
multiplier will cap the CPU speed of your ARM CPU to a constant 600Mhz instead of fluctuating speed up to 1.2Ghz so the baud rate of the mini-UART will be stable. This is roughly equivalent to earlier attempts to solve the problem with core_freq=250
.
For extra information, you can also add dtoverlay=pi3-miniuart-bt
to switch the pin mappings of the BCM2837 so the Serial Debug port will use the hardware UART and the Bluetooth part of the wireless chip will use the mini-UART.
- Unmount the SD card and insert into your Rpi3 and plug your USB-TTL cable.
We will need to install the pi-bluetooth package. This package has been ported from Raspbian and posted on AUR by someone. But before that, we should install Yaourt, a tool to install AUR packages.
Using a terminal program on your computer like screen
with the serial-TTL console cable, login with default user:alarm, password:alarm. Do not use root yet as makepkg
does not like root.
screen /dev/ttyUSB0 115200
#Arch Linux 4.1.19-2-ARCH (ttyS0)
#alarmpi login: alarm
#Password: alarm
#Install package-query, a dependency for Yaourt
su -c "pacman -Syu --needed wget base-devel yajl git"
#Install everything when asked. Password for root is "root"
git clone https://aur.archlinux.org/package-query.git
cd package-query
makepkg -s
su -c "pacman -U package-query-1.8-2-armv7h.pkg.tar.xz"
cd ..
git clone https://aur.archlinux.org/yaourt.git
cd yaourt
makepkg -s
su -c "pacman -U yaourt-1.8.1-1-any.pkg.tar.xz"
Continue from the above using the alarm account.
#You might have to remove the existing bluez package if you have istalled it as pi-bluetooth downloads the bluez source code to do some patching before installation.
yaourt -S pi-bluetooth
#1. Enter "1" to install the only package
#2. Give root password (default "root") when asked
#3. Do NOT edit PKGBUILD or anything else when they say "Unsupported Package" or similar warnings. Press "N".
#4. Answer Yes to install any requested dependencies or building
#Do not enable the brcm43438.service now if you have specified `dtoverlay=pi3-miniuart-bt` to swap the Bluetooth to use mini-UART. You have to edit the brcm43438.service first.
#Login as root with default password "root"
su
#ONLY edit the brcm43438.service file if you want Bluetooth to use mini-UART (/dev/ttyS0) instead of hardware UART (/dev/ttyAMA0).
#That is, if you have specified "dtoverlay=pi3-miniuart-bt" in "/boot/config.txt" earlier
nano /lib/systemd/system/brcm43438.service
#Edit the file to replace all references of /dev/ttyAMA0 with /dev/ttyS0 as below
#start
[Unit]
Description=Broadcom BCM43438 bluetooth HCI
ConditionPathIsDirectory=/proc/device-tree/soc/gpio@7e200000/bt_pins
Before=bluetooth.service
After=dev-ttyS0.device
[Service]
Type=simple
ExecStart=/usr/bin/hciattach-rpi3 -n /dev/ttyS0 bcm43xx 921600 noflow -
[Install]
WantedBy=multi-user.target
#end
systemctl enable brcm43438.service
reboot
If you set the Bluetooth communication to go through the mini-UART channel, the performance will be significantly degraded in theory. In fact, you may want to reduce the baud rate from 921600
to something lower like 460800
or even as low as 115200
. However, it should be enough for Bluetooth Low Energy applications. Higher speed data/audio transfer on Bluetooth classic may face issues. You will also need to set core_freq=250
or force_turbo=1
in /boot/config.txt
so the baud rate of the mini-UART will be stable to use Bluetooth.
If you use just enable_uart=1
in /boot/config.txt
, your RPi 3 will just be slow but everything should work as per normal.
What would be needed to make bluetooth work without the pi-bluetooth package? new version of bluez deprecates hciattach and btattach should be used instead and apart from that it just feels hacky to use that package