Raspberry PI 3 official touch screen not working

Hi guys!

I want to use the official 7’ touch screen with my Raspberry PI 3, but as soon as the kernel starts, it just turns black. It’s still on, but is just black. It does display the rainbow splashscreen and the uboot bootloader at the beginning, though.

What’s strange is, that everything works nicely when connecting an HDMI monitor.

Does anybody have an idea what the reason could be, why the linux kernel doesn’t work with the raspberry pi touch screen display, but does work with a screen connected over HDMI?

The PI and the screen is definitely fine, I’ve tried it with arch linux and it worked pretty well.

Is there maybe missing a kernel module or something?

Here’s what I currently have:

{ lib, pkgs, ... }: {
  imports = [

  nixpkgs.system = "aarch64-linux";

  sdImage.compressImage = false;

  boot.loader.raspberryPi.enable = true;
  # Set the version depending on your raspberry pi.
  boot.loader.raspberryPi.version = 3;
  console.keyMap = "de_CH-latin1";

  users.extraUsers.root.openssh.authorizedKeys.keys = [
   "ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEA289vddtq4A1/TNluSFhWE9VZY5CXXa/458iSUzeXtfC5mN/+dZe8kzCQmqBIqhYETdhMi/dvJyzL7oADJUFKL1cxLjF4A+MoBbRD1lsk9a0Fk08SsGGeJkW3Xb/B/NJbHGEYIB58ALS8kWJgFP0YH6gvZGXn8Fv2Odkorj65H702TOrKCib/CfWrwXd21cDPrXihFgKifsPKtk1odnobJS1h1ADOoIZqRpOKyQBr6+H352BuWhQpARmlII5soKpVxbTANrBvLEl6dhFzRf6dw2ftgdwRfJYjFlyxFArp4MweQ+9bi+D5YjeBi6uwGsRZfemdelXS3u/oxi4SDCJkLw=="

  services.openssh.enable = true;
  systemd.services.sshd.wantedBy = lib.mkOverride 40 [ "multi-user.target" ];

  networking.interfaces.eth0.ipv4.addresses = [ {
    address = "";
    prefixLength = 24;
  } ];

  networking.defaultGateway = "";
  networking.nameservers = [ "" ];

  boot.loader.raspberryPi.uboot.configurationLimit = 3;

  hardware.opengl = {
    enable = true;
    setLdLibraryPath = true;
    package = pkgs.mesa_drivers;
    driSupport = true;

  boot.kernelParams = [ "cma=256" ];
  boot.loader.raspberryPi.firmwareConfig = ''

  services.xserver.enable = true;
  services.xserver.displayManager.startx.enable = true;
  services.xserver.videoDrivers = [ "modesetting" ];
  environment.systemPackages = with pkgs; [

With that, I can put something like “firefox” inside .xinitrc and then run startx, and then, with HDMI connected, firefox comes up after a while.

I’m thankful for any hints I get!

Have you checked config.txt in both images for differences? Maybe you could check both kernel versions too.

Thank you very much for looking into this :slight_smile:

What do you mean with “both images”? I currently only have the one generated with the configuration above. Additionally, I couldn’t find out where the config.txt is stored.

Ah! You mean the arch linux image :face_with_hand_over_mouth:
No, I was not able to directly compare them yet, because I couldn’t find out where the config.txt file gets stored on the nixos image. Doing find / -name config.txt didn’t return anything if I remember correclty, so I thought it maybe gets compiled into something. But I looked at the arch config.txt and cmdline.txt and tried to apply the params from there via boot.kernelParams and boot.loader.raspberryPi.firmwareConfig, but that didn’t change anything.

Comparing kernel versions would be a good idea, but I don’t currently know how to do that :sweat_smile:

Which arch imge are you using? There’s ArchLinuxARM-rpi-2-latest.tar.gz and ArchLinuxARM-rpi-3-latest.tar.gz.

I guess you need to compare the config.txt with boot.loader.raspberryPi.firmwareConfig.

I had a look into ArchLinuxARM-rpi-3-latest.tar.gz which contains enable_uart=1 maybe you can try to add the option to boot.loader.raspberryPi.firmwareConfig. But it’s just a guess.

Comparing kernel versions would be a good idea, but I don’t currently know how to do that

Try uname -a.

Ok, I think I’ve found out what’s going on:

Initially, I generated the image using an older version of the configuration above and copied it over to the SD-card. Then, I started modifying the configuration, built it on the pc, and then applied it on the raspberry pi using nixos-rebuild --target-host ssh://myraspberrypi

But doing so never updated the actual bootloader or the config.txt file, because the bootloader is located on another partition, that does not get mounted. But setting boot.loader.raspberryPi.uboot.enable = true; enables writing the bootloader to /boot when switching to a new configuration, which is not there.

This is also the reason why I couldn’t find a config.txt file.

I’ll do some more research on this and will post my findings here.

Do you have an update on this? I’m need to communicate with some peripherals via UART on my RPi3 also, but without success. The furthest I’ve come is to get the expected /dev/ttyAMA0 when using linuxPackages_rpi3 as my kernel. But shorting the UART RX/TX pins running minicom -D /dev/ttyAMA0 -b 115200 doesn’t echo my entered characters back.

1 Like

No, I wasn’t able to solve this problem yet :frowning:
I’m able to modify config.txt now, and it definitely is used, but I had no success even after trying lots of different options.

I think it’s not a problem with the config.txt file and instead one of the kernel. Because the display works fine until it says “starting kernel”. Right after this, it goes black.

I don’t know why it works with an hdmi monitor connected, but not with the official display…

I believe so too. The generic linuxPackages_4_19 simply does not seem to know what hardware peripherals are available on the Pi. I managed to get SPI to work by applying a device-tree overlay. There is an extensive list of of overlays available, but I don’t believe any of them properly applies. I surmise whatever kernel is used in Raspbian and derivatives just have these applied already.

I’m unsure what difference linuxPackages_rpi* the kernels offers.