Add general quirk support and specific quirk for SD mem clock bug

This commit is contained in:
NGnius (Graham) 2024-02-01 19:39:29 -05:00
parent 59a0727f88
commit 32a36f8627
10 changed files with 120 additions and 41 deletions

View file

@ -8,6 +8,8 @@ pub struct Base {
pub configs: Vec<super::Config>,
/// Server messages
pub messages: Vec<super::DeveloperMessage>,
/// Base URL for the config store
pub store: String,
/// URL from which to grab the next update
pub refresh: Option<String>,
}
@ -110,7 +112,7 @@ impl Default for Base {
..Default::default()
}; 4],
global_governors: true,
experiments: false,
..Default::default()
}
},
gpu: super::GpuLimit {
@ -154,7 +156,7 @@ impl Default for Base {
..Default::default()
}; 12], // 6 cores with SMTx2
global_governors: true,
experiments: false,
..Default::default()
}
},
gpu: super::GpuLimit {
@ -198,7 +200,7 @@ impl Default for Base {
..Default::default()
}; 16], // 8 cores with SMTx2
global_governors: true,
experiments: false,
..Default::default()
}
},
gpu: super::GpuLimit {
@ -242,7 +244,7 @@ impl Default for Base {
..Default::default()
}; 16], // 8 cores with SMTx2
global_governors: true,
experiments: false,
..Default::default()
}
},
gpu: super::GpuLimit {
@ -286,7 +288,7 @@ impl Default for Base {
..Default::default()
}; 16], // 8 cores with SMTx2
global_governors: true,
experiments: false,
..Default::default()
}
},
gpu: super::GpuLimit {
@ -341,6 +343,7 @@ impl Default for Base {
url: Some("https://git.ngni.us/NG-SD-Plugins/PowerTools/wiki".to_owned()),
}
],
store: "https://powertools.ngni.us".to_owned(),
refresh: Some("http://limits.ngni.us:45000/powertools/v2".to_owned())
}
}

View file

@ -19,7 +19,7 @@ pub struct GenericBatteryLimit {
pub charge_modes: Vec<String>,
pub charge_limit: Option<RangeLimit<f64>>, // battery charge %
pub extra_readouts: bool,
pub experiments: bool,
pub extras: super::LimitExtras,
}
impl GenericBatteryLimit {
@ -47,7 +47,7 @@ impl GenericBatteryLimit {
max: Some(90.0),
}),
extra_readouts: false,
experiments: false,
extras: Default::default(),
}
}
@ -67,7 +67,10 @@ impl GenericBatteryLimit {
max: Some(99.0),
}),
extra_readouts: true,
experiments: true,
extras: super::LimitExtras {
experiments: true,
quirks: vec!["".to_owned()].into_iter().collect(),
},
}
}
@ -91,6 +94,6 @@ impl GenericBatteryLimit {
}
}
self.extra_readouts = limit_override.extra_readouts;
self.experiments = limit_override.experiments;
self.extras = limit_override.extras;
}
}

View file

@ -19,7 +19,7 @@ pub enum CpuLimitType {
pub struct GenericCpusLimit {
pub cpus: Vec<GenericCpuLimit>,
pub global_governors: bool,
pub experiments: bool,
pub extras: super::LimitExtras,
}
impl GenericCpusLimit {
@ -29,14 +29,17 @@ impl GenericCpusLimit {
Self {
cpus: [(); 8].iter().enumerate().map(|(i, _)| GenericCpuLimit::default_for(&t, i)).collect(),
global_governors: true,
experiments: false,
extras: Default::default(),
}
},
CpuLimitType::DevMode => {
Self {
cpus: [(); 11].iter().enumerate().map(|(i, _)| GenericCpuLimit::default_for(&t, i)).collect(),
global_governors: true,
experiments: true,
extras: super::LimitExtras {
experiments: true,
quirks: vec!["".to_owned()].into_iter().collect(),
},
}
},
t => {
@ -48,7 +51,7 @@ impl GenericCpusLimit {
Self {
cpus,
global_governors: true,
experiments: false,
extras: Default::default(),
}
}
}
@ -76,7 +79,7 @@ impl GenericCpusLimit {
.for_each(|(cpu, limit_override)| cpu.apply_override(limit_override));
}
self.global_governors = limit_override.global_governors;
self.experiments = limit_override.experiments;
self.extras = limit_override.extras;
}
}

View file

@ -32,7 +32,7 @@ pub struct GenericGpuLimit {
pub memory_clock: Option<RangeLimit<u64>>,
pub memory_clock_step: Option<u64>,
pub skip_resume_reclock: bool,
pub experiments: bool,
pub extras: super::LimitExtras,
}
impl GenericGpuLimit {
@ -72,16 +72,21 @@ impl GenericGpuLimit {
max: Some(1600),
}),
clock_step: Some(100),
// Disabled for now since LCD version is a bit broken on sysfs right now
/*memory_clock: Some(RangeLimit {
// LCD version is a bit broken on sysfs, but it's ok
memory_clock: Some(RangeLimit {
min: Some(400),
max: Some(800),
}),
memory_clock_step: Some(400),*/
memory_clock: None,
memory_clock_step: None,
memory_clock_step: Some(400),
skip_resume_reclock: false,
experiments: false,
extras: super::LimitExtras {
experiments: false,
quirks: vec![
"pp_dpm_fclk-reversed".to_owned(),
"pp_dpm_fclk-not-updated-on-LCD".to_owned(),
//"pp_dpm_fclk-static".to_owned(),
].into_iter().collect(),
}
}
}
@ -124,7 +129,10 @@ impl GenericGpuLimit {
}),
memory_clock_step: Some(100),
skip_resume_reclock: false,
experiments: true,
extras: super::LimitExtras {
experiments: true,
quirks: vec!["dev".to_owned()].into_iter().collect(),
},
}
}
@ -190,6 +198,6 @@ impl GenericGpuLimit {
self.clock_step = Some(val);
}
self.skip_resume_reclock = limit_override.skip_resume_reclock;
self.experiments = limit_override.experiments;
self.extras = limit_override.extras;
}
}

View file

@ -26,3 +26,9 @@ pub struct Limit<P, L> {
pub type CpuLimit = Limit<super::CpuLimitType, super::GenericCpusLimit>;
pub type GpuLimit = Limit<super::GpuLimitType, super::GenericGpuLimit>;
pub type BatteryLimit = Limit<super::BatteryLimitType, super::GenericBatteryLimit>;
#[derive(Serialize, Deserialize, Debug, Clone, Default)]
pub struct LimitExtras {
pub experiments: bool,
pub quirks: std::collections::HashSet<String>,
}

View file

@ -16,6 +16,6 @@ pub use cpu_limit::{CpuLimitType, GenericCpusLimit, GenericCpuLimit};
pub use devel_message::DeveloperMessage;
pub use gpu_limit::{GpuLimitType, GenericGpuLimit};
pub use config::Config;
pub use limits::{Limits, Limit, CpuLimit, GpuLimit, BatteryLimit};
pub use limits::{Limits, Limit, CpuLimit, GpuLimit, BatteryLimit, LimitExtras};
pub use range::RangeLimit;
pub use target::Target;

View file

@ -1,17 +1,40 @@
use std::sync::mpsc::{self, Sender};
use std::sync::{Arc, Mutex};
use std::sync::{Arc, Mutex, RwLock};
use usdpl_back::core::serdes::Primitive;
use usdpl_back::AsyncCallable;
use super::handler::{ApiMessage, GeneralMessage};
const BASE_URL: &'static str = "http://powertools.ngni.us";
const BASE_URL_FALLBACK: &'static str = "https://powertools.ngni.us";
static BASE_URL: RwLock<Option<String>> = RwLock::new(None);
pub fn set_base_url(base_url: String) {
*BASE_URL.write().expect("Failed to acquire write lock for store base url") = Some(base_url);
}
fn get_base_url() -> String {
BASE_URL.read().expect("Failed to acquire read lock for store base url")
.clone()
.unwrap_or_else(|| BASE_URL_FALLBACK.to_owned())
}
fn url_search_by_app_id(steam_app_id: u32) -> String {
format!("{}/api/setting/by_app_id/{}", get_base_url(), steam_app_id)
}
fn url_download_config_by_id(id: u128) -> String {
format!("{}/api/setting/by_id/{}", get_base_url(), id)
}
fn url_upload_config() -> String {
format!("{}/api/setting", get_base_url())
}
/// Get search results web method
pub fn search_by_app_id() -> impl AsyncCallable {
let getter = move || {
move |steam_app_id: u32| {
let req_url = format!("{}/api/setting/by_app_id/{}", BASE_URL, steam_app_id);
let req_url = url_search_by_app_id(steam_app_id);
match ureq::get(&req_url).call() {
Ok(response) => {
let json_res: std::io::Result<Vec<community_settings_core::v1::Metadata>> =
@ -110,7 +133,7 @@ fn web_config_to_settings_json(
}
fn download_config(id: u128) -> std::io::Result<community_settings_core::v1::Metadata> {
let req_url = format!("{}/api/setting/by_id/{}", BASE_URL, id);
let req_url = url_download_config_by_id(id);
let response = ureq::get(&req_url).call().map_err(|e| {
log::warn!("GET to {} failed: {}", req_url, e);
std::io::Error::new(std::io::ErrorKind::ConnectionAborted, e)
@ -207,7 +230,7 @@ fn settings_to_web_config(
}
fn upload_config(config: community_settings_core::v1::Metadata) -> std::io::Result<()> {
let req_url = format!("{}/api/setting", BASE_URL);
let req_url = url_upload_config();
ureq::post(&req_url)
.send_json(&config)
.map_err(|e| {

View file

@ -32,6 +32,7 @@ pub fn spawn() -> JoinHandle<()> {
save_base(&base, &limits_path);
base
};
crate::api::web::set_base_url(base.store);
if let Some(refresh) = &base.refresh {
// try to retrieve newer version
match ureq::get(refresh).call() {

View file

@ -192,18 +192,50 @@ impl Gpu {
fn build_memory_clock_payload(&self, clock: u64) -> String {
let max_val = self.quantize_memory_clock(clock);
match max_val {
0 => "0\n".to_owned(),
max_val => {
use std::fmt::Write;
let mut payload = String::from("0");
for i in 1..max_val {
write!(payload, " {}", i)
let is_oled = matches!(self.variant, super::Model::OLED);
let is_lcd = matches!(self.variant, super::Model::LCD);
let is_lock_feature_enabled = self.limits.extras.quirks.contains("pp_dpm_fclk-static");
if (is_oled && self.limits.extras.quirks.contains("pp_dpm_fclk-reversed-on-OLED"))
|| (is_lcd && self.limits.extras.quirks.contains("pp_dpm_fclk-reversed-on-LCD"))
|| self.limits.extras.quirks.contains("pp_dpm_fclk-reversed") {
let options_count = self
.sysfs_card
.read_value(GPU_MEMORY_DOWNCLOCK_ATTRIBUTE.to_owned())
.map(|b| parse_pp_dpm_fclk(&String::from_utf8_lossy(&b)).len())
.unwrap_or_else(|_| if is_oled { 4 } else { 2 });
let modifier = (options_count - 1) as u64;
if is_lock_feature_enabled {
format!("{}\n", modifier - max_val)
} else {
if max_val == 0 as u64 {
format!("{}\n", modifier)
} else {
use std::fmt::Write;
let mut payload = format!("{}", modifier - max_val);
for i in (0..max_val).rev(/* rev() isn't necessary but it creates a nicer (ascending) order */) {
write!(payload, " {}", modifier - i)
.expect("Failed to write to memory payload (should be infallible!?)");
}
write!(payload, "\n")
.expect("Failed to write to memory payload (should be infallible!?)");
payload
}
}
} else {
match max_val {
0 => "0\n".to_owned(),
max_val => {
use std::fmt::Write;
let mut payload = String::from("0");
for i in 1..max_val {
write!(payload, " {}", i)
.expect("Failed to write to memory payload (should be infallible!?)");
}
write!(payload, " {}\n", max_val)
.expect("Failed to write to memory payload (should be infallible!?)");
payload
}
write!(payload, " {}\n", max_val)
.expect("Failed to write to memory payload (should be infallible!?)");
payload
}
}
}

View file

@ -23,7 +23,7 @@ import {
//joinClassNames,
} from "decky-frontend-lib";
import { VFC, useState } from "react";
import { GiDrill, GiTimeBomb, GiTimeTrap, GiDynamite } from "react-icons/gi";
import { GiDrill, GiFireExtinguisher, GiFireBomb, GiMineExplosion } from "react-icons/gi";
import { HiRefresh, HiTrash, HiPlus, HiUpload } from "react-icons/hi";
import { TbWorldPlus } from "react-icons/tb";
@ -532,7 +532,7 @@ export default definePlugin((serverApi: ServerAPI) => {
let ico = <GiDrill />;
let now = new Date();
if (now.getDate() == 1 && now.getMonth() == 3) {
ico = <span><GiDynamite /><GiTimeTrap /><GiTimeBomb /></span>;
ico = <span><GiFireExtinguisher /><GiFireBomb /><GiMineExplosion /></span>;
}
//registerCallbacks(false);
serverApi.routerHook.addRoute(STORE_RESULTS_URI, StoreResultsPage);