mirror of
https://gitlab.com/asus-linux/asusctl.git
synced 2026-01-22 09:23:19 +01:00
Compare commits
21 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
9ffeb19c8c | ||
|
|
f61f62c219 | ||
|
|
bb70fd7b71 | ||
|
|
b80c860b7a | ||
|
|
3c7544f034 | ||
|
|
6746c2b654 | ||
|
|
8d59f89438 | ||
|
|
5753160e91 | ||
|
|
622cd9d943 | ||
|
|
2daa7f0811 | ||
|
|
05c53df0ed | ||
|
|
a7419cbc4c | ||
|
|
67ad38a7e6 | ||
|
|
e572ae2c62 | ||
|
|
24962eedc1 | ||
|
|
368d279ca5 | ||
|
|
9e4cc329ed | ||
|
|
d4702a166a | ||
|
|
925c709097 | ||
|
|
411788f72c | ||
|
|
4e4ea0035e |
16
CHANGELOG.md
16
CHANGELOG.md
@@ -5,6 +5,22 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [Unreleased]
|
||||
# [2.0.5] - 2020-09-29
|
||||
### Changed
|
||||
- Bugfixes
|
||||
|
||||
# [2.0.4] - 2020-09-24
|
||||
### Changed
|
||||
- Better and more verbose error handling and logging in many places.
|
||||
- Fix timeout for client waiting on reply for graphics switching
|
||||
|
||||
# [2.0.2] - 2020-09-21
|
||||
### Changed
|
||||
- graphics options via CLI are now a command block:
|
||||
+ `asusctl graphics`
|
||||
+ -m Mode <nvidia, hybrid, compute, integrated>
|
||||
+ -g Get current mode
|
||||
+ -f Force reboot or restart display manager without confirmation
|
||||
|
||||
# [2.0.0] - 2020-09-21
|
||||
### Changed
|
||||
|
||||
67
Cargo.lock
generated
67
Cargo.lock
generated
@@ -29,7 +29,7 @@ checksum = "cff77d8686867eceff3105329d4698d96c2391c176d5d03adc90c7389162b5b8"
|
||||
|
||||
[[package]]
|
||||
name = "asus-nb"
|
||||
version = "2.0.0"
|
||||
version = "2.0.4"
|
||||
dependencies = [
|
||||
"ctrl-gfx",
|
||||
"dbus",
|
||||
@@ -46,7 +46,7 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "asus-nb-ctrl"
|
||||
version = "2.0.0"
|
||||
version = "2.0.4"
|
||||
dependencies = [
|
||||
"asus-nb",
|
||||
"ctrl-gfx",
|
||||
@@ -69,7 +69,7 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "asus-notify"
|
||||
version = "1.0.0"
|
||||
version = "2.0.4"
|
||||
dependencies = [
|
||||
"asus-nb",
|
||||
"asus-nb-ctrl",
|
||||
@@ -152,13 +152,15 @@ checksum = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822"
|
||||
|
||||
[[package]]
|
||||
name = "chrono"
|
||||
version = "0.4.15"
|
||||
version = "0.4.18"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "942f72db697d8767c22d46a598e01f2d3b475501ea43d0db4f16d90259182d0b"
|
||||
checksum = "d021fddb7bd3e734370acfa4a83f34095571d8570c039f1420d77540f68d5772"
|
||||
dependencies = [
|
||||
"libc",
|
||||
"num-integer",
|
||||
"num-traits",
|
||||
"time",
|
||||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -189,7 +191,7 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "ctrl-gfx"
|
||||
version = "2.0.0"
|
||||
version = "2.1.1"
|
||||
dependencies = [
|
||||
"log",
|
||||
"sysfs-class",
|
||||
@@ -215,7 +217,7 @@ checksum = "cb582b60359da160a9477ee80f15c8d784c477e69c217ef2cdd4169c24ea380f"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
"syn 1.0.41",
|
||||
"syn 1.0.42",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -247,7 +249,7 @@ checksum = "946ee94e3dbf58fdd324f9ce245c7b238d46a66f00e86a020b71996349e46cce"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
"syn 1.0.41",
|
||||
"syn 1.0.42",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -273,7 +275,7 @@ dependencies = [
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
"rustversion",
|
||||
"syn 1.0.41",
|
||||
"syn 1.0.42",
|
||||
"synstructure",
|
||||
]
|
||||
|
||||
@@ -323,14 +325,14 @@ checksum = "915ef07c710d84733522461de2a734d4d62a3fd39a4d4f404c2f385ef8618d05"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
"syn 1.0.41",
|
||||
"syn 1.0.42",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "hermit-abi"
|
||||
version = "0.1.15"
|
||||
version = "0.1.16"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3deed196b6e7f9e44a2ae8d94225d80302d81208b1bb673fd21fe634645c85a9"
|
||||
checksum = "4c30f6d0bc6b00693347368a67d41b58f2fb851215ff1da49e90fe2c5c667151"
|
||||
dependencies = [
|
||||
"libc",
|
||||
]
|
||||
@@ -411,9 +413,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "libusb1-sys"
|
||||
version = "0.4.1"
|
||||
version = "0.4.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ca5c2a82e2c56537de7d1a163575049593667af689122fafbccc117bbaa59079"
|
||||
checksum = "1f02e930161703cc97c0aab3a905feb9740db03a80910f31ab0f8fa309223f39"
|
||||
dependencies = [
|
||||
"cc",
|
||||
"libc",
|
||||
@@ -577,7 +579,7 @@ dependencies = [
|
||||
"proc-macro-error-attr",
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
"syn 1.0.41",
|
||||
"syn 1.0.42",
|
||||
"version_check",
|
||||
]
|
||||
|
||||
@@ -594,9 +596,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.21"
|
||||
version = "1.0.23"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "36e28516df94f3dd551a587da5357459d9b36d945a7c37c3557928c1c2ff2a2c"
|
||||
checksum = "51ef7cd2518ead700af67bf9d1a658d90b6037d77110fd9c0445429d0ba1c6c9"
|
||||
dependencies = [
|
||||
"unicode-xid 0.2.1",
|
||||
]
|
||||
@@ -665,9 +667,9 @@ checksum = "cabe4fa914dec5870285fa7f71f602645da47c486e68486d2b4ceb4a343e90ac"
|
||||
|
||||
[[package]]
|
||||
name = "rog_fan_curve"
|
||||
version = "0.1.5"
|
||||
version = "0.1.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b9d3867a0df47bf57c6eebe8b2fb3c2e5c09586a23c715cd7963c2f090c9983f"
|
||||
checksum = "da77fe4a6ad41da874d83eca6a32075a5b8f6ad4778682bc1308075e7ef856a9"
|
||||
dependencies = [
|
||||
"serde",
|
||||
]
|
||||
@@ -702,7 +704,7 @@ checksum = "b9bdc5e856e51e685846fb6c13a1f5e5432946c2c90501bdc76a1319f19e29da"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
"syn 1.0.41",
|
||||
"syn 1.0.42",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -734,7 +736,7 @@ checksum = "f630a6370fd8e457873b4bd2ffdae75408bc291ba72be773772a4c2a065d9ae8"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
"syn 1.0.41",
|
||||
"syn 1.0.42",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -756,7 +758,7 @@ checksum = "2dc6b7951b17b051f3210b063f12cc17320e2fe30ae05b0fe2a3abb068551c76"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
"syn 1.0.41",
|
||||
"syn 1.0.42",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -767,7 +769,7 @@ checksum = "133659a15339456eeeb07572eb02a91c91e9815e9cbc89566944d2c8d3efdbf6"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
"syn 1.0.41",
|
||||
"syn 1.0.42",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -799,9 +801,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "1.0.41"
|
||||
version = "1.0.42"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6690e3e9f692504b941dc6c3b188fd28df054f7fb8469ab40680df52fdcc842b"
|
||||
checksum = "9c51d92969d209b54a98397e1b91c8ae82d8c87a7bb87df0b29aa2ad81454228"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
@@ -825,7 +827,7 @@ checksum = "b834f2d66f734cb897113e34aaff2f1ab4719ca946f9a7358dba8f8064148701"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
"syn 1.0.41",
|
||||
"syn 1.0.42",
|
||||
"unicode-xid 0.2.1",
|
||||
]
|
||||
|
||||
@@ -1040,9 +1042,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "zbus"
|
||||
version = "1.1.1"
|
||||
version = "1.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e941349efbc28a22449be1e7bdaac074c9f9d96b465f855af018aa1a4e99d0a6"
|
||||
checksum = "3f3d015ea4cb76e7f951e429086995126807372f80c9a2a29bf00fcfd31a50b0"
|
||||
dependencies = [
|
||||
"byteorder",
|
||||
"derivative",
|
||||
@@ -1055,19 +1057,18 @@ dependencies = [
|
||||
"serde_repr",
|
||||
"zbus_macros",
|
||||
"zvariant",
|
||||
"zvariant_derive",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "zbus_macros"
|
||||
version = "1.1.0"
|
||||
version = "1.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a153562b600280af9eaf6aff75132e1781e04bdcbb37ae03ebcc8286bb0ede42"
|
||||
checksum = "54567d486c1ece9268173866c227ac1e168aa5cdf983ae9d13aaf45767fdf679"
|
||||
dependencies = [
|
||||
"proc-macro-crate",
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
"syn 1.0.41",
|
||||
"syn 1.0.42",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -1091,5 +1092,5 @@ dependencies = [
|
||||
"proc-macro-crate",
|
||||
"proc-macro2",
|
||||
"quote 1.0.7",
|
||||
"syn 1.0.41",
|
||||
"syn 1.0.42",
|
||||
]
|
||||
|
||||
6
Makefile
6
Makefile
@@ -16,7 +16,7 @@ BIN_D=asusd
|
||||
BIN_N=asus-notify
|
||||
LEDCFG=asusd-ledmodes.toml
|
||||
X11CFG=90-nvidia-screen-G05.conf
|
||||
UDEVRULES=90-nvidia-pm.rules
|
||||
PMRULES=90-asusd-nvidia-pm.rules
|
||||
VERSION:=$(shell grep -Pm1 'version = "(\d.\d.\d)"' asus-nb-ctrl/Cargo.toml | cut -d'"' -f2)
|
||||
|
||||
DEBUG ?= 0
|
||||
@@ -42,7 +42,7 @@ install: all
|
||||
install -D -m 0755 "target/release/$(BIN_C)" "$(DESTDIR)$(bindir)/$(BIN_C)"
|
||||
install -D -m 0755 "target/release/$(BIN_D)" "$(DESTDIR)$(bindir)/$(BIN_D)"
|
||||
install -D -m 0755 "target/release/$(BIN_N)" "$(DESTDIR)$(bindir)/$(BIN_N)"
|
||||
install -D -m 0644 "data/$(UDEVRULES)" "$(DESTDIR)/lib/udev/rules.d/$(UDEVRULES)"
|
||||
install -D -m 0644 "data/$(PMRULES)" "$(DESTDIR)/lib/udev/rules.d/$(PMRULES)"
|
||||
install -D -m 0644 "data/$(BIN_D).rules" "$(DESTDIR)/lib/udev/rules.d/99-$(BIN_D).rules"
|
||||
install -D -m 0644 "data/$(LEDCFG)" "$(DESTDIR)$(sysconfdir)/asusd/$(LEDCFG)"
|
||||
install -D -m 0644 "data/$(BIN_D).conf" "$(DESTDIR)$(sysconfdir)/dbus-1/system.d/$(BIN_D).conf"
|
||||
@@ -57,7 +57,7 @@ uninstall:
|
||||
rm -f "$(DESTDIR)$(bindir)/$(BIN_C)"
|
||||
rm -f "$(DESTDIR)$(bindir)/$(BIN_D)"
|
||||
rm -f "$(DESTDIR)$(bindir)/$(BIN_N)"
|
||||
rm -f "$(DESTDIR)/lib/udev/rules.d/$(UDEVRULES)"
|
||||
rm -f "$(DESTDIR)/lib/udev/rules.d/$(PMRULES)"
|
||||
rm -f "$(DESTDIR)/lib/udev/rules.d/99-$(BIN_D).rules"
|
||||
rm -f "$(DESTDIR)$(sysconfdir)/dbus-1/system.d/$(BIN_D).conf"
|
||||
rm -f "$(DESTDIR)$(sysconfdir)/X11/xorg.conf.d/$(X11CFG)"
|
||||
|
||||
72
README.md
72
README.md
@@ -1,7 +1,12 @@
|
||||
# ASUS NB Ctrl
|
||||
|
||||
`asusd` is a utility for Linux to control many aspects of various ASUS laptops
|
||||
but can also be used with non-asus laptops with reduced features.
|
||||
|
||||
**NOTICE:**
|
||||
|
||||
This app is developed and tested on fedora only. Support is not provided for Arch or Arch based distros.
|
||||
|
||||
This program requires the kernel patch [here](https://www.spinics.net/lists/linux-input/msg68977.html) to be applied.
|
||||
Alternatively you may use the dkms module for 'hid-asus-rog` from one of the
|
||||
repositories [here](https://download.opensuse.org/repositories/home:/luke_nukem:/asus/).
|
||||
@@ -12,17 +17,12 @@ The patch enables the following in kernel:
|
||||
- Control of keyboard brightness using FN+Key combos (not RGB)
|
||||
- FN+F5 (fan) to toggle fan modes
|
||||
|
||||
You will not get RGB control in kernel (yet), and asusd is still required to
|
||||
change modes and RGB settings. The previous version of this program is named
|
||||
`rog-core` and takes full control of the interfaces required - if you can't
|
||||
apply the kernel patches then `rog-core` is still highly usable.
|
||||
You will not get RGB control in kernel (yet), and `asusd` + `asusctl` is required
|
||||
to change modes and RGB settings.
|
||||
|
||||
Many other patches for these laptops, AMD and Intel based, are working their way
|
||||
in to the kernel.
|
||||
|
||||
---
|
||||
asusd is a utility for Linux to control many aspects of various ASUS laptops.
|
||||
|
||||
## Discord
|
||||
|
||||
[Discord server link](https://discord.gg/PVyFzWj)
|
||||
@@ -54,9 +54,9 @@ will probably suffer another rename once it becomes generic enough to do so.
|
||||
- [X] Fancy fan control on G14 + G15 thanks to @Yarn1
|
||||
- [X] Graphics mode switching between iGPU, dGPU, and On-Demand
|
||||
|
||||
## FUNCTIONS
|
||||
# FUNCTIONS
|
||||
|
||||
### Graphics switching
|
||||
## Graphics switching
|
||||
|
||||
A new feature has been added to enable switching graphics modes. This can be disabled
|
||||
in the config with `"manage_gfx": false,`. Please be aware it is a work in progress.
|
||||
@@ -64,7 +64,34 @@ in the config with `"manage_gfx": false,`. Please be aware it is a work in progr
|
||||
The CLI option for this does not require root until it asks for it, and provides
|
||||
instructions.
|
||||
|
||||
### KEYBOARD BACKLIGHT MODES
|
||||
This switcher conflicts with other gpu switchers like optimus-manager, suse-prime
|
||||
or ubuntu-prime, system76-power, and bbswitch. If you have issues with `asusd`
|
||||
always defaulting to `integrated` mode on boot then you will need to check for
|
||||
stray configs blocking nvidia modules from loading in:
|
||||
- `/etc/modprobe.d/`
|
||||
- `/usr/lib/modprope.d/`
|
||||
|
||||
### Power management udev rule
|
||||
|
||||
If you have installed the Nvidia driver manually you will require the
|
||||
`data/90-asusd-nvidia-pm.rules` udev rule to be installed in `/etc/udev/rules.d/`.
|
||||
|
||||
### fedora and openSUSE
|
||||
|
||||
You *may* need a file `/etc/dracut.conf.d/90-nvidia-dracut-G05.conf` installed
|
||||
to stop dracut including the nvidia modules in the ramdisk.
|
||||
|
||||
```
|
||||
# filename /etc/dracut.conf.d/90-nvidia-dracut-G05.conf
|
||||
# Omit the nvidia driver from the ramdisk, to avoid needing to regenerate
|
||||
# the ramdisk on updates, and to ensure the power-management udev rules run
|
||||
# on module load
|
||||
omit_drivers+=" nvidia nvidia-drm nvidia-modeset nvidia-uvm "
|
||||
```
|
||||
|
||||
and run `dracut -f` after creating it.
|
||||
|
||||
## KEYBOARD BACKLIGHT MODES
|
||||
|
||||
Models GA401, GA502, GU502 support LED brightness change only (no RGB).
|
||||
|
||||
@@ -90,7 +117,9 @@ If you model isn't getting the correct led modes, you can edit the file
|
||||
|
||||
use `cat /sys/class/dmi/id/product_name` to get details about your laptop.
|
||||
|
||||
## Requirements for compiling
|
||||
# BUILDING
|
||||
|
||||
Requirements are:
|
||||
|
||||
- `rustc` + `cargo` + `make`
|
||||
- `libusb-1.0-0-dev`
|
||||
@@ -120,6 +149,11 @@ $ systemctl daemon-reload && systemctl restart asusd
|
||||
|
||||
You may also need to activate the service for debian install. If running Pop!_OS, I suggest disabling `system76-power` gnome-shell extension and systemd service.
|
||||
|
||||
If you would like to run this daemon on another non-ASUS laptop you can. You'll
|
||||
have all features available except the LED and AniMe control (further controllers
|
||||
can be added on request). You will need to install the alternative service from
|
||||
`data/asusd-alt.service`.
|
||||
|
||||
## Uninstalling
|
||||
|
||||
Run `sudo make uninstall` in the source repo, and remove `/etc/asusd/`.
|
||||
@@ -130,7 +164,7 @@ If there has been a config file format change your config will be overwritten. T
|
||||
become less of an issue once the feature set is nailed down. Work is happening to enable
|
||||
parsing of older configs and transferring settings to new.
|
||||
|
||||
# Usage
|
||||
# USAGE
|
||||
|
||||
**NOTE! Fan mode toggling requires a newer kernel**. I'm unsure when the patches
|
||||
required for it got merged - I've tested with the 5.6.6 kernel and above only.
|
||||
@@ -176,11 +210,11 @@ The daemon also saves the settings per mode as the keyboard does not do this
|
||||
itself - this means cycling through modes with the Aura keys will use the
|
||||
settings that were used via CLI.
|
||||
|
||||
Daemon mode creates a config file at `/etc/asusd/asusd.conf` which you can edit a
|
||||
Daemon mode creates a config file at `/etc/asusd/asusd.conf` which you can edit a
|
||||
little of. Most parts will be byte arrays, but you can adjust things like
|
||||
`mode_performance`.
|
||||
|
||||
## User daemon for notification via dbus
|
||||
## User NOTIFICATIONS via dbus
|
||||
|
||||
If you have a notifications handler set up, or are using KDE or Gnome then you
|
||||
can enable the user service to get basic notifications when something changes.
|
||||
@@ -189,7 +223,7 @@ can enable the user service to get basic notifications when something changes.
|
||||
systemctl --user enable asus-notify.service
|
||||
systemctl --user start asus-notify.service
|
||||
```
|
||||
# Other
|
||||
# OTHER
|
||||
|
||||
## DBUS Input
|
||||
|
||||
@@ -208,6 +242,14 @@ Please file a support request.
|
||||
- If charge limit or fan modes are not working, then you may require a kernel newer than 5.6.10.
|
||||
- AniMe device check is performed on start, if your device has one it will be detected.
|
||||
- GA14/GA401 and GA15/GA502/GU502, You will need kernel [patches](https://lab.retarded.farm/zappel/asus-rog-zephyrus-g14/-/tree/master/kernel_patches), these are on their way to the kernel upstream.
|
||||
- On fedora manually installed Nvidia driver requires a dracut config as follows:
|
||||
```
|
||||
# filename/etc/dracut.conf.d/90-nvidia-dracut-G05.conf
|
||||
# Omit the nvidia driver from the ramdisk, to avoid needing to regenerate
|
||||
# the ramdisk on updates, and to ensure the power-management udev rules run
|
||||
# on module load
|
||||
omit_drivers+=" nvidia nvidia-drm nvidia-modeset nvidia-uvm "
|
||||
```
|
||||
|
||||
# License
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
[package]
|
||||
name = "asus-nb-ctrl"
|
||||
version = "2.0.0"
|
||||
version = "2.0.5"
|
||||
license = "MPL-2.0"
|
||||
readme = "README.md"
|
||||
authors = ["Luke <luke@ljones.dev>"]
|
||||
@@ -22,7 +22,7 @@ name = "asusd"
|
||||
path = "src/daemon.rs"
|
||||
|
||||
[dependencies]
|
||||
ctrl-gfx = { path = "../ctrl-gfx" }
|
||||
ctrl-gfx = { path = "../ctrl-gfx" }
|
||||
asus-nb = { path = "../asus-nb" }
|
||||
rusb = "^0.6.0"
|
||||
udev = "^0.4.0"
|
||||
@@ -33,7 +33,7 @@ log = "^0.4.8"
|
||||
env_logger = "^0.7.1"
|
||||
|
||||
# async
|
||||
zbus = "1.1.1"
|
||||
zbus = "1.2.0"
|
||||
zvariant = "2.2.0"
|
||||
#tokio = { version = "^0.2.4", features = ["rt-threaded", "sync"] }
|
||||
|
||||
@@ -49,4 +49,4 @@ rog_fan_curve = { version = "0.1.5", features = ["serde"] }
|
||||
# cpu power management
|
||||
intel-pstate = "^0.2.1"
|
||||
|
||||
yansi-term = "^0.1"
|
||||
yansi-term = "^0.1"
|
||||
|
||||
@@ -23,15 +23,14 @@ pub struct Config {
|
||||
}
|
||||
|
||||
impl Config {
|
||||
/// `load` will attempt to read the config, but if it is not found it
|
||||
/// will create a new default config and write that out.
|
||||
/// `load` will attempt to read the config, and panic if the dir is missing
|
||||
pub fn load(mut self, supported_led_modes: &[u8]) -> Self {
|
||||
let mut file = OpenOptions::new()
|
||||
.read(true)
|
||||
.write(true)
|
||||
.create(true)
|
||||
.open(&CONFIG_PATH)
|
||||
.unwrap(); // okay to cause panic here
|
||||
.expect(&format!("The file {} or directory /etc/asusd/ is missing", CONFIG_PATH)); // okay to cause panic here
|
||||
let mut buf = String::new();
|
||||
if let Ok(l) = file.read_to_string(&mut buf) {
|
||||
if l == 0 {
|
||||
|
||||
@@ -40,7 +40,11 @@ impl crate::ZbusAdd for CtrlAnimeDisplay {
|
||||
fn add_to_server(self, server: &mut zbus::ObjectServer) {
|
||||
server
|
||||
.at(&"/org/asuslinux/Anime".try_into().unwrap(), self)
|
||||
.unwrap();
|
||||
.map_err(|err| {
|
||||
warn!("CtrlAnimeDisplay: add_to_server {}", err);
|
||||
err
|
||||
})
|
||||
.ok();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -16,22 +16,26 @@ pub struct CtrlCharge {
|
||||
config: Arc<Mutex<Config>>,
|
||||
}
|
||||
|
||||
trait Dbus {
|
||||
fn set_limit(&mut self, charge: u8);
|
||||
fn limit(&self) -> i8;
|
||||
fn notify_charge(&self, limit: u8) -> zbus::Result<()>;
|
||||
}
|
||||
|
||||
#[dbus_interface(name = "org.asuslinux.Daemon")]
|
||||
impl Dbus for CtrlCharge {
|
||||
fn set_limit(&mut self, limit: u8) {
|
||||
impl CtrlCharge {
|
||||
pub fn set_limit(&mut self, limit: u8) {
|
||||
if let Ok(mut config) = self.config.try_lock() {
|
||||
self.set(limit, &mut config).unwrap();
|
||||
self.notify_charge(limit).unwrap();
|
||||
self.set(limit, &mut config)
|
||||
.map_err(|err| {
|
||||
warn!("CtrlCharge: set_limit {}", err);
|
||||
err
|
||||
})
|
||||
.ok();
|
||||
self.notify_charge(limit)
|
||||
.map_err(|err| {
|
||||
warn!("CtrlCharge: set_limit {}", err);
|
||||
err
|
||||
})
|
||||
.ok();
|
||||
}
|
||||
}
|
||||
|
||||
fn limit(&self) -> i8 {
|
||||
pub fn limit(&self) -> i8 {
|
||||
if let Ok(config) = self.config.try_lock() {
|
||||
return config.bat_charge_limit as i8;
|
||||
}
|
||||
@@ -39,14 +43,18 @@ impl Dbus for CtrlCharge {
|
||||
}
|
||||
|
||||
#[dbus_interface(signal)]
|
||||
fn notify_charge(&self, limit: u8) -> zbus::Result<()>;
|
||||
pub fn notify_charge(&self, limit: u8) -> zbus::Result<()>;
|
||||
}
|
||||
|
||||
impl crate::ZbusAdd for CtrlCharge {
|
||||
fn add_to_server(self, server: &mut zbus::ObjectServer) {
|
||||
server
|
||||
.at(&"/org/asuslinux/Charge".try_into().unwrap(), self)
|
||||
.unwrap();
|
||||
.map_err(|err| {
|
||||
warn!("CtrlCharge: add_to_server {}", err);
|
||||
err
|
||||
})
|
||||
.ok();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -45,6 +45,16 @@ impl DbusFanAndCpu {
|
||||
}
|
||||
}
|
||||
|
||||
fn active_profile_name(&mut self) -> String {
|
||||
if let Ok(ctrl) = self.inner.try_lock() {
|
||||
if let Ok(mut cfg) = ctrl.config.try_lock() {
|
||||
cfg.read();
|
||||
return cfg.active_profile.clone();
|
||||
}
|
||||
}
|
||||
"Failed".to_string()
|
||||
}
|
||||
|
||||
fn profile(&mut self) -> String {
|
||||
if let Ok(ctrl) = self.inner.try_lock() {
|
||||
if let Ok(mut cfg) = ctrl.config.try_lock() {
|
||||
@@ -79,7 +89,11 @@ impl crate::ZbusAdd for DbusFanAndCpu {
|
||||
fn add_to_server(self, server: &mut zbus::ObjectServer) {
|
||||
server
|
||||
.at(&"/org/asuslinux/Profile".try_into().unwrap(), self)
|
||||
.unwrap();
|
||||
.map_err(|err| {
|
||||
warn!("DbusFanAndCpu: {}", err);
|
||||
err
|
||||
})
|
||||
.ok();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -311,7 +325,7 @@ impl CtrlFanAndCPU {
|
||||
|
||||
let boost = if mode_config.turbo { "1" } else { "0" }; // opposite of Intel
|
||||
file.write_all(boost.as_bytes())
|
||||
.map_err(|err| RogError::Write(AMD_BOOST_PATH.into(), err))?;
|
||||
.map_err(|err| RogError::Write(AMD_BOOST_PATH.into(), err))?;
|
||||
info!("AMD CPU Turbo: {}", boost);
|
||||
}
|
||||
Ok(())
|
||||
|
||||
@@ -42,7 +42,7 @@ impl crate::ZbusAdd for DbusKbdBacklight {
|
||||
fn add_to_server(self, server: &mut zbus::ObjectServer) {
|
||||
server
|
||||
.at(&"/org/asuslinux/Led".try_into().unwrap(), self)
|
||||
.unwrap();
|
||||
.ok();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -58,10 +58,11 @@ impl DbusKbdBacklight {
|
||||
.unwrap_or_else(|err| warn!("{}", err));
|
||||
}
|
||||
_ => {
|
||||
let json = serde_json::to_string(&data).unwrap();
|
||||
ctrl.do_command(data, &mut cfg)
|
||||
.unwrap_or_else(|err| warn!("{}", err));
|
||||
self.notify_led(&json).unwrap();
|
||||
if let Ok(json) = serde_json::to_string(&data) {
|
||||
ctrl.do_command(data, &mut cfg)
|
||||
.unwrap_or_else(|err| warn!("{}", err));
|
||||
self.notify_led(&json).ok();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -151,7 +152,12 @@ impl crate::CtrlTask for CtrlKbdBacklight {
|
||||
let mut file = OpenOptions::new()
|
||||
.read(true)
|
||||
.open(&self.bright_node)
|
||||
.map_err(|err| RogError::Path((&self.bright_node).into(), err))?;
|
||||
.map_err(|err| {
|
||||
match err.kind() {
|
||||
std::io::ErrorKind::NotFound => RogError::MissingLedBrightNode((&self.bright_node).into(), err),
|
||||
_ => RogError::Path((&self.bright_node).into(), err),
|
||||
}
|
||||
})?;
|
||||
let mut buf = [0u8; 1];
|
||||
file.read_exact(&mut buf)
|
||||
.map_err(|err| RogError::Read("buffer".into(), err))?;
|
||||
@@ -233,8 +239,11 @@ impl CtrlKbdBacklight {
|
||||
RogError::Udev("parent_with_subsystem_devtype failed".into(), err)
|
||||
})?
|
||||
{
|
||||
if parent.attribute_value("idProduct").unwrap() == id_product {
|
||||
// && device.parent().unwrap().sysnum().unwrap() == 3
|
||||
if parent
|
||||
.attribute_value("idProduct")
|
||||
.ok_or(RogError::NotFound("LED idProduct".into()))?
|
||||
== id_product
|
||||
{
|
||||
if let Some(dev_node) = device.devnode() {
|
||||
info!("Using device at: {:?} for LED control", dev_node);
|
||||
return Ok(dev_node.to_string_lossy().to_string());
|
||||
@@ -264,13 +273,17 @@ impl CtrlKbdBacklight {
|
||||
RogError::Udev("match_property failed".into(), err)
|
||||
})?;
|
||||
|
||||
for device in enumerator.scan_devices().map_err(|err| {
|
||||
warn!("{}", err);
|
||||
err
|
||||
}).map_err(|err| {
|
||||
warn!("{}", err);
|
||||
RogError::Udev("scan_devices failed".into(), err)
|
||||
})? {
|
||||
for device in enumerator
|
||||
.scan_devices()
|
||||
.map_err(|err| {
|
||||
warn!("{}", err);
|
||||
err
|
||||
})
|
||||
.map_err(|err| {
|
||||
warn!("{}", err);
|
||||
RogError::Udev("scan_devices failed".into(), err)
|
||||
})?
|
||||
{
|
||||
if let Some(dev_node) = device.devnode() {
|
||||
if let Some(inum) = device.property_value("ID_USB_INTERFACE_NUM") {
|
||||
if let Some(iface) = iface {
|
||||
@@ -298,8 +311,7 @@ impl CtrlKbdBacklight {
|
||||
fn write_bytes(&self, message: &[u8]) -> Result<(), RogError> {
|
||||
if let Some(led_node) = &self.led_node {
|
||||
if let Ok(mut file) = OpenOptions::new().write(true).open(led_node) {
|
||||
file.write_all(message).unwrap();
|
||||
return Ok(());
|
||||
return file.write_all(message).map_err(|err| RogError::Write("write_bytes".into(), err));
|
||||
}
|
||||
}
|
||||
Err(RogError::NotSupported)
|
||||
|
||||
@@ -17,6 +17,8 @@ use std::sync::Mutex;
|
||||
|
||||
use zbus::fdo;
|
||||
use zbus::Connection;
|
||||
use std::convert::Into;
|
||||
use std::convert::TryInto;
|
||||
|
||||
pub fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||
let mut logger = env_logger::Builder::new();
|
||||
@@ -126,11 +128,19 @@ fn start_daemon() -> Result<(), Box<dyn Error>> {
|
||||
|
||||
for ctrl in tasks.iter() {
|
||||
if let Ok(mut lock) = ctrl.try_lock() {
|
||||
lock.do_task().unwrap();
|
||||
lock.do_task().map_err(|err| {
|
||||
warn!("do_task error: {}", err);
|
||||
})
|
||||
.ok();
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
object_server.with(&"/org/asuslinux/Charge".try_into()?, |obj: &CtrlCharge| {
|
||||
let x = obj.limit();
|
||||
obj.notify_charge(x as u8)
|
||||
})?;
|
||||
|
||||
loop {
|
||||
if let Err(err) = object_server.try_handle_next() {
|
||||
eprintln!("{}", err);
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
use std::fmt;
|
||||
use std::convert::From;
|
||||
use intel_pstate::PStateError;
|
||||
use rog_fan_curve::CurveError;
|
||||
use std::convert::From;
|
||||
use std::fmt;
|
||||
|
||||
#[derive(Debug)]
|
||||
pub enum RogError {
|
||||
@@ -19,6 +19,7 @@ pub enum RogError {
|
||||
FanCurve(CurveError),
|
||||
DoTask(String),
|
||||
MissingFunction(String),
|
||||
MissingLedBrightNode(String, std::io::Error),
|
||||
}
|
||||
|
||||
impl fmt::Display for RogError {
|
||||
@@ -39,6 +40,7 @@ impl fmt::Display for RogError {
|
||||
RogError::FanCurve(err) => write!(f, "Custom fan-curve error: {}", err),
|
||||
RogError::DoTask(deets) => write!(f, "Task error: {}", deets),
|
||||
RogError::MissingFunction(deets) => write!(f, "Missing functionality: {}", deets),
|
||||
RogError::MissingLedBrightNode(path, error) => write!(f, "Led node at {} is missing, please check you have the required patch or dkms module installed: {}", path, error),
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -55,4 +57,4 @@ impl From<CurveError> for RogError {
|
||||
fn from(err: CurveError) -> Self {
|
||||
RogError::FanCurve(err)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,7 +19,7 @@ use config::Config;
|
||||
use crate::error::RogError;
|
||||
use zbus::ObjectServer;
|
||||
|
||||
pub static VERSION: &str = "2.0.0";
|
||||
pub static VERSION: &str = env!("CARGO_PKG_VERSION");
|
||||
|
||||
pub trait Reloadable {
|
||||
fn reload(&mut self) -> Result<(), RogError>;
|
||||
|
||||
@@ -8,6 +8,7 @@ use daemon::ctrl_fan_cpu::FanLevel;
|
||||
use gumdrop::Options;
|
||||
use log::LevelFilter;
|
||||
use std::io::Write;
|
||||
use std::process::Command;
|
||||
use yansi_term::Colour::Green;
|
||||
use yansi_term::Colour::Red;
|
||||
|
||||
@@ -23,18 +24,18 @@ struct CLIStart {
|
||||
pwr_profile: Option<FanLevel>,
|
||||
#[options(meta = "CHRG", help = "<20-100>")]
|
||||
chg_limit: Option<u8>,
|
||||
#[options(help = "Set graphics mode: <nvidia, hybrid, compute, integrated>")]
|
||||
graphics: Option<GfxVendors>,
|
||||
#[options(command)]
|
||||
command: Option<Command>,
|
||||
command: Option<CliCommand>,
|
||||
}
|
||||
|
||||
#[derive(Options)]
|
||||
enum Command {
|
||||
enum CliCommand {
|
||||
#[options(help = "Set the keyboard lighting from built-in modes")]
|
||||
LedMode(LedModeCommand),
|
||||
#[options(help = "Create and configure profiles")]
|
||||
Profile(ProfileCommand),
|
||||
#[options(help = "Set the graphics mode")]
|
||||
Graphics(GraphicsCommand),
|
||||
}
|
||||
|
||||
#[derive(Options)]
|
||||
@@ -45,6 +46,20 @@ struct LedModeCommand {
|
||||
command: Option<SetAuraBuiltin>,
|
||||
}
|
||||
|
||||
#[derive(Options)]
|
||||
struct GraphicsCommand {
|
||||
#[options(help = "print help message")]
|
||||
help: bool,
|
||||
#[options(help = "Set graphics mode: <nvidia, hybrid, compute, integrated>")]
|
||||
mode: Option<GfxVendors>,
|
||||
#[options(help = "Get the current mode")]
|
||||
get: bool,
|
||||
#[options(help = "Get the current power status")]
|
||||
pow: bool,
|
||||
#[options(help = "Do not ask for confirmation")]
|
||||
force: bool,
|
||||
}
|
||||
|
||||
fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||
let mut logger = env_logger::Builder::new();
|
||||
logger
|
||||
@@ -62,14 +77,15 @@ fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||
let writer = AuraDbusClient::new()?;
|
||||
|
||||
match parsed.command {
|
||||
Some(Command::LedMode(mode)) => {
|
||||
Some(CliCommand::LedMode(mode)) => {
|
||||
if let Some(command) = mode.command {
|
||||
writer.write_builtin_mode(&command.into())?
|
||||
}
|
||||
}
|
||||
Some(Command::Profile(command)) => {
|
||||
Some(CliCommand::Profile(command)) => {
|
||||
writer.write_profile_command(&ProfileEvent::Cli(command))?
|
||||
}
|
||||
Some(CliCommand::Graphics(command)) => do_gfx(command, &writer)?,
|
||||
None => (),
|
||||
}
|
||||
|
||||
@@ -82,52 +98,94 @@ fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||
if let Some(chg_limit) = parsed.chg_limit {
|
||||
writer.write_charge_limit(chg_limit)?;
|
||||
}
|
||||
if let Some(gfx) = parsed.graphics {
|
||||
println!("Updating settings, please wait...");
|
||||
println!("If this takes longer than 30s, ctrl+c then check journalctl");
|
||||
Ok(())
|
||||
}
|
||||
|
||||
writer.write_gfx_mode(gfx)?;
|
||||
fn do_gfx(
|
||||
command: GraphicsCommand,
|
||||
writer: &AuraDbusClient,
|
||||
) -> Result<(), Box<dyn std::error::Error>> {
|
||||
if let Some(mode) = command.mode {
|
||||
println!("Updating settings, please wait...");
|
||||
println!("If this takes longer than 30s, ctrl+c then check `journalctl -b -u asusd`");
|
||||
|
||||
writer.write_gfx_mode(mode)?;
|
||||
let res = writer.wait_gfx_changed()?;
|
||||
match res.as_str() {
|
||||
"reboot" => println!(
|
||||
"{}\n{}",
|
||||
Green.paint("\nGraphics vendor mode changed successfully\n"),
|
||||
Red.paint("\nPlease reboot to complete switch to iGPU\n")
|
||||
),
|
||||
"reboot" => {
|
||||
println!(
|
||||
"{}",
|
||||
Green.paint("\nGraphics vendor mode changed successfully\n"),
|
||||
);
|
||||
do_gfx_action(
|
||||
command.force,
|
||||
Command::new("systemctl").arg("reboot").arg("-i"),
|
||||
"Reboot Linux PC",
|
||||
"Please reboot when ready",
|
||||
)?;
|
||||
}
|
||||
"restartx" => {
|
||||
println!(
|
||||
"{}",
|
||||
Green.paint("\nGraphics vendor mode changed successfully\n")
|
||||
);
|
||||
restart_x()?;
|
||||
do_gfx_action(
|
||||
command.force,
|
||||
Command::new("systemctl")
|
||||
.arg("restart")
|
||||
.arg("display-manager.service"),
|
||||
"Restart display-manager server",
|
||||
"Please restart display-manager when ready",
|
||||
)?;
|
||||
std::process::exit(1)
|
||||
}
|
||||
_ => std::process::exit(-1),
|
||||
}
|
||||
std::process::exit(-1)
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn restart_x() -> Result<(), Box<dyn std::error::Error>> {
|
||||
println!("Restart X server? y/n");
|
||||
|
||||
let mut buf = String::new();
|
||||
std::io::stdin().read_line(&mut buf).expect("Input failed");
|
||||
let input = buf.chars().next().unwrap() as char;
|
||||
|
||||
if input == 'Y' || input == 'y' {
|
||||
println!("Restarting X server");
|
||||
let status = std::process::Command::new("systemctl")
|
||||
.arg("restart")
|
||||
.arg("display-manager.service")
|
||||
.status()?;
|
||||
|
||||
if !status.success() {
|
||||
println!("systemctl: display-manager returned with {}", status);
|
||||
if command.get {
|
||||
let res = writer.get_gfx_mode()?;
|
||||
println!("Current graphics mode: {}", res);
|
||||
}
|
||||
if command.pow {
|
||||
let res = writer.get_gfx_pwr()?;
|
||||
if res.contains("active") {
|
||||
println!("Current power status: {}", Red.paint(&format!("{}", res)));
|
||||
} else {
|
||||
println!("Current power status: {}", Green.paint(&format!("{}", res)));
|
||||
}
|
||||
} else {
|
||||
println!("{}", Red.paint("Cancelled. Please restart X when ready"));
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn do_gfx_action(
|
||||
no_confirm: bool,
|
||||
command: &mut Command,
|
||||
ask_msg: &str,
|
||||
cancel_msg: &str,
|
||||
) -> Result<(), Box<dyn std::error::Error>> {
|
||||
println!("{}? y/n", ask_msg);
|
||||
|
||||
let mut buf = String::new();
|
||||
if no_confirm {
|
||||
let status = command.status()?;
|
||||
|
||||
if !status.success() {
|
||||
println!("systemctl: returned with {}", status);
|
||||
}
|
||||
}
|
||||
|
||||
std::io::stdin().read_line(&mut buf).expect("Input failed");
|
||||
let input = buf.chars().next().unwrap() as char;
|
||||
|
||||
if input == 'Y' || input == 'y' || no_confirm {
|
||||
let status = command.status()?;
|
||||
|
||||
if !status.success() {
|
||||
println!("systemctl: returned with {}", status);
|
||||
}
|
||||
} else {
|
||||
println!("{}", Red.paint(&format!("{}", cancel_msg)));
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
[package]
|
||||
name = "asus-nb"
|
||||
version = "2.0.0"
|
||||
version = "2.0.4"
|
||||
license = "MPL-2.0"
|
||||
readme = "README.md"
|
||||
authors = ["Luke <luke@ljones.dev>"]
|
||||
|
||||
@@ -14,9 +14,10 @@ fn main() {
|
||||
let mut matrix = AniMeMatrix::new();
|
||||
|
||||
// Aligned left
|
||||
for px in pixels {
|
||||
for (i, px) in pixels.iter().enumerate() {
|
||||
if (px.x as usize / 2) < WIDTH && (px.y as usize) < HEIGHT && px.x % 2 == 0 {
|
||||
matrix.get_mut()[px.y as usize][px.x as usize / 2] = px.color as u8;
|
||||
let mut c = px.color as u32;
|
||||
matrix.get_mut()[px.y as usize][px.x as usize / 2] = c as u8;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -17,7 +17,7 @@ pub const ANIME_PANE2_PREFIX: [u8; 7] = [0x5e, 0xc0, 0x02, 0x74, 0x02, 0x73, 0x0
|
||||
/// The resolution is 34x56 (1904) but only 1,215 LEDs in the top-left are used.
|
||||
/// The display is available only on select GA401 models.
|
||||
///
|
||||
/// Actual image ration when displayed is stretched width.
|
||||
/// Actual image ratio when displayed is stretched width.
|
||||
///
|
||||
/// Data structure should be nested array of [[u8; 33]; 56]
|
||||
pub struct AniMeDbusWriter {
|
||||
|
||||
@@ -46,9 +46,9 @@ impl AniMeMatrix {
|
||||
// Write the top block of LEDs (first 7 rows)
|
||||
if count < 6 {
|
||||
if count % 2 != 0 {
|
||||
print!(" ");
|
||||
print!(" ");
|
||||
} else {
|
||||
print!(" ");
|
||||
print!("");
|
||||
}
|
||||
let tmp = if count == 0 || count == 1 || count == 3 || count == 5 {
|
||||
row[1..].iter()
|
||||
@@ -56,7 +56,7 @@ impl AniMeMatrix {
|
||||
row.iter()
|
||||
};
|
||||
for x in tmp {
|
||||
print!(" {}", RGB(*x, *x, *x).paint(&format!("{:#04X}", x)));
|
||||
print!(" {}", RGB(*x, *x, *x).paint("XY"));
|
||||
}
|
||||
|
||||
println!();
|
||||
@@ -76,13 +76,13 @@ impl AniMeMatrix {
|
||||
let index = row.len() - prog_row_len;
|
||||
|
||||
if count % 2 == 0 {
|
||||
print!(" ");
|
||||
print!(" ");
|
||||
}
|
||||
for (i, x) in row.iter().enumerate() {
|
||||
if i >= index {
|
||||
print!(" {}", RGB(*x, *x, *x).paint(&format!("{:#04X}", x)));
|
||||
print!(" {}", RGB(*x, *x, *x).paint("XY"));
|
||||
} else {
|
||||
print!(" ");
|
||||
print!(" ");
|
||||
}
|
||||
}
|
||||
println!();
|
||||
|
||||
@@ -2,7 +2,6 @@ use super::*;
|
||||
use crate::fancy::KeyColourArray;
|
||||
use crate::profile::ProfileEvent;
|
||||
use ctrl_gfx::vendors::GfxVendors;
|
||||
use dbus::channel::Sender;
|
||||
use dbus::{blocking::Connection, Message};
|
||||
use std::error::Error;
|
||||
use std::sync::{
|
||||
@@ -11,14 +10,22 @@ use std::sync::{
|
||||
};
|
||||
use std::{thread, time::Duration};
|
||||
|
||||
use crate::dbus_gfx::OrgAsuslinuxDaemonNotifyGfx;
|
||||
use crate::dbus_ledmode::OrgAsuslinuxDaemonNotifyLed;
|
||||
use crate::dbus_profile::OrgAsuslinuxDaemonNotifyProfile;
|
||||
use crate::dbus_charge::OrgAsuslinuxDaemonNotifyCharge;
|
||||
use crate::dbus_charge::{OrgAsuslinuxDaemonNotifyCharge, OrgAsuslinuxDaemon as OrgAsuslinuxDaemonCharge};
|
||||
use crate::dbus_gfx::{
|
||||
OrgAsuslinuxDaemon as OrgAsuslinuxDaemonGfx, OrgAsuslinuxDaemonNotifyAction,
|
||||
OrgAsuslinuxDaemonNotifyGfx,
|
||||
};
|
||||
use crate::dbus_ledmode::{
|
||||
OrgAsuslinuxDaemon as OrgAsuslinuxDaemonLed, OrgAsuslinuxDaemonNotifyLed,
|
||||
};
|
||||
use crate::dbus_profile::{
|
||||
OrgAsuslinuxDaemon as OrgAsuslinuxDaemonProfile, OrgAsuslinuxDaemonNotifyProfile,
|
||||
};
|
||||
|
||||
// Signals separated out
|
||||
pub struct CtrlSignals {
|
||||
pub gfx_signal: Arc<Mutex<Option<String>>>,
|
||||
pub gfx_vendor_signal: Arc<Mutex<Option<String>>>,
|
||||
pub gfx_action_signal: Arc<Mutex<Option<String>>>,
|
||||
pub profile_signal: Arc<Mutex<Option<String>>>,
|
||||
pub ledmode_signal: Arc<Mutex<Option<AuraModes>>>,
|
||||
pub charge_signal: Arc<Mutex<Option<u8>>>,
|
||||
@@ -30,11 +37,11 @@ impl CtrlSignals {
|
||||
let proxy = connection.with_proxy(
|
||||
"org.asuslinux.Daemon",
|
||||
"/org/asuslinux/Gfx",
|
||||
Duration::from_millis(5000),
|
||||
Duration::from_secs(2),
|
||||
);
|
||||
|
||||
let gfx_signal = Arc::new(Mutex::new(None));
|
||||
let gfx_res1 = gfx_signal.clone();
|
||||
let gfx_vendor_signal = Arc::new(Mutex::new(None));
|
||||
let gfx_res1 = gfx_vendor_signal.clone();
|
||||
|
||||
let _x = proxy.match_signal(
|
||||
move |sig: OrgAsuslinuxDaemonNotifyGfx, _: &Connection, _: &Message| {
|
||||
@@ -45,11 +52,23 @@ impl CtrlSignals {
|
||||
},
|
||||
)?;
|
||||
|
||||
let gfx_action_signal = Arc::new(Mutex::new(None));
|
||||
let gfx_res1 = gfx_action_signal.clone();
|
||||
|
||||
let _x = proxy.match_signal(
|
||||
move |sig: OrgAsuslinuxDaemonNotifyAction, _: &Connection, _: &Message| {
|
||||
if let Ok(mut lock) = gfx_res1.lock() {
|
||||
*lock = Some(sig.action);
|
||||
}
|
||||
true
|
||||
},
|
||||
)?;
|
||||
|
||||
//
|
||||
let proxy = connection.with_proxy(
|
||||
"org.asuslinux.Daemon",
|
||||
"/org/asuslinux/Profile",
|
||||
Duration::from_millis(5000),
|
||||
Duration::from_secs(2),
|
||||
);
|
||||
|
||||
let profile_signal = Arc::new(Mutex::new(None));
|
||||
@@ -68,7 +87,7 @@ impl CtrlSignals {
|
||||
let proxy = connection.with_proxy(
|
||||
"org.asuslinux.Daemon",
|
||||
"/org/asuslinux/Led",
|
||||
Duration::from_millis(5000),
|
||||
Duration::from_secs(2),
|
||||
);
|
||||
|
||||
let ledmode_signal = Arc::new(Mutex::new(None));
|
||||
@@ -89,7 +108,7 @@ impl CtrlSignals {
|
||||
let proxy = connection.with_proxy(
|
||||
"org.asuslinux.Daemon",
|
||||
"/org/asuslinux/Charge",
|
||||
Duration::from_millis(5000),
|
||||
Duration::from_secs(2),
|
||||
);
|
||||
|
||||
let charge_signal = Arc::new(Mutex::new(None));
|
||||
@@ -98,14 +117,15 @@ impl CtrlSignals {
|
||||
let _x = proxy.match_signal(
|
||||
move |sig: OrgAsuslinuxDaemonNotifyCharge, _: &Connection, _: &Message| {
|
||||
if let Ok(mut lock) = charge_res1.lock() {
|
||||
*lock = Some(sig.limit);
|
||||
*lock = Some(sig.limit);
|
||||
}
|
||||
true
|
||||
},
|
||||
)?;
|
||||
|
||||
Ok(CtrlSignals {
|
||||
gfx_signal,
|
||||
gfx_vendor_signal,
|
||||
gfx_action_signal,
|
||||
profile_signal,
|
||||
ledmode_signal,
|
||||
charge_signal,
|
||||
@@ -148,8 +168,8 @@ impl AuraDbusClient {
|
||||
|
||||
pub fn wait_gfx_changed(&self) -> Result<String, Box<dyn Error>> {
|
||||
loop {
|
||||
self.connection.process(Duration::from_micros(500))?;
|
||||
if let Ok(lock) = self.signals.gfx_signal.lock() {
|
||||
self.connection.process(Duration::from_millis(1))?;
|
||||
if let Ok(lock) = self.signals.gfx_action_signal.lock() {
|
||||
if let Some(stuff) = lock.as_ref() {
|
||||
return Ok(stuff.to_string());
|
||||
}
|
||||
@@ -162,11 +182,12 @@ impl AuraDbusClient {
|
||||
#[inline]
|
||||
pub fn init_effect(&self) -> Result<(), Box<dyn std::error::Error>> {
|
||||
let mode = AuraModes::PerKey(vec![vec![]]);
|
||||
let mut msg =
|
||||
Message::new_method_call(DBUS_NAME, "/org/asuslinux/Led", DBUS_IFACE, "SetLedMode")?
|
||||
.append1(serde_json::to_string(&mode)?);
|
||||
msg.set_no_reply(true);
|
||||
self.connection.send(msg).unwrap();
|
||||
let proxy = self.connection.with_proxy(
|
||||
"org.asuslinux.Daemon",
|
||||
"/org/asuslinux/Led",
|
||||
Duration::from_secs(2),
|
||||
);
|
||||
proxy.set_led_mode(&serde_json::to_string(&mode)?)?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
@@ -185,13 +206,12 @@ impl AuraDbusClient {
|
||||
vecs.push(v.to_vec());
|
||||
}
|
||||
let mode = AuraModes::PerKey(vecs);
|
||||
let mut msg =
|
||||
Message::new_method_call(DBUS_NAME, "/org/asuslinux/Led", DBUS_IFACE, "SetLedMode")?
|
||||
.append1(serde_json::to_string(&mode)?);
|
||||
msg.set_no_reply(true);
|
||||
self.connection.send(msg).unwrap();
|
||||
|
||||
self.write_keyboard_leds(&mode)?;
|
||||
|
||||
thread::sleep(Duration::from_micros(self.block_time));
|
||||
self.connection.process(Duration::from_micros(500))?;
|
||||
|
||||
if self.stop.load(Ordering::Relaxed) {
|
||||
println!("Keyboard backlight was changed, exiting");
|
||||
std::process::exit(1)
|
||||
@@ -201,35 +221,56 @@ impl AuraDbusClient {
|
||||
|
||||
#[inline]
|
||||
pub fn write_keyboard_leds(&self, mode: &AuraModes) -> Result<(), Box<dyn std::error::Error>> {
|
||||
let mut msg =
|
||||
Message::new_method_call(DBUS_NAME, "/org/asuslinux/Led", DBUS_IFACE, "SetLedMode")?
|
||||
.append1(serde_json::to_string(mode)?);
|
||||
msg.set_no_reply(true);
|
||||
self.connection.send(msg).unwrap();
|
||||
let proxy = self.connection.with_proxy(
|
||||
"org.asuslinux.Daemon",
|
||||
"/org/asuslinux/Led",
|
||||
Duration::from_secs(2),
|
||||
);
|
||||
proxy.set_led_mode(&serde_json::to_string(mode)?)?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn get_gfx_pwr(&self) -> Result<String, Box<dyn std::error::Error>> {
|
||||
let proxy = self.connection.with_proxy(
|
||||
"org.asuslinux.Daemon",
|
||||
"/org/asuslinux/Gfx",
|
||||
Duration::from_secs(2),
|
||||
);
|
||||
let x = proxy.power()?;
|
||||
Ok(x)
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn get_gfx_mode(&self) -> Result<String, Box<dyn std::error::Error>> {
|
||||
let proxy = self.connection.with_proxy(
|
||||
"org.asuslinux.Daemon",
|
||||
"/org/asuslinux/Gfx",
|
||||
Duration::from_secs(2),
|
||||
);
|
||||
let x = proxy.vendor()?;
|
||||
Ok(x)
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn write_gfx_mode(&self, vendor: GfxVendors) -> Result<(), Box<dyn std::error::Error>> {
|
||||
let proxy = self.connection.with_proxy(
|
||||
"org.asuslinux.Daemon",
|
||||
"/org/asuslinux/Gfx",
|
||||
Duration::from_secs(30),
|
||||
);
|
||||
proxy.set_vendor(<&str>::from(&vendor))?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn write_fan_mode(&self, level: u8) -> Result<(), Box<dyn std::error::Error>> {
|
||||
let mut msg = Message::new_method_call(
|
||||
DBUS_NAME,
|
||||
let proxy = self.connection.with_proxy(
|
||||
"org.asuslinux.Daemon",
|
||||
"/org/asuslinux/Profile",
|
||||
DBUS_IFACE,
|
||||
"SetProfile",
|
||||
)?
|
||||
.append1(serde_json::to_string(&ProfileEvent::ChangeMode(level))?);
|
||||
msg.set_no_reply(true);
|
||||
self.connection.send(msg).unwrap();
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn write_gfx_mode(&self, vendor: GfxVendors) -> Result<(), Box<dyn std::error::Error>> {
|
||||
let mut msg =
|
||||
Message::new_method_call(DBUS_NAME, "/org/asuslinux/Gfx", DBUS_IFACE, "SetVendor")?
|
||||
.append1(<&str>::from(&vendor));
|
||||
msg.set_no_reply(true);
|
||||
self.connection.send(msg).unwrap();
|
||||
Duration::from_secs(2),
|
||||
);
|
||||
proxy.set_profile(&serde_json::to_string(&ProfileEvent::ChangeMode(level))?)?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
@@ -238,25 +279,23 @@ impl AuraDbusClient {
|
||||
&self,
|
||||
cmd: &ProfileEvent,
|
||||
) -> Result<(), Box<dyn std::error::Error>> {
|
||||
let mut msg = Message::new_method_call(
|
||||
DBUS_NAME,
|
||||
let proxy = self.connection.with_proxy(
|
||||
"org.asuslinux.Daemon",
|
||||
"/org/asuslinux/Profile",
|
||||
DBUS_IFACE,
|
||||
"SetProfile",
|
||||
)?
|
||||
.append1(serde_json::to_string(cmd)?);
|
||||
msg.set_no_reply(true);
|
||||
self.connection.send(msg).unwrap();
|
||||
Duration::from_secs(2),
|
||||
);
|
||||
proxy.set_profile(&serde_json::to_string(cmd)?)?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn write_charge_limit(&self, level: u8) -> Result<(), Box<dyn std::error::Error>> {
|
||||
let mut msg =
|
||||
Message::new_method_call(DBUS_NAME, "/org/asuslinux/Charge", DBUS_IFACE, "SetLimit")?
|
||||
.append1(level);
|
||||
msg.set_no_reply(true);
|
||||
self.connection.send(msg).unwrap();
|
||||
let proxy = self.connection.with_proxy(
|
||||
"org.asuslinux.Daemon",
|
||||
"/org/asuslinux/Charge",
|
||||
Duration::from_secs(2),
|
||||
);
|
||||
proxy.set_limit(level)?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
|
||||
@@ -1,18 +1,29 @@
|
||||
// This code was autogenerated with `dbus-codegen-rust -s -d org.asuslinux.Daemon -p /org/asuslinux/Gfx -m None -f org.asuslinux.Daemon -c blocking`, see https://github.com/diwic/dbus-rs
|
||||
use dbus;
|
||||
use dbus as dbus;
|
||||
#[allow(unused_imports)]
|
||||
use dbus::arg;
|
||||
use dbus::blocking;
|
||||
|
||||
pub trait OrgAsuslinuxDaemon {
|
||||
fn vendor(&self) -> Result<String, dbus::Error>;
|
||||
fn power(&self) -> Result<String, dbus::Error>;
|
||||
fn set_vendor(&self, vendor: &str) -> Result<(), dbus::Error>;
|
||||
}
|
||||
|
||||
impl<'a, T: blocking::BlockingSender, C: ::std::ops::Deref<Target = T>> OrgAsuslinuxDaemon
|
||||
for blocking::Proxy<'a, C>
|
||||
{
|
||||
impl<'a, T: blocking::BlockingSender, C: ::std::ops::Deref<Target=T>> OrgAsuslinuxDaemon for blocking::Proxy<'a, C> {
|
||||
|
||||
fn vendor(&self) -> Result<String, dbus::Error> {
|
||||
self.method_call("org.asuslinux.Daemon", "Vendor", ())
|
||||
.and_then(|r: (String, )| Ok(r.0, ))
|
||||
}
|
||||
|
||||
fn power(&self) -> Result<String, dbus::Error> {
|
||||
self.method_call("org.asuslinux.Daemon", "Power", ())
|
||||
.and_then(|r: (String, )| Ok(r.0, ))
|
||||
}
|
||||
|
||||
fn set_vendor(&self, vendor: &str) -> Result<(), dbus::Error> {
|
||||
self.method_call("org.asuslinux.Daemon", "SetVendor", (vendor,))
|
||||
self.method_call("org.asuslinux.Daemon", "SetVendor", (vendor, ))
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,7 +40,9 @@ impl arg::AppendAll for OrgAsuslinuxDaemonNotifyGfx {
|
||||
|
||||
impl arg::ReadAll for OrgAsuslinuxDaemonNotifyGfx {
|
||||
fn read(i: &mut arg::Iter) -> Result<Self, arg::TypeMismatchError> {
|
||||
Ok(OrgAsuslinuxDaemonNotifyGfx { vendor: i.read()? })
|
||||
Ok(OrgAsuslinuxDaemonNotifyGfx {
|
||||
vendor: i.read()?,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -37,3 +50,27 @@ impl dbus::message::SignalArgs for OrgAsuslinuxDaemonNotifyGfx {
|
||||
const NAME: &'static str = "NotifyGfx";
|
||||
const INTERFACE: &'static str = "org.asuslinux.Daemon";
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct OrgAsuslinuxDaemonNotifyAction {
|
||||
pub action: String,
|
||||
}
|
||||
|
||||
impl arg::AppendAll for OrgAsuslinuxDaemonNotifyAction {
|
||||
fn append(&self, i: &mut arg::IterAppend) {
|
||||
arg::RefArg::append(&self.action, i);
|
||||
}
|
||||
}
|
||||
|
||||
impl arg::ReadAll for OrgAsuslinuxDaemonNotifyAction {
|
||||
fn read(i: &mut arg::Iter) -> Result<Self, arg::TypeMismatchError> {
|
||||
Ok(OrgAsuslinuxDaemonNotifyAction {
|
||||
action: i.read()?,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
impl dbus::message::SignalArgs for OrgAsuslinuxDaemonNotifyAction {
|
||||
const NAME: &'static str = "NotifyAction";
|
||||
const INTERFACE: &'static str = "org.asuslinux.Daemon";
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
[package]
|
||||
name = "asus-notify"
|
||||
version = "1.0.0"
|
||||
version = "2.0.4"
|
||||
authors = ["Luke D Jones <luke@ljones.dev>"]
|
||||
edition = "2018"
|
||||
|
||||
|
||||
@@ -6,6 +6,8 @@ use std::error::Error;
|
||||
use std::time::Duration;
|
||||
|
||||
fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||
println!("Version {}", env!("CARGO_PKG_VERSION"));
|
||||
|
||||
let mut cfg = Config::read_new()?;
|
||||
let mut last_profile = String::new();
|
||||
|
||||
@@ -21,7 +23,7 @@ fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||
std::thread::sleep(Duration::from_millis(100));
|
||||
connection.process(std::time::Duration::from_millis(200))?;
|
||||
|
||||
if let Ok(mut lock) = signals.gfx_signal.lock() {
|
||||
if let Ok(mut lock) = signals.gfx_vendor_signal.lock() {
|
||||
if let Some(vendor) = lock.take() {
|
||||
if let Some(notif) = last_gfx_notif.take() {
|
||||
notif.close();
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
[package]
|
||||
name = "ctrl-gfx"
|
||||
version = "2.0.0"
|
||||
version = "2.1.1"
|
||||
license = "MPL-2.0"
|
||||
readme = "README.md"
|
||||
authors = ["Luke <luke@ljones.dev>"]
|
||||
|
||||
@@ -14,8 +14,8 @@ use crate::{error::GfxError, system::*};
|
||||
|
||||
pub struct CtrlGraphics {
|
||||
bus: PciBus,
|
||||
amd: Vec<GraphicsDevice>,
|
||||
intel: Vec<GraphicsDevice>,
|
||||
_amd: Vec<GraphicsDevice>,
|
||||
_intel: Vec<GraphicsDevice>,
|
||||
nvidia: Vec<GraphicsDevice>,
|
||||
#[allow(dead_code)]
|
||||
other: Vec<GraphicsDevice>,
|
||||
@@ -23,8 +23,11 @@ pub struct CtrlGraphics {
|
||||
}
|
||||
|
||||
trait Dbus {
|
||||
fn vendor(&self) -> String;
|
||||
fn power(&self) -> String;
|
||||
fn set_vendor(&mut self, vendor: String);
|
||||
fn notify_gfx(&self, vendor: &str) -> zbus::Result<()>;
|
||||
fn notify_action(&self, action: &str) -> zbus::Result<()>;
|
||||
}
|
||||
|
||||
#[cfg(feature = "use-zbus")]
|
||||
@@ -33,19 +36,32 @@ use std::convert::TryInto;
|
||||
#[cfg(feature = "use-zbus")]
|
||||
#[dbus_interface(name = "org.asuslinux.Daemon")]
|
||||
impl Dbus for CtrlGraphics {
|
||||
fn vendor(&self) -> String {
|
||||
Self::get_vendor().unwrap_or_else(|err| format!("Get vendor failed: {}", err))
|
||||
}
|
||||
|
||||
fn power(&self) -> String {
|
||||
Self::get_runtime_status().unwrap_or_else(|err| format!("Get power status failed: {}", err))
|
||||
}
|
||||
|
||||
fn set_vendor(&mut self, vendor: String) {
|
||||
if let Ok(tmp) = GfxVendors::from_str(&vendor) {
|
||||
self.set(tmp).unwrap_or_else(|err| {
|
||||
let action = self.set(tmp).unwrap_or_else(|err| {
|
||||
warn!("{}", err);
|
||||
format!("Failed: {}", err.to_string())
|
||||
});
|
||||
self.notify_gfx(&vendor)
|
||||
.unwrap_or_else(|err| warn!("{}", err));
|
||||
self.notify_action(&action)
|
||||
.unwrap_or_else(|err| warn!("{}", err));
|
||||
}
|
||||
}
|
||||
|
||||
#[dbus_interface(signal)]
|
||||
fn notify_gfx(&self, vendor: &str) -> zbus::Result<()>;
|
||||
|
||||
#[dbus_interface(signal)]
|
||||
fn notify_action(&self, action: &str) -> zbus::Result<()>;
|
||||
}
|
||||
|
||||
impl CtrlGraphics {
|
||||
@@ -107,17 +123,18 @@ impl CtrlGraphics {
|
||||
cmd.arg("-u");
|
||||
initfs_cmd = Some(cmd);
|
||||
info!("Using initramfs update command 'update-initramfs'");
|
||||
} else if Path::new(DRACUT_PATH).exists() {
|
||||
let mut cmd = Command::new("dracut");
|
||||
cmd.arg("-f");
|
||||
initfs_cmd = Some(cmd);
|
||||
info!("Using initramfs update command 'dracut'");
|
||||
}
|
||||
// } else if Path::new(DRACUT_PATH).exists() {
|
||||
// let mut cmd = Command::new("dracut");
|
||||
// cmd.arg("-f");
|
||||
// initfs_cmd = Some(cmd);
|
||||
// info!("Using initramfs update command 'dracut'");
|
||||
// }
|
||||
|
||||
Ok(CtrlGraphics {
|
||||
bus,
|
||||
amd,
|
||||
intel,
|
||||
_amd: amd,
|
||||
_intel: intel,
|
||||
nvidia,
|
||||
other,
|
||||
initfs_cmd,
|
||||
@@ -128,7 +145,11 @@ impl CtrlGraphics {
|
||||
pub fn add_to_server(self, server: &mut zbus::ObjectServer) {
|
||||
server
|
||||
.at(&"/org/asuslinux/Gfx".try_into().unwrap(), self)
|
||||
.unwrap();
|
||||
.map_err(|err| {
|
||||
warn!("CtrlGraphics: add_to_server {}", err);
|
||||
err
|
||||
})
|
||||
.ok();
|
||||
}
|
||||
|
||||
pub fn reload(&mut self) -> Result<(), Box<dyn Error>> {
|
||||
@@ -137,9 +158,9 @@ impl CtrlGraphics {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn can_switch(&self) -> bool {
|
||||
!self.nvidia.is_empty() && (!self.intel.is_empty() || !self.amd.is_empty())
|
||||
}
|
||||
// fn can_switch(&self) -> bool {
|
||||
// !self.nvidia.is_empty() && (!self.intel.is_empty() || !self.amd.is_empty())
|
||||
// }
|
||||
|
||||
fn get_prime_discrete() -> Result<String, GfxError> {
|
||||
let s = std::fs::read_to_string(PRIME_DISCRETE_PATH)
|
||||
@@ -162,6 +183,7 @@ impl CtrlGraphics {
|
||||
.iter()
|
||||
.any(|module| module.name == "nouveau" || module.name == "nvidia")
|
||||
{
|
||||
info!("nvidia or nouveau module found");
|
||||
let mode = match Self::get_prime_discrete() {
|
||||
Ok(m) => m,
|
||||
Err(_) => "nvidia".to_string(),
|
||||
@@ -175,6 +197,7 @@ impl CtrlGraphics {
|
||||
"nvidia".to_string()
|
||||
}
|
||||
} else {
|
||||
info!("No dGPU driver (nouveau or nvidia) loaded");
|
||||
"integrated".to_string()
|
||||
};
|
||||
|
||||
@@ -206,10 +229,10 @@ impl CtrlGraphics {
|
||||
|
||||
// Switching from hybrid to/from nvidia shouldn't require a ramdisk update
|
||||
// or a reboot.
|
||||
let switching_prime_modes = Self::is_switching_prime_modes(&vendor)?;
|
||||
let no_reboot = Self::is_switching_prime_modes(&vendor)?;
|
||||
|
||||
{
|
||||
info!("Creating {}", MODPROBE_PATH);
|
||||
info!("Writing {}", MODPROBE_PATH);
|
||||
|
||||
let mut file = std::fs::OpenOptions::new()
|
||||
.create(true)
|
||||
@@ -233,7 +256,7 @@ impl CtrlGraphics {
|
||||
.map_err(|err| GfxError::Write(MODPROBE_PATH.into(), err))?;
|
||||
}
|
||||
|
||||
info!("Creating {}", PRIMARY_GPU_XORG_PATH);
|
||||
info!("Writing {}", PRIMARY_GPU_XORG_PATH);
|
||||
|
||||
// begin section for non-separated Nvidia xorg modules
|
||||
// eg, not put in their own directory
|
||||
@@ -277,7 +300,7 @@ impl CtrlGraphics {
|
||||
}
|
||||
|
||||
let mut required_action = GfxCtrlAction::None;
|
||||
if !switching_prime_modes {
|
||||
if !no_reboot {
|
||||
info!("Updating initramfs");
|
||||
if let Some(cmd) = self.initfs_cmd.as_mut() {
|
||||
let status = cmd
|
||||
@@ -290,18 +313,23 @@ impl CtrlGraphics {
|
||||
}
|
||||
}
|
||||
required_action = GfxCtrlAction::Reboot;
|
||||
} else if switching_prime_modes {
|
||||
} else if no_reboot {
|
||||
required_action = GfxCtrlAction::RestartX;
|
||||
}
|
||||
|
||||
Ok(required_action.into())
|
||||
}
|
||||
|
||||
pub fn get_power(&self) -> Option<bool> {
|
||||
if self.can_switch() {
|
||||
return Some(self.nvidia.iter().any(GraphicsDevice::exists));
|
||||
}
|
||||
None
|
||||
// pub fn get_power(&self) -> Option<bool> {
|
||||
// if self.can_switch() {
|
||||
// return Some(self.nvidia.iter().any(GraphicsDevice::exists));
|
||||
// }
|
||||
// None
|
||||
// }
|
||||
pub fn get_runtime_status() -> Result<String, GfxError> {
|
||||
const PATH: &str = "/sys/bus/pci/devices/0000:01:00.0/power/runtime_status";
|
||||
let buf = std::fs::read_to_string(PATH).map_err(|err| GfxError::Read(PATH.into(), err))?;
|
||||
Ok(buf)
|
||||
}
|
||||
|
||||
fn set_power(&self, power: bool) -> Result<(), GfxError> {
|
||||
|
||||
@@ -9,7 +9,7 @@ pub mod system;
|
||||
const PRIME_DISCRETE_PATH: &str = "/etc/prime-discrete";
|
||||
const MODPROBE_PATH: &str = "/etc/modprobe.d/asusd.conf";
|
||||
const INITRAMFS_PATH: &str = "/usr/sbin/update-initramfs";
|
||||
const DRACUT_PATH: &str = "/usr/bin/dracut";
|
||||
// const DRACUT_PATH: &str = "/usr/bin/dracut";
|
||||
|
||||
static MODPROBE_NVIDIA: &[u8] = MODPROBE_HYBRID;
|
||||
|
||||
@@ -47,7 +47,6 @@ Section "OutputClass"
|
||||
Identifier "nvidia"
|
||||
MatchDriver "nvidia-drm"
|
||||
Driver "nvidia"
|
||||
Option "TripleBuffer" "true"
|
||||
Option "AllowEmptyInitialConfiguration"
|
||||
Option "AllowExternalGpus""#;
|
||||
|
||||
@@ -56,3 +55,4 @@ static PRIMARY_GPU_NVIDIA: &[u8] = br#"
|
||||
|
||||
static PRIMARY_GPU_END: &[u8] = br#"
|
||||
EndSection"#;
|
||||
|
||||
|
||||
@@ -121,7 +121,7 @@ impl GraphicsDevice {
|
||||
warn!("{}: Already removed", func.id());
|
||||
}
|
||||
}
|
||||
info!("Remmoved all gfx devices");
|
||||
info!("Removed all gfx devices");
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
Section "ServerLayout"
|
||||
Identifier "layout"
|
||||
Option "AllowNVIDIAGPUScreens"
|
||||
Option "metamodes" "nvidia-auto-select +0+0 {AllowGSYNC=On, AllowGSYNCCompatible=On}"
|
||||
EndSection
|
||||
|
||||
12
data/asusd-alt.service
Normal file
12
data/asusd-alt.service
Normal file
@@ -0,0 +1,12 @@
|
||||
[Unit]
|
||||
Description=ASUS Notebook Control
|
||||
After=basic.target syslog.target
|
||||
|
||||
[Service]
|
||||
ExecStart=/usr/bin/asusd
|
||||
Restart=on-failure
|
||||
Type=dbus
|
||||
BusName=org.asuslinux.Daemon
|
||||
|
||||
[Install]
|
||||
WantedBy=multi-user.target
|
||||
@@ -3,6 +3,11 @@ prod_family = "Zephyrus S"
|
||||
board_names = ["GX502", "GX701", "G531", "GL531", "G532"]
|
||||
led_modes = [0, 1, 2, 3, 4, 5, 6, 7, 8, 10, 11, 12, 255]
|
||||
|
||||
[[led_modes]]
|
||||
prod_family = "Zephyrus M"
|
||||
board_names = ["GU502GV"]
|
||||
led_modes = [0, 1, 2, 3, 4, 5, 6, 7, 8, 10, 11, 12, 255]
|
||||
|
||||
[[led_modes]]
|
||||
prod_family = "Zephyrus"
|
||||
board_names = ["GM501GM", "GX531"]
|
||||
|
||||
Reference in New Issue
Block a user