mirror of
https://gitlab.com/asus-linux/asusctl.git
synced 2026-02-06 00:15:04 +01:00
Move DBUS and keyboard reads on to tokio
This greatly improves throughput of per-key LED effects. Also add a cool-down timer in the main loop to adjust thread speed and prevent it running at maximum speed.
This commit is contained in:
12
Cargo.lock
generated
12
Cargo.lock
generated
@@ -24,17 +24,6 @@ dependencies = [
|
|||||||
"winapi 0.3.8",
|
"winapi 0.3.8",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
|
||||||
name = "async-trait"
|
|
||||||
version = "0.1.30"
|
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
||||||
checksum = "da71fef07bc806586090247e971229289f64c210a278ee5ae419314eb386b31d"
|
|
||||||
dependencies = [
|
|
||||||
"proc-macro2",
|
|
||||||
"quote",
|
|
||||||
"syn",
|
|
||||||
]
|
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "atty"
|
name = "atty"
|
||||||
version = "0.2.14"
|
version = "0.2.14"
|
||||||
@@ -631,7 +620,6 @@ name = "rog-daemon"
|
|||||||
version = "0.6.1"
|
version = "0.6.1"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"aho-corasick",
|
"aho-corasick",
|
||||||
"async-trait",
|
|
||||||
"dbus",
|
"dbus",
|
||||||
"dbus-tokio",
|
"dbus-tokio",
|
||||||
"env_logger",
|
"env_logger",
|
||||||
|
|||||||
@@ -29,5 +29,3 @@ log = "^0.4.8"
|
|||||||
uhid-virt = "^0.0.4"
|
uhid-virt = "^0.0.4"
|
||||||
#keycode = "0.3"
|
#keycode = "0.3"
|
||||||
env_logger = "^0.7.1"
|
env_logger = "^0.7.1"
|
||||||
|
|
||||||
async-trait = "0.1.30"
|
|
||||||
@@ -46,7 +46,7 @@ fn main() -> Result<(), Box<dyn std::error::Error>> {
|
|||||||
|
|
||||||
// It takes each interrupt at least 1ms. 10ms to write complete block. Plus any extra
|
// It takes each interrupt at least 1ms. 10ms to write complete block. Plus any extra
|
||||||
// penalty time such as read waits
|
// penalty time such as read waits
|
||||||
let time = time::Duration::from_millis(1); // aim for 60 per second
|
let time = time::Duration::from_millis(10); // aim for 100 per second
|
||||||
|
|
||||||
let row = KeyColourArray::get_init_msg();
|
let row = KeyColourArray::get_init_msg();
|
||||||
let msg =
|
let msg =
|
||||||
|
|||||||
68
src/core.rs
68
src/core.rs
@@ -98,7 +98,7 @@ impl RogCore {
|
|||||||
.get_field_from(BuiltInModeByte::from(mode_curr).into())
|
.get_field_from(BuiltInModeByte::from(mode_curr).into())
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.to_owned();
|
.to_owned();
|
||||||
self.aura_write_messages(&[&mode]).await?;
|
self.aura_write_messages(&[&mode])?;
|
||||||
|
|
||||||
let path = if Path::new(FAN_TYPE_1_PATH).exists() {
|
let path = if Path::new(FAN_TYPE_1_PATH).exists() {
|
||||||
FAN_TYPE_1_PATH
|
FAN_TYPE_1_PATH
|
||||||
@@ -131,7 +131,7 @@ impl RogCore {
|
|||||||
Err(AuraError::UsbError(rusb::Error::NoDevice))
|
Err(AuraError::UsbError(rusb::Error::NoDevice))
|
||||||
}
|
}
|
||||||
|
|
||||||
pub async fn aura_write(&mut self, message: &[u8]) -> Result<(), AuraError> {
|
pub fn aura_write(&mut self, message: &[u8]) -> Result<(), AuraError> {
|
||||||
match self
|
match self
|
||||||
.handle
|
.handle
|
||||||
.write_interrupt(self.led_endpoint, message, Duration::from_millis(1))
|
.write_interrupt(self.led_endpoint, message, Duration::from_millis(1))
|
||||||
@@ -145,31 +145,31 @@ impl RogCore {
|
|||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn aura_write_messages(&mut self, messages: &[&[u8]]) -> Result<(), AuraError> {
|
fn aura_write_messages(&mut self, messages: &[&[u8]]) -> Result<(), AuraError> {
|
||||||
if !self.initialised {
|
if !self.initialised {
|
||||||
self.aura_write(&LED_INIT1).await?;
|
self.aura_write(&LED_INIT1)?;
|
||||||
self.aura_write(LED_INIT2.as_bytes()).await?;
|
self.aura_write(LED_INIT2.as_bytes())?;
|
||||||
self.aura_write(&LED_INIT3).await?;
|
self.aura_write(&LED_INIT3)?;
|
||||||
self.aura_write(LED_INIT4.as_bytes()).await?;
|
self.aura_write(LED_INIT4.as_bytes())?;
|
||||||
self.aura_write(&LED_INIT5).await?;
|
self.aura_write(&LED_INIT5)?;
|
||||||
self.initialised = true;
|
self.initialised = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
for message in messages {
|
for message in messages {
|
||||||
self.aura_write(*message).await?;
|
self.aura_write(*message)?;
|
||||||
self.aura_write(&LED_SET).await?;
|
self.aura_write(&LED_SET)?;
|
||||||
}
|
}
|
||||||
// Changes won't persist unless apply is set
|
// Changes won't persist unless apply is set
|
||||||
self.aura_write(&LED_APPLY).await?;
|
self.aura_write(&LED_APPLY)?;
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Initialise and clear the keyboard for custom effects
|
/// Initialise and clear the keyboard for custom effects
|
||||||
pub async fn aura_effect_init(&mut self) -> Result<(), AuraError> {
|
pub fn aura_effect_init(&mut self) -> Result<(), AuraError> {
|
||||||
let mut init = [0u8; 64];
|
let mut init = [0u8; 64];
|
||||||
init[0] = 0x5d; // Report ID
|
init[0] = 0x5d; // Report ID
|
||||||
init[1] = 0xbc; // Mode = custom??, 0xb3 is builtin
|
init[1] = 0xbc; // Mode = custom??, 0xb3 is builtin
|
||||||
self.aura_write(&init).await?;
|
self.aura_write(&init)?;
|
||||||
self.initialised = true;
|
self.initialised = true;
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
@@ -178,25 +178,25 @@ impl RogCore {
|
|||||||
/// Write an effect block
|
/// Write an effect block
|
||||||
///
|
///
|
||||||
/// `aura_effect_init` must be called any effect routine, and called only once.
|
/// `aura_effect_init` must be called any effect routine, and called only once.
|
||||||
pub async fn aura_write_effect(&mut self, effect: Vec<Vec<u8>>) -> Result<(), AuraError> {
|
pub fn aura_write_effect(&mut self, effect: Vec<Vec<u8>>) -> Result<(), AuraError> {
|
||||||
for row in effect.iter() {
|
for row in effect.iter() {
|
||||||
self.aura_write(row).await?;
|
self.aura_write(row)?;
|
||||||
}
|
}
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) async fn aura_set_and_save(
|
pub(crate) fn aura_set_and_save(
|
||||||
&mut self,
|
&mut self,
|
||||||
supported_modes: &[BuiltInModeByte],
|
supported_modes: &[BuiltInModeByte],
|
||||||
bytes: &[u8],
|
bytes: &[u8],
|
||||||
) -> Result<(), AuraError> {
|
) -> Result<(), AuraError> {
|
||||||
let mode = BuiltInModeByte::from(bytes[3]);
|
let mode = BuiltInModeByte::from(bytes[3]);
|
||||||
if bytes[1] == 0xbc {
|
if bytes[1] == 0xbc {
|
||||||
self.aura_write(bytes).await?;
|
self.aura_write(bytes)?;
|
||||||
return Ok(());
|
return Ok(());
|
||||||
} else if supported_modes.contains(&mode) || bytes[1] == 0xba {
|
} else if supported_modes.contains(&mode) || bytes[1] == 0xba {
|
||||||
let messages = [bytes];
|
let messages = [bytes];
|
||||||
self.aura_write_messages(&messages).await?;
|
self.aura_write_messages(&messages)?;
|
||||||
self.config.set_field_from(bytes);
|
self.config.set_field_from(bytes);
|
||||||
self.config.write();
|
self.config.write();
|
||||||
return Ok(());
|
return Ok(());
|
||||||
@@ -205,7 +205,7 @@ impl RogCore {
|
|||||||
Err(AuraError::NotSupported)
|
Err(AuraError::NotSupported)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) async fn aura_bright_inc(
|
pub(crate) fn aura_bright_inc(
|
||||||
&mut self,
|
&mut self,
|
||||||
supported_modes: &[BuiltInModeByte],
|
supported_modes: &[BuiltInModeByte],
|
||||||
max_bright: u8,
|
max_bright: u8,
|
||||||
@@ -216,11 +216,11 @@ impl RogCore {
|
|||||||
self.config.brightness = bright;
|
self.config.brightness = bright;
|
||||||
}
|
}
|
||||||
let bytes = aura_brightness_bytes(bright);
|
let bytes = aura_brightness_bytes(bright);
|
||||||
self.aura_set_and_save(supported_modes, &bytes).await?;
|
self.aura_set_and_save(supported_modes, &bytes)?;
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) async fn aura_bright_dec(
|
pub(crate) fn aura_bright_dec(
|
||||||
&mut self,
|
&mut self,
|
||||||
supported_modes: &[BuiltInModeByte],
|
supported_modes: &[BuiltInModeByte],
|
||||||
min_bright: u8,
|
min_bright: u8,
|
||||||
@@ -231,14 +231,14 @@ impl RogCore {
|
|||||||
self.config.brightness = bright;
|
self.config.brightness = bright;
|
||||||
}
|
}
|
||||||
let bytes = aura_brightness_bytes(bright);
|
let bytes = aura_brightness_bytes(bright);
|
||||||
self.aura_set_and_save(supported_modes, &bytes).await?;
|
self.aura_set_and_save(supported_modes, &bytes)?;
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Select next Aura effect
|
/// Select next Aura effect
|
||||||
///
|
///
|
||||||
/// If the current effect is the last one then the effect selected wraps around to the first.
|
/// If the current effect is the last one then the effect selected wraps around to the first.
|
||||||
pub(crate) async fn aura_mode_next(
|
pub(crate) fn aura_mode_next(
|
||||||
&mut self,
|
&mut self,
|
||||||
supported_modes: &[BuiltInModeByte],
|
supported_modes: &[BuiltInModeByte],
|
||||||
) -> Result<(), AuraError> {
|
) -> Result<(), AuraError> {
|
||||||
@@ -256,7 +256,7 @@ impl RogCore {
|
|||||||
.get_field_from(supported_modes[idx_next].into())
|
.get_field_from(supported_modes[idx_next].into())
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.to_owned();
|
.to_owned();
|
||||||
self.aura_set_and_save(supported_modes, &mode_next).await?;
|
self.aura_set_and_save(supported_modes, &mode_next)?;
|
||||||
info!("Switched LED mode to {:#?}", supported_modes[idx_next]);
|
info!("Switched LED mode to {:#?}", supported_modes[idx_next]);
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
@@ -264,7 +264,7 @@ impl RogCore {
|
|||||||
/// Select previous Aura effect
|
/// Select previous Aura effect
|
||||||
///
|
///
|
||||||
/// If the current effect is the first one then the effect selected wraps around to the last.
|
/// If the current effect is the first one then the effect selected wraps around to the last.
|
||||||
pub(crate) async fn aura_mode_prev(
|
pub(crate) fn aura_mode_prev(
|
||||||
&mut self,
|
&mut self,
|
||||||
supported_modes: &[BuiltInModeByte],
|
supported_modes: &[BuiltInModeByte],
|
||||||
) -> Result<(), AuraError> {
|
) -> Result<(), AuraError> {
|
||||||
@@ -282,7 +282,7 @@ impl RogCore {
|
|||||||
.get_field_from(supported_modes[idx_next].into())
|
.get_field_from(supported_modes[idx_next].into())
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.to_owned();
|
.to_owned();
|
||||||
self.aura_set_and_save(supported_modes, &mode_next).await?;
|
self.aura_set_and_save(supported_modes, &mode_next)?;
|
||||||
info!("Switched LED mode to {:#?}", supported_modes[idx_next]);
|
info!("Switched LED mode to {:#?}", supported_modes[idx_next]);
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
@@ -322,12 +322,13 @@ impl RogCore {
|
|||||||
///
|
///
|
||||||
/// `report_filter_bytes` is used to filter the data read from the interupt so
|
/// `report_filter_bytes` is used to filter the data read from the interupt so
|
||||||
/// only the relevant byte array is returned.
|
/// only the relevant byte array is returned.
|
||||||
pub(crate) async fn poll_keyboard(&mut self, report_filter_bytes: &[u8]) -> Option<[u8; 32]> {
|
pub(crate) async fn poll_keyboard(
|
||||||
|
handle: &DeviceHandle<rusb::GlobalContext>,
|
||||||
|
endpoint: u8,
|
||||||
|
report_filter_bytes: Vec<u8>,
|
||||||
|
) -> Option<[u8; 32]> {
|
||||||
let mut buf = [0u8; 32];
|
let mut buf = [0u8; 32];
|
||||||
match self
|
match handle.read_interrupt(endpoint, &mut buf, Duration::from_millis(200)) {
|
||||||
.handle
|
|
||||||
.read_interrupt(self.keys_endpoint, &mut buf, Duration::from_millis(50))
|
|
||||||
{
|
|
||||||
Ok(_) => {
|
Ok(_) => {
|
||||||
if report_filter_bytes.contains(&buf[0]) {
|
if report_filter_bytes.contains(&buf[0]) {
|
||||||
return Some(buf);
|
return Some(buf);
|
||||||
@@ -341,6 +342,11 @@ impl RogCore {
|
|||||||
None
|
None
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub(crate) fn get_raw_device_handle(&mut self) -> *mut DeviceHandle<rusb::GlobalContext> {
|
||||||
|
// Breaking every damn lifetime guarantee rust gives us
|
||||||
|
&mut self.handle as *mut DeviceHandle<rusb::GlobalContext>
|
||||||
|
}
|
||||||
|
|
||||||
/// A direct call to systemd to suspend the PC.
|
/// A direct call to systemd to suspend the PC.
|
||||||
///
|
///
|
||||||
/// This avoids desktop environments being required to handle it
|
/// This avoids desktop environments being required to handle it
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ use dbus_tokio::connection;
|
|||||||
use log::{error, info};
|
use log::{error, info};
|
||||||
use std::error::Error;
|
use std::error::Error;
|
||||||
use std::sync::{Arc, Mutex};
|
use std::sync::{Arc, Mutex};
|
||||||
use std::time::Duration;
|
use std::time::{Duration, Instant};
|
||||||
|
|
||||||
pub async fn start_daemon() -> Result<(), Box<dyn Error>> {
|
pub async fn start_daemon() -> Result<(), Box<dyn Error>> {
|
||||||
let laptop = match_laptop();
|
let laptop = match_laptop();
|
||||||
@@ -28,7 +28,7 @@ pub async fn start_daemon() -> Result<(), Box<dyn Error>> {
|
|||||||
);
|
);
|
||||||
// Reload settings
|
// Reload settings
|
||||||
rogcore.reload().await?;
|
rogcore.reload().await?;
|
||||||
println!("RELOADED");
|
info!("Reloaded last saved settings");
|
||||||
|
|
||||||
let (resource, connection) = connection::new_system_sync()?;
|
let (resource, connection) = connection::new_system_sync()?;
|
||||||
tokio::spawn(async {
|
tokio::spawn(async {
|
||||||
@@ -36,11 +36,9 @@ pub async fn start_daemon() -> Result<(), Box<dyn Error>> {
|
|||||||
panic!("Lost connection to D-Bus: {}", err);
|
panic!("Lost connection to D-Bus: {}", err);
|
||||||
});
|
});
|
||||||
|
|
||||||
println!("CONN REQUEST");
|
|
||||||
connection
|
connection
|
||||||
.request_name(DBUS_IFACE, false, true, false)
|
.request_name(DBUS_IFACE, false, true, false)
|
||||||
.await?;
|
.await?;
|
||||||
println!("CONN REQUEST DONE");
|
|
||||||
|
|
||||||
let factory = Factory::new_sync::<()>();
|
let factory = Factory::new_sync::<()>();
|
||||||
|
|
||||||
@@ -127,6 +125,27 @@ pub async fn start_daemon() -> Result<(), Box<dyn Error>> {
|
|||||||
tree.start_receive_send(&*connection);
|
tree.start_receive_send(&*connection);
|
||||||
|
|
||||||
let supported = Vec::from(laptop.supported_modes());
|
let supported = Vec::from(laptop.supported_modes());
|
||||||
|
|
||||||
|
let key_buf: Arc<Mutex<Option<[u8; 32]>>> = Arc::new(Mutex::new(None));
|
||||||
|
let handle = unsafe { &*(rogcore.get_raw_device_handle()) };
|
||||||
|
let endpoint = laptop.key_endpoint();
|
||||||
|
let report_filter_bytes = laptop.key_filter().to_owned();
|
||||||
|
|
||||||
|
let key_buf1 = key_buf.clone();
|
||||||
|
// This is *not* safe
|
||||||
|
tokio::spawn(async move {
|
||||||
|
loop {
|
||||||
|
let data = RogCore::poll_keyboard(handle, endpoint, report_filter_bytes.clone()).await;
|
||||||
|
if let Some(stuff) = data {
|
||||||
|
if let Ok(mut lock) = key_buf1.lock() {
|
||||||
|
lock.replace(stuff);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// When any action occurs this time is reset
|
||||||
|
let mut time_mark = Instant::now();
|
||||||
loop {
|
loop {
|
||||||
// Timing is such that:
|
// Timing is such that:
|
||||||
// - interrupt write is minimum 1ms (sometimes lower)
|
// - interrupt write is minimum 1ms (sometimes lower)
|
||||||
@@ -143,26 +162,43 @@ pub async fn start_daemon() -> Result<(), Box<dyn Error>> {
|
|||||||
if let Ok(mut lock) = input.try_lock() {
|
if let Ok(mut lock) = input.try_lock() {
|
||||||
if let Some(bytes) = &*lock {
|
if let Some(bytes) = &*lock {
|
||||||
// It takes up to 20 milliseconds to write a complete colour block here
|
// It takes up to 20 milliseconds to write a complete colour block here
|
||||||
rogcore.aura_set_and_save(&supported, &bytes).await?;
|
rogcore.aura_set_and_save(&supported, &bytes)?;
|
||||||
*lock = None;
|
*lock = None;
|
||||||
|
time_mark = Instant::now();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if let Ok(mut lock) = effect.try_lock() {
|
if let Ok(mut lock) = effect.lock() {
|
||||||
if lock.is_some() {
|
if lock.is_some() {
|
||||||
let effect = lock.take();
|
let effect = lock.take();
|
||||||
rogcore.aura_write_effect(effect.unwrap()).await?;
|
rogcore.aura_write_effect(effect.unwrap())?;
|
||||||
|
time_mark = Instant::now();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
match laptop.run(&mut rogcore).await {
|
if let Ok(mut lock) = key_buf.try_lock() {
|
||||||
Ok(_) => {}
|
if let Some(bytes) = *lock {
|
||||||
Err(err) => {
|
// this takes at least 10ms per colour block
|
||||||
error!("{:?}", err);
|
match laptop.run(&mut rogcore, bytes) {
|
||||||
panic!("Force crash for systemd to restart service")
|
Ok(_) => {}
|
||||||
|
Err(err) => {
|
||||||
|
error!("{:?}", err);
|
||||||
|
panic!("Force crash for systemd to restart service")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*lock = None;
|
||||||
|
time_mark = Instant::now();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// When using an effect gen, 17-20ms is the min/max time to account for.
|
|
||||||
// If DBUS didn't take so long we could get this down to 11-12ms.
|
let now = Instant::now();
|
||||||
|
// Cool-down steps
|
||||||
|
if now.duration_since(time_mark).as_millis() > 500 {
|
||||||
|
std::thread::sleep(Duration::from_millis(100));
|
||||||
|
} else if now.duration_since(time_mark).as_millis() > 20 {
|
||||||
|
std::thread::sleep(Duration::from_millis(20));
|
||||||
|
} else {
|
||||||
|
std::thread::sleep(Duration::from_micros(400));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -47,44 +47,42 @@ impl LaptopGL753 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl LaptopGL753 {
|
impl LaptopGL753 {
|
||||||
async fn do_keypress_actions(&self, rogcore: &mut RogCore) -> Result<(), AuraError> {
|
fn do_keypress_actions(
|
||||||
if let Some(key_buf) = rogcore.poll_keyboard(&self.report_filter_bytes).await {
|
&self,
|
||||||
match GL753Keys::from(key_buf[1]) {
|
rogcore: &mut RogCore,
|
||||||
GL753Keys::LedBrightUp => {
|
key_buf: [u8; 32],
|
||||||
rogcore
|
) -> Result<(), AuraError> {
|
||||||
.aura_bright_inc(&self.supported_modes, self.max_led_bright)
|
match GL753Keys::from(key_buf[1]) {
|
||||||
.await?;
|
GL753Keys::LedBrightUp => {
|
||||||
}
|
rogcore.aura_bright_inc(&self.supported_modes, self.max_led_bright)?;
|
||||||
GL753Keys::LedBrightDown => {
|
}
|
||||||
rogcore
|
GL753Keys::LedBrightDown => {
|
||||||
.aura_bright_dec(&self.supported_modes, self.min_led_bright)
|
rogcore.aura_bright_dec(&self.supported_modes, self.min_led_bright)?;
|
||||||
.await?;
|
}
|
||||||
}
|
GL753Keys::ScreenBrightUp => self.backlight.step_up(),
|
||||||
GL753Keys::ScreenBrightUp => self.backlight.step_up(),
|
GL753Keys::ScreenBrightDown => self.backlight.step_down(),
|
||||||
GL753Keys::ScreenBrightDown => self.backlight.step_down(),
|
GL753Keys::Sleep => rogcore.suspend_with_systemd(),
|
||||||
GL753Keys::Sleep => rogcore.suspend_with_systemd(),
|
GL753Keys::AirplaneMode => rogcore.toggle_airplane_mode(),
|
||||||
GL753Keys::AirplaneMode => rogcore.toggle_airplane_mode(),
|
GL753Keys::ScreenToggle => {
|
||||||
GL753Keys::ScreenToggle => {
|
rogcore.virt_keys().press(ConsumerKeys::BacklightTog.into());
|
||||||
rogcore.virt_keys().press(ConsumerKeys::BacklightTog.into());
|
}
|
||||||
}
|
GL753Keys::TouchPadToggle => {
|
||||||
GL753Keys::TouchPadToggle => {
|
let mut key = [0u8; 32];
|
||||||
let mut key = [0u8; 32];
|
key[0] = 0x01;
|
||||||
key[0] = 0x01;
|
key[3] = 0x070;
|
||||||
key[3] = 0x070;
|
rogcore.virt_keys().press(key);
|
||||||
rogcore.virt_keys().press(key);
|
}
|
||||||
}
|
GL753Keys::Rog => {
|
||||||
GL753Keys::Rog => {
|
let mut key = [0u8; 32];
|
||||||
let mut key = [0u8; 32];
|
key[0] = 0x01;
|
||||||
key[0] = 0x01;
|
key[3] = 0x68; // XF86Tools? F13
|
||||||
key[3] = 0x68; // XF86Tools? F13
|
rogcore.virt_keys().press(key);
|
||||||
rogcore.virt_keys().press(key);
|
}
|
||||||
}
|
GL753Keys::None => {
|
||||||
GL753Keys::None => {
|
if key_buf[0] != 0x5A {
|
||||||
if key_buf[0] != 0x5A {
|
info!("Unmapped key array: {:X?}", &key_buf);
|
||||||
info!("Unmapped key array: {:X?}", &key_buf);
|
info!("Attempting passthrough: {:X?}", &key_buf[1]);
|
||||||
info!("Attempting passthrough: {:X?}", &key_buf[1]);
|
rogcore.virt_keys().press(key_buf);
|
||||||
rogcore.virt_keys().press(key_buf);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -92,11 +90,9 @@ impl LaptopGL753 {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
use async_trait::async_trait;
|
|
||||||
#[async_trait]
|
|
||||||
impl Laptop for LaptopGL753 {
|
impl Laptop for LaptopGL753 {
|
||||||
async fn run(&self, rogcore: &mut RogCore) -> Result<(), AuraError> {
|
fn run(&self, rogcore: &mut RogCore, key_buf: [u8; 32]) -> Result<(), AuraError> {
|
||||||
self.do_keypress_actions(rogcore).await
|
self.do_keypress_actions(rogcore, key_buf)
|
||||||
}
|
}
|
||||||
fn led_endpoint(&self) -> u8 {
|
fn led_endpoint(&self) -> u8 {
|
||||||
self.led_endpoint
|
self.led_endpoint
|
||||||
@@ -104,6 +100,9 @@ impl Laptop for LaptopGL753 {
|
|||||||
fn key_endpoint(&self) -> u8 {
|
fn key_endpoint(&self) -> u8 {
|
||||||
self.key_endpoint
|
self.key_endpoint
|
||||||
}
|
}
|
||||||
|
fn key_filter(&self) -> &[u8] {
|
||||||
|
&self.report_filter_bytes
|
||||||
|
}
|
||||||
fn usb_vendor(&self) -> u16 {
|
fn usb_vendor(&self) -> u16 {
|
||||||
self.usb_vendor
|
self.usb_vendor
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -89,53 +89,51 @@ impl LaptopGX502 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl LaptopGX502 {
|
impl LaptopGX502 {
|
||||||
async fn do_keypress_actions(&self, rogcore: &mut RogCore) -> Result<(), AuraError> {
|
fn do_keypress_actions(
|
||||||
if let Some(key_buf) = rogcore.poll_keyboard(&self.report_filter_bytes).await {
|
&self,
|
||||||
match GX502Keys::from(key_buf[1]) {
|
rogcore: &mut RogCore,
|
||||||
GX502Keys::LedBrightUp => {
|
key_buf: [u8; 32],
|
||||||
rogcore
|
) -> Result<(), AuraError> {
|
||||||
.aura_bright_inc(&self.supported_modes, self.max_led_bright)
|
match GX502Keys::from(key_buf[1]) {
|
||||||
.await?;
|
GX502Keys::LedBrightUp => {
|
||||||
}
|
rogcore.aura_bright_inc(&self.supported_modes, self.max_led_bright)?;
|
||||||
GX502Keys::LedBrightDown => {
|
}
|
||||||
rogcore
|
GX502Keys::LedBrightDown => {
|
||||||
.aura_bright_dec(&self.supported_modes, self.min_led_bright)
|
rogcore.aura_bright_dec(&self.supported_modes, self.min_led_bright)?;
|
||||||
.await?;
|
}
|
||||||
}
|
GX502Keys::AuraNext => rogcore.aura_mode_next(&self.supported_modes)?,
|
||||||
GX502Keys::AuraNext => rogcore.aura_mode_next(&self.supported_modes).await?,
|
GX502Keys::AuraPrevious => rogcore.aura_mode_prev(&self.supported_modes)?,
|
||||||
GX502Keys::AuraPrevious => rogcore.aura_mode_prev(&self.supported_modes).await?,
|
GX502Keys::ScreenBrightUp => self.backlight.step_up(),
|
||||||
GX502Keys::ScreenBrightUp => self.backlight.step_up(),
|
GX502Keys::ScreenBrightDown => self.backlight.step_down(),
|
||||||
GX502Keys::ScreenBrightDown => self.backlight.step_down(),
|
GX502Keys::Sleep => rogcore.suspend_with_systemd(),
|
||||||
GX502Keys::Sleep => rogcore.suspend_with_systemd(),
|
GX502Keys::AirplaneMode => rogcore.toggle_airplane_mode(),
|
||||||
GX502Keys::AirplaneMode => rogcore.toggle_airplane_mode(),
|
GX502Keys::MicToggle => {}
|
||||||
GX502Keys::MicToggle => {}
|
GX502Keys::Fan => {
|
||||||
GX502Keys::Fan => {
|
rogcore.fan_mode_step().unwrap_or_else(|err| {
|
||||||
rogcore.fan_mode_step().unwrap_or_else(|err| {
|
warn!("Couldn't toggle fan mode: {:?}", err);
|
||||||
warn!("Couldn't toggle fan mode: {:?}", err);
|
});
|
||||||
});
|
}
|
||||||
}
|
GX502Keys::ScreenToggle => {
|
||||||
GX502Keys::ScreenToggle => {
|
rogcore.virt_keys().press(ConsumerKeys::BacklightTog.into());
|
||||||
rogcore.virt_keys().press(ConsumerKeys::BacklightTog.into());
|
}
|
||||||
}
|
GX502Keys::TouchPadToggle => {
|
||||||
GX502Keys::TouchPadToggle => {
|
let mut key = [0u8; 32];
|
||||||
let mut key = [0u8; 32];
|
key[0] = 0x01;
|
||||||
key[0] = 0x01;
|
key[3] = 0x070;
|
||||||
key[3] = 0x070;
|
rogcore.virt_keys().press(key);
|
||||||
rogcore.virt_keys().press(key);
|
}
|
||||||
}
|
GX502Keys::Rog => {
|
||||||
GX502Keys::Rog => {
|
//rogcore.aura_effect_init()?;
|
||||||
//rogcore.aura_effect_init()?;
|
//rogcore.aura_write_effect(&self.per_key_led)?;
|
||||||
//rogcore.aura_write_effect(&self.per_key_led)?;
|
// let mut key = [0u8; 32];
|
||||||
// let mut key = [0u8; 32];
|
// key[0] = 0x01;
|
||||||
// key[0] = 0x01;
|
// key[3] = 0x68; // XF86Tools? F13
|
||||||
// key[3] = 0x68; // XF86Tools? F13
|
// rogcore.virt_keys().press(key);
|
||||||
// rogcore.virt_keys().press(key);
|
}
|
||||||
}
|
GX502Keys::None => {
|
||||||
GX502Keys::None => {
|
if key_buf[0] != 0x5A {
|
||||||
if key_buf[0] != 0x5A {
|
info!("Unmapped key, attempt passthrough: {:X?}", &key_buf[1]);
|
||||||
info!("Unmapped key, attempt passthrough: {:X?}", &key_buf[1]);
|
rogcore.virt_keys().press(key_buf);
|
||||||
rogcore.virt_keys().press(key_buf);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -143,11 +141,9 @@ impl LaptopGX502 {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
use async_trait::async_trait;
|
|
||||||
#[async_trait]
|
|
||||||
impl Laptop for LaptopGX502 {
|
impl Laptop for LaptopGX502 {
|
||||||
async fn run(&self, rogcore: &mut RogCore) -> Result<(), AuraError> {
|
fn run(&self, rogcore: &mut RogCore, key_buf: [u8; 32]) -> Result<(), AuraError> {
|
||||||
self.do_keypress_actions(rogcore).await
|
self.do_keypress_actions(rogcore, key_buf)
|
||||||
}
|
}
|
||||||
fn led_endpoint(&self) -> u8 {
|
fn led_endpoint(&self) -> u8 {
|
||||||
self.led_endpoint
|
self.led_endpoint
|
||||||
@@ -155,6 +151,9 @@ impl Laptop for LaptopGX502 {
|
|||||||
fn key_endpoint(&self) -> u8 {
|
fn key_endpoint(&self) -> u8 {
|
||||||
self.key_endpoint
|
self.key_endpoint
|
||||||
}
|
}
|
||||||
|
fn key_filter(&self) -> &[u8] {
|
||||||
|
&self.report_filter_bytes
|
||||||
|
}
|
||||||
fn usb_vendor(&self) -> u16 {
|
fn usb_vendor(&self) -> u16 {
|
||||||
self.usb_vendor
|
self.usb_vendor
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,7 +1,6 @@
|
|||||||
use crate::aura::BuiltInModeByte;
|
use crate::aura::BuiltInModeByte;
|
||||||
use crate::core::RogCore;
|
use crate::core::RogCore;
|
||||||
use crate::error::AuraError;
|
use crate::error::AuraError;
|
||||||
use async_trait::async_trait;
|
|
||||||
//use keycode::{KeyMap, KeyMappingId, KeyState, KeyboardState};
|
//use keycode::{KeyMap, KeyMappingId, KeyState, KeyboardState};
|
||||||
use log::info;
|
use log::info;
|
||||||
|
|
||||||
@@ -63,13 +62,13 @@ pub(crate) fn match_laptop() -> Box<dyn Laptop> {
|
|||||||
///
|
///
|
||||||
/// If using the `keycode` crate to build keyboard input, the report must be prefixed
|
/// If using the `keycode` crate to build keyboard input, the report must be prefixed
|
||||||
/// with the report ID (usually `0x01` for the virtual keyboard).
|
/// with the report ID (usually `0x01` for the virtual keyboard).
|
||||||
#[async_trait]
|
|
||||||
pub(crate) trait Laptop {
|
pub(crate) trait Laptop {
|
||||||
fn board_name(&self) -> &str;
|
fn board_name(&self) -> &str;
|
||||||
fn prod_family(&self) -> &str;
|
fn prod_family(&self) -> &str;
|
||||||
async fn run(&self, core: &mut RogCore) -> Result<(), AuraError>;
|
fn run(&self, core: &mut RogCore, key_buf: [u8; 32]) -> Result<(), AuraError>;
|
||||||
fn led_endpoint(&self) -> u8;
|
fn led_endpoint(&self) -> u8;
|
||||||
fn key_endpoint(&self) -> u8;
|
fn key_endpoint(&self) -> u8;
|
||||||
|
fn key_filter(&self) -> &[u8];
|
||||||
fn usb_vendor(&self) -> u16;
|
fn usb_vendor(&self) -> u16;
|
||||||
fn usb_product(&self) -> u16;
|
fn usb_product(&self) -> u16;
|
||||||
fn supported_modes(&self) -> &[BuiltInModeByte];
|
fn supported_modes(&self) -> &[BuiltInModeByte];
|
||||||
|
|||||||
Reference in New Issue
Block a user