pop-os / pop

A project for managing all Pop!_OS sources
https://system76.com/pop
2.47k stars 87 forks source link

Screen brightness control stop working since nvidia driver 510.54 update #2227

Open nachomozo opened 2 years ago

nachomozo commented 2 years ago

Distribution (run cat /etc/os-release): NAME="Pop!_OS" VERSION="21.10" ID=pop ID_LIKE="ubuntu debian" PRETTY_NAME="Pop!_OS 21.10" VERSION_ID="21.10" HOME_URL="https://pop.system76.com" SUPPORT_URL="https://support.system76.com" BUG_REPORT_URL="https://github.com/pop-os/pop/issues" PRIVACY_POLICY_URL="https://system76.com/privacy" VERSION_CODENAME=impish UBUNTU_CODENAME=impish LOGO=distributor-logo-pop-os

Related Application and/or Package Version (run apt policy $PACKAGE NAME): nvidia-driver-510: Instalados: 510.54-1pop0~1645544462~21.10~e35d257 Candidato: 510.54-1pop0~1645544462~21.10~e35d257 Tabla de versión: *** 510.54-1pop0~1645544462~21.10~e35d257 1001 1001 http://apt.pop-os.org/release impish/main amd64 Packages 100 /var/lib/dpkg/status 510.47.03-0ubuntu0.21.10.1 500 500 http://us.archive.ubuntu.com/ubuntu impish-security/restricted amd64 Packages 500 http://us.archive.ubuntu.com/ubuntu impish-updates/restricted amd64 Packages

Issue/Bug Description: The screen brightness control stop working since nvidia 510.54 driver update (both topbar menu and keyboard hot keys). Now is always on minimum.

Steps to reproduce (if you know): Update nvidia driver to 510.54 usind Pop!_Shop or apt and reboot.

Expected behavior: Brightness must change as it did before update.

Other Notes:

I add the relevant specifications of my system in case it helps.

OS: Pop!_OS 21.10 x86_64 Host: 20YM Lenovo ThinkBook 16p Gen 2 Kernel: 5.15.23-76051523-generic DE: GNOME 40.5 WM: Mutter CPU: AMD Ryzen 7 5800H with Radeon Graphics (16) @ 3.200GHz GPU: AMD ATI 05:00.0 Cezanne GPU: NVIDIA GeForce RTX 3060 Mobile / Max-Q Memory: 3585MiB / 15422MiB

nachomozo commented 2 years ago

Doing some tests, it does not work even in Hybrid mode. using the command xrandr --output eDP --brightness 1 changes the brightnes as expected.

Another anoying issue: if i boot the laptop with an external monitor connected, Pop!_OS doesn't event starts (it stuck on a gray screen).

leviport commented 2 years ago

Might be a duplicate of https://github.com/pop-os/shop/issues/329 or https://github.com/pop-os/pop/issues/2197

nachomozo commented 2 years ago

Might be a duplicate of pop-os/shop#329 or #2197

Might be... unfortunately none of the solutions proposed in those issues have worked in my case.

I tried to switch to discrete graphics, and brighness control works again but fails again when I return to nvidia. I tried to congfigure xorg or kernelstub adding RegistryDwords EnableBrightnessControl=1 none of them worked I tried to disable nvidia card in bios: Pop!_OS does not boot.

Brightness is still at minimum. So fustrating.

nachomozo commented 2 years ago

Ok, got my backlight control working again with a dirty workaround.

Trying different solutions, I found the /sys/class/backlight settings folder that control the brightness according to the device.

The problem is that even though you are using the Nvidia card, it only listens to the brightness changes in the files corresponding to the integrated card (AMD in my case)

It seems that the brightness control writes to the Nvidia files but to read them it uses the AMD ones.

I am a basic user of linux and I don't know why.

So, my workaround is to change the brightness on gnome and then run:

sudo cp /sys/class/backlight/nvidia_0/actual_brightness /sys/class/backlight/amdgpu_bl0/brightness

Where nvidia_0 and amdgpu_bl0 are my devices (May be different on other setups)

I have also made a small script to let it run and change the brightness in real time:

sudo apt install inotify-tools
#!/bin/sh

path=/sys/class/backlight/nvidia_0

inotifywait -q -m -e close_write $path |
while read -r actual_brightness event; do
  cp $path/actual_brightness /sys/class/backlight/amdgpu_bl0/brightness
done

If someone knows how to put this script in the system startup or see the solution with the data I have given, it would be appreciated.

InsanityM commented 2 years ago

I have the same problem even on a fresh install of pop os 22.04

nachomozo commented 2 years ago

I have the same problem even on a fresh install of pop os 22.04

I have also tried a fresh install and the issue persists. I have also tried other distros like Manjaro, Ubuntu or Endevour and it works until I enable the 510 Nvidia driver. This is not related to Pop_OS!. Maybe something in the kernel or in the driver itself.

blagalucianflorin commented 2 years ago

I have also made a small script to let it run and change the brightness in real time:

I'd also like to add to this answer (btw thank you for finding a solution @nachomozo!)

I experienced some problems with permissions (that's why a temp file is used, check out Wireheadbe's answer below if don't experience issues with sudo echo 50 > /sys/class/backlight/amdgpu_bl0/brightness) and in my case another thing is that one brightness file ranges from 0 to 100 and another from 0 to 255, so I had to adapt the script a little bit:

#!/bin/sh

path=/sys/class/backlight/nvidia_wmi_ec_backlight

inotifywait -q -m -e close_write $path |
while read -r actual_brightness event; do
  brightness_var=$(expr $(expr $(cat $path/actual_brightness) \* 255) / 100)
  echo $brightness_var > /tmp/temp_brightness
  cp /tmp/temp_brightness /sys/class/backlight/amdgpu_bl0/brightness
  rm /tmp/temp_brightness
done

I have a Lenovo Legion Slim 7 with Vega 8 and an Nvidia 3060.

EDIT: Regarding the problem of auto-running the script at startup: you also need to run the script as root. I used the solution from here: https://askubuntu.com/a/290102, so:

sudo crontab -e

And then this at the end of the file

@reboot <path/to/your/script.sh>
Wireheadbe commented 2 years ago

This workaround + nachomozo's original path worked for my Legion 5 15ARH05. Many thanks! - finally able to run the 515 driver on Ubuntu as well. Note that the addition of "amdgpu.backlight=0" in GRUB_CMDLINE_LINUX_DEFAULT is also needed.

Small modification to not need a temp file:

#!/bin/sh
path=/sys/class/backlight/nvidia_0

inotifywait -q -m -e close_write $path |
while read -r actual_brightness event; do
  brightness_var=$(expr $(expr $(cat $path/actual_brightness) \* 255) / 100)
  echo $brightness_var > /sys/class/backlight/amdgpu_bl0/brightness
done
nachomozo commented 2 years ago

Regarding the permissions, I found out that by adding my username to the "video" group, I no longer need sudo to run the script.

sudo usermod -a -G video $USER

I hope that helps.

Thankyou @blagalucianflorin and @Wireheadbe for improving the script!

nachomozo commented 2 years ago

Well, it seems that by adding the user to the "video" group and setting the script as the gnome startup application, I have my brightness control working again.

In summary:

Add your user to the video group:

sudo usermod -a -G video $USER

Istall inotify-tools

sudo apt install inotify-tools

Create the script:

#!/bin/sh
path=/sys/class/backlight/nvidia_0

inotifywait -q -m -e close_write $path |
while read -r actual_brightness event; do
  brightness_var=$(expr $(expr $(cat $path/actual_brightness) \* 255) / 100)
  echo $brightness_var > /sys/class/backlight/amdgpu_bl0/brightness
done

Add it to gnome startup apps:

imagen

With this, everything should work fine.

krshrimali commented 2 years ago

Hi everyone, thanks! The above workarounds worked for me, but I had to enable "dynamic graphics" (discrete graphics was turned on in the BIOS). Is there a way to fix this for discrete graphics as well?

blagalucianflorin commented 2 years ago

Hi @krshrimali! From what I know (but don't quote me on it!), discrete graphics disables the integrated GPU altogether. I get the following lspci -k output:

With discrete graphis:

< 06:00.0 Non-Essential Instrumentation [1300]: Advanced Micro Devices, Inc. [AMD] Zeppelin/Raven/Raven2 PCIe Dummy Function (rev c5)
<   Subsystem: Lenovo Zeppelin/Raven/Raven2 PCIe Dummy Function

With dynamic graphics:

> 06:00.0 VGA compatible controller: Advanced Micro Devices, Inc. [AMD/ATI] Cezanne (rev c5)
>   Subsystem: Lenovo Cezanne
>   Kernel driver in use: amdgpu
>   Kernel modules: amdgpu

So the solution from this thread doesn't really make sense for discrete graphics as the OS only really sees one GPU when in discrete graphics. (also from my experience, using discrete graphics I didn't experience any brightness issues, what problems are you experiencing?).

I suggest, if you can, to just set the system in Dynamic graphics in BIOS and Hybrid graphics in Pop_OS. This way you get the better battery life of the integrated GPU with the performance of the dedicated GPU.

krshrimali commented 2 years ago

Hi, @blagalucianflorin - Thank you so much for your quick response, and context behind the thinking. Very helpful!

With discrete graphics, I was unable to change the brightness (though I could see the bar changing). I've changed it to dynamic graphics, and will use hybrid in Pop OS settings. That works fine for me. Thank you so much again!!

Wireheadbe commented 2 years ago

Only issue is that after a sleep, upon wake, (well at least here with 515), the nvidia driver seems to reload or such, causing the inotifywait to listen for a file which is no longer there, and is recreated. Hence, you need to relaunch the script.

Ideally, this bug is sent upstream to Nvidia.

nachomozo commented 2 years ago

You are right, the script stop listening after a sleep :disappointed:

Wireheadbe commented 2 years ago

Allright, found a workaround to the driver being reloaded after sleep events and because of that the inotifywatch listening to a file that isn't there anymore. We don't just watch one dir up, as is usual, but two dirs: small caveat: We might have some unneeded syncs from time to time, but meh: it survives sleeps - which is handy with a laptop :-)

Here's the basic script. It listens to "close" events on /sys/class/backlight. It first checks if that path is available:

#!/usr/bin/bash 
# script to move backlight info from nvidia to amdgpu_bl0
path=/sys/class/backlight

while true
do
  if [[ -d $path ]]
  then
    inotifywait -q -m -e close $path |
    while read -r brightness; do
      let brightness_var="$(cat $path/nvidia_0/brightness)*255/100"
      echo $brightness_var > /sys/class/backlight/amdgpu_bl0/brightness
    done 
  fi
  sleep 1
done

And then you can just start it in the root crontab so it loads upon boot:

@reboot /home/someone/script.sh
nachomozo commented 2 years ago

Allright, found a workaround to the driver being reloaded after sleep events and because of that the inotifywatch listening to a file that isn't there anymore. We don't just watch one dir up, as is usual, but two dirs: small caveat: We might have some unneeded syncs from time to time, but meh: it survives sleeps - which is handy with a laptop :-)

Here's the basic script. It listens to "close" events on /sys/class/backlight. It first checks if that path is available:

* if not: wait a second and try again, probably the device is still booting

* if yes: continue to start the inotifywatch as mentioned.
#!/usr/bin/bash 
# script to move backlight info from nvidia to amdgpu_bl0
path=/sys/class/backlight

while true
do
  if [[ -d $path ]]
  then
    inotifywait -q -m -e close $path |
    while read -r brightness; do
      let brightness_var="$(cat $path/nvidia_0/brightness)*255/100"
      echo $brightness_var > /sys/class/backlight/amdgpu_bl0/brightness
    done 
  fi
  sleep 1
done

And then you can just start it in the root crontab so it loads upon boot:

@reboot /home/someone/script.sh

Thank you @Wireheadbe it works perfectly.

amarkovits commented 2 years ago

The script works great for me except the sleep part. After sleep I don't have the /sys/class/backlight/nvidia_0 folder. I only have /sys/class/backlight/amdgpu_bl0

amarkovits commented 2 years ago

fun thing: changing the brightness from the system ui works fine. only the Fn keys are not working. image

Dan1jel commented 1 year ago

Dont know if this is allowed or not but i ended up using these commands, and added them to my keys instead. Only downlide is there is no overlay icon showing what procentage the brightness is at (what you get when using xdotool, but i noticed it was slower/buggier then gbus option).

Faster better option but no overlay icon:

# Increase brightness:
gdbus call --session --dest org.gnome.SettingsDaemon.Power --object-path /org/gnome/SettingsDaemon/Power --method org.gnome.SettingsDaemon.Power.Screen.StepUp
# Decrease brightness:
gdbus call --session --dest org.gnome.SettingsDaemon.Power --object-path /org/gnome/SettingsDaemon/Power --method org.gnome.SettingsDaemon.Power.Screen.StepDown

Slower and buggier but you get an overlay icon:

# Increase brightness:
xdotool key XF86MonBrightnessUp
# Decrease brightness:
xdotool key XF86MonBrightnessDown

Source 1: https://askubuntu.com/a/1107046/1113550 Source 2: https://askubuntu.com/a/1339651/1113550

Pintyadot commented 1 year ago

My Lenovo Legion Y540 Stopped the working of Brightness!!

Pintyadot commented 1 year ago

Dont know if this is allowed or not but i ended up using these commands, and added them to my keys instead. Only downlide is there is no overlay icon showing what procentage the brightness is at (what you get when using xdotool, but i noticed it was slower/buggier then gbus option).

Faster better option but no overlay icon:

# Increase brightness:
gdbus call --session --dest org.gnome.SettingsDaemon.Power --object-path /org/gnome/SettingsDaemon/Power --method org.gnome.SettingsDaemon.Power.Screen.StepUp
# Decrease brightness:
gdbus call --session --dest org.gnome.SettingsDaemon.Power --object-path /org/gnome/SettingsDaemon/Power --method org.gnome.SettingsDaemon.Power.Screen.StepDown

Slower and buggier but you get an overlay icon:

# Increase brightness:
xdotool key XF86MonBrightnessUp
# Decrease brightness:
xdotool key XF86MonBrightnessDown

Source 1: https://askubuntu.com/a/1107046/1113550 Source 2: https://askubuntu.com/a/1339651/1113550

Not Working for me

Dan1jel commented 1 year ago

Dont know if this is allowed or not but i ended up using these commands, and added them to my keys instead. Only downlide is there is no overlay icon showing what procentage the brightness is at (what you get when using xdotool, but i noticed it was slower/buggier then gbus option).

Faster better option but no overlay icon:

# Increase brightness:
gdbus call --session --dest org.gnome.SettingsDaemon.Power --object-path /org/gnome/SettingsDaemon/Power --method org.gnome.SettingsDaemon.Power.Screen.StepUp
# Decrease brightness:
gdbus call --session --dest org.gnome.SettingsDaemon.Power --object-path /org/gnome/SettingsDaemon/Power --method org.gnome.SettingsDaemon.Power.Screen.StepDown

Slower and buggier but you get an overlay icon:

# Increase brightness:
xdotool key XF86MonBrightnessUp
# Decrease brightness:
xdotool key XF86MonBrightnessDown

Source 1: https://askubuntu.com/a/1107046/1113550 Source 2: https://askubuntu.com/a/1339651/1113550

Not Working for me

What dose the output give you when typing one of the commands?

etorres07 commented 1 year ago

Having the same issue on 22.04 with nvidia-driver-525.

The only thing that worked for me was dropping back down to nvidia-driver-470.

leviport commented 1 year ago

@eduardoltorres what GPU do you have?

InsanityM commented 1 year ago

I have a gtx 1650 and it's the same in ubuntu 23.04 with driver 525, but with the open variant of 525 brightness is working

dpcdpc11 commented 1 year ago

Having the same issue on my Lenovo Thinkbook 16 G2 with a Ryzen 7 5800h with Radeon graphics + RTX 3060 onboard. The only way to fix it is to use the nvidia-driver-470 and Hybrid mode. I've tried all the solutions I could find online including the scrips presented here on this thread. Any other ideas?

etorres07 commented 1 year ago

Some package updates broke the nvidia-driver-470 workaround. However, no brightness issue after upgrading to nvidia-driver-535. Using system76-power graphics nvidia and "Discrete Graphics" in BIOS settings. Haven't tested with other configurations.

I have a ThinkPad X1 Extreme 2nd Gen with NVIDIA GeForce GTX 1650 Mobile / Max-Q and Intel i7-9750H (12) @ 4.500GHz.