Last year I tested two older graphics cards—a Radeon 5450 and a GeForce GT710—on a Raspberry Pi Compute Module 4.
This year, I've been testing three more graphics cards—a GeForce GTX 750 Ti, a Radeon RX 550, and the diminutive ASRock Rack M2_VGA.
The Compute Module 4, if you didn't know already, exposes the BCM2711's single PCI express lane, and the official IO Board has a nice, standard, 1x PCIe slot into which you can plug any PCI express device.
Video version of this post
I also published a YouTube video on this topic, with even more detail: Will ANY GPUs work on the Raspberry Pi?.
Difficulties with PCIe on the Pi
But physical connection is one thing—getting a card to work on the Pi is a different problem, and it is compounded because:
- Until the CM4, no Pi exposed a PCI express interface (the Pi 4 model B internally uses the bus for a VL805 USB 3.0 chip). So Pi OS and other distributions easy to run on the Pi have never really optimized their PCI express support, or even included standard drivers for things you'd plug into a typical PC.
- Until late last year, the default BAR (Base Address Register) allocation on the Pi was 256 MB, and many cards require much more than this. The default allocation was raised to 1 GB in newer Pi OS kernels, and you can even raise it further (to 4 or 8 GB) following these instructions.
- The PCI express interface on the BCM2711 system on a chip was never optimized for general purpose 'desktop' use, and there are some quirks in its implementation (one of which was patched around to get a MegaRAID card working for SAS RAID storage on the Pi).
- Features like MSI-X were not originally supported and now are... mostly—and some PCI express cards rely on these features and expect them to behave a certain way in their driver.
- The Raspberry Pi uses an ARM processor. Many drivers are written for and tested on X86 but not ARM. Luckily, this is changing a bit over time, as ARM is slowly entering data center usage, and is finally gaining a foothold on end-user workstations.
- The CM4 IO Board is powered through either a 4-pin floppy connector or a 12v barrel plug. If you don't supply enough juice, PCI express cards can exhibit weird behavior. I spend a ton of time testing various scenarios and making sure the power supply was not the issue when I am testing cards.
I've tested a large variety of PCI express cards, and have been compiling the results of my testing on my Raspberry Pi PCI Express device compatibility database.
Some cards, like USB 3.0 controllers and NVMe drives, 'just work,' while others require a driver download and install (like Intel's AX200 WiFi 6 chip), or a kernel recompile (like Rosewill's 2.5 Gigabit NIC).
GPUs in Linux
Graphics cards on Linux have traditionally had... interesting levels of support, even on the most widely-used hardware.
For example, Nvidia supplies proprietary closed-source drivers for most of their modern cards, but loading them taints the kernel and if you have a problem, there's no real way to fix it short of begging Nvidia to deliver a new driver. Because of this, an open source, but inferior (performance-wise) reverse-engineered 'nouveau' driver exists in the Linux kernel source tree.
AMD actually submits its driver code straight into the Linux kernel source, so it can be inspected and patched if need be.
So against that backdrop, there are many challenges to overcome if one wants to get a graphics card working (for any purpose, whether gaming, AI/ML, mining, or just to add another display) on a Raspberry Pi.
But I like a good challenge, so I keep plunging forward:
Nvidia GeForce GTX 750 Ti
Like with the GT710, I tried installing the proprietary Nvidia ARM 64-bit driver. Doing so requires the installation of the raspberrypi-kernel-headers
on the 64-bit Pi OS beta. The driver installed, but upon restart, when X server started up, the Nvidia driver errored out with Internal error: Oops: 96000005 [#1] PREEMPT SMP
.
Since the driver is closed-source, I had no hope of debugging it, so I switched to recompiling the kernel with the nouveau
driver.
After doing so, and rebooting the Pi, it would lock up in the middle of initialization—and not a gentle lockup, a full hard lockup that required power cycling the Pi to get it to reboot.
I tried debugging the lockup over a serial connection, but was not getting very far, so I shelved the card and moved on.
AMD Radeon RX 550
The Radeon RX 550 uses the amdgpu
driver in the kernel source, so debugging it is a lot easier than with the proprietary Nvidia driver. I recompiled the kernel with that driver, rebooted the Pi and... lockup, just like every other card I've tested.
In this case, it locked up seemingly at the same point each time, so I dropped some debug printk()
s in the source in various places, eventually narrowing down the problem to something inside amdgpu_ring_init()
. I patched an errant call to memset()
with some help from GitHub user elFarto, but eventually after a ton more debugging I kind of petered out on the card and shelved it too.
ASRock Rack M2_VGA
Around that time, I recieved ASRock Rack's M2_VGA in the mail. I had emailed them after seeing it mentioned in a forum post about low-power graphics cards, and they graciously sent me one for testing.
It's an M.2 graphics card that sips 2W of power, supports one VGA port (though the SM750 GPU supports multiple displays and even video inputs!), and is almost as tiny as the Compute Module itself!
How did it fare on the Pi? Well, I recompiled the kernel with the built-in sm750fb
driver (which happens to be in the staging drivers still, after five years in the kernel source), and the Pi locked up when it tried starting the X window server. Just like all the other cards.
I was digging around in the SM750 driver source, found there was a fork that seems to have been started to 'get it into shape' and migrate it to the drm
subsystem, and tried that, but to no avail. That fork was actually more out of date than the in-tree fb driver, probably because the in-tree one, despite being hardly maintained, was at least updated to compile with the rest of the Linux kernel.
Maybe Phoronix's article Silicon Motion Has Open-Source Driver, But Fails was prescient. I tried reaching out to a few of the people who were listed as maintainers for the driver, but didn't get anywhere.
A reason for hope
After five fails (well, a couple were more "I give up after hours of testing"), all hope is not lost, though! GitHub user Coreforge is testing with a Radeon 6450, and was able to get a blinking cursor to be output through the card (albeit in a very noisy image):
This means that it is likely possible to get a graphics card working with the Pi CM4... but it's going to take a bit of driver debugging to get there.
Conclusion
I'm definitely getting out of my element in terms of driver work. Hopefully someone can make a breakthrough and figure out what's holding back all these drivers. Likely memory access issues or maybe even some yet-uncovered bug with how PCIe addressing works on the Pi's BCM2711 SoC.
Check out the companion video that goes into more depth: Will ANY GPUs work on the Raspberry Pi?.
Also check out the Pi PCI Express card database site for more details on my experience with each of the cards, along with links to the full discussion on GitHub.
Comments
Jeff, let me start by saying I'm atleast incredibly grateful for all the work and information you share. There is a question that I don't understand that maybe you could better explain. The raspberry pi 4b 8gb is a quad core cpu with 8gb ddr4 ram, and it has a gpu capable of displaying 4k. Why, then, does the gpu seem so.... for lack of better term, wimpy? I mean, part of me still thinks it's a modern miracle to fit a computer that capable into that small a size, and I don't understand what the gpu lacks that holds it back. Like, does it need more dedicated ram? Is it that programmers just don't optimize for that type of gpu? Or am I just ignorantly having unrealistic expectations? This most drives me nuts when 3d printing something, and needing to make a quick adjustment with onshape. I can have youtube, cura, and diablo 1 all running at the same time with little slowdown. If I wanna use onshape though I have to close all other active programs and it's still slow enough I get frustrated and just go upstairs to my desktop.... Help me understand, for I am dumb.
I myself am not an owner of any high-powered video hardware, but I am typing this on a Pi 4, so I know a bit. First is the physical size of the Pi's GPU - it shares a (quite small) die with all 4 CPUs and all of the associated pieces of circuitry. It is also confined to something like 40nm of transistor size, but I won't go into that.
But while the Pi is *capable* of 4k60 in refresh rate, most things it is displaying won'e be able to hit that many frames per second. As I understand it, the monitor can be updated at 60hz, but it won't have 60 distinct frames to display.
And the slowdowns like you are describing are likely caused by a CPU or RAM bottleneck - both of these are decidedly 'wimpy' on the Pi. One thing you can do to help this is installing a heatsink and/or fan, which will help a ton in long workloads.
So yes, because of the underpowered GPU, in the future you will be better served using a PC for something like 3D rendering. If compatibility is a problem... it's like we say - Linux all the things!
Hello Jeff,
You sure do love the RPi to go that way. ;)
Thank you so much for your write-up!
You do a fantastic job.
The pi4 GPU isn't exactly wimpy, but it's been held back by extremely poor drivers until recently. It also targets desktop use more than gaming. But:
For simple apps, you can most definitely hit 60 fames a second at 4096x2160. I've written an input lag tester (
http://alantechreview.blogspot.com/2020/08/pilagtester-pro-order-page.h…) and as a side effect I know for sure if it's dropping any franes, and it's not. At lower resolutions it can also do 120hz with no dropped framed.