@@ -43,6 +43,13 @@ const DRM_ENGINES: &[(&str, ProcessUtilizationType)] = &[
4343 ( "video" , ProcessUtilizationType :: Decode ) ,
4444] ;
4545const FALLBACK_MAX_POWER_CAP : f64 = 400.0 ;
46+ const POWER_CAP_NAMES : & [ & str ] = & [ "power1_cap" , "power2_cap" , "power1_max" , "power2_max" ] ;
47+ const MAX_POWER_CAP_NAMES : & [ & str ] = & [
48+ "power1_rated_max" ,
49+ "power2_rated_max" ,
50+ "power1_crit" ,
51+ "power2_crit" ,
52+ ] ;
4653
4754#[ derive( Clone , Copy ) ]
4855enum DriverType {
@@ -189,7 +196,11 @@ impl IntelGpuController {
189196 }
190197
191198 fn write_file ( & self , path : impl AsRef < Path > , contents : & str ) -> anyhow:: Result < ( ) > {
192- let file_path = self . common . sysfs_path . join ( path) ;
199+ let file_path = if path. as_ref ( ) . is_absolute ( ) {
200+ Cow :: Borrowed ( path. as_ref ( ) )
201+ } else {
202+ Cow :: Owned ( self . common . sysfs_path . join ( path) )
203+ } ;
193204
194205 if file_path. exists ( ) {
195206 fs:: write ( & file_path, contents)
@@ -237,57 +248,31 @@ impl IntelGpuController {
237248 . flatten ( )
238249 }
239250
251+ fn match_hwmon_files < ' a > (
252+ & ' a self ,
253+ possible_names : & ' a [ & str ] ,
254+ ) -> impl Iterator < Item = PathBuf > + ' a {
255+ self . hwmon_path
256+ . iter ( )
257+ . flat_map ( |hwmon| possible_names. iter ( ) . map ( |file| hwmon. join ( file) ) )
258+ . filter ( |path| path. exists ( ) )
259+ }
260+
240261 fn read_hwmon_file ( & self , possible_names : & [ & str ] , filter_zero : bool ) -> Option < u64 > {
241- self . hwmon_path . as_ref ( ) . and_then ( |hwmon| {
242- let mut iter = possible_names
243- . iter ( )
244- . map ( |file| hwmon. join ( file) )
245- . filter_map ( |path| self . read_file ( path) ) ;
246-
247- if filter_zero {
248- iter. find ( |value| * value != 0 )
249- } else {
250- iter. next ( )
251- }
252- } )
262+ self . match_hwmon_files ( possible_names)
263+ . filter_map ( |path| self . read_file :: < u64 > ( path) )
264+ . find ( |value| !filter_zero || * value != 0 )
253265 }
254266
255- fn write_hwmon_file (
256- & self ,
257- file_prefix : & str ,
258- file_suffix : & str ,
259- contents : & str ,
260- ) -> anyhow:: Result < ( ) > {
261- debug ! ( "writing value '{contents}' to '{file_prefix}*{file_suffix}'" ) ;
267+ fn write_hwmon_file ( & self , possible_names : & [ & str ] , contents : & str ) -> anyhow:: Result < ( ) > {
268+ let path = self
269+ . match_hwmon_files ( possible_names)
270+ . next ( )
271+ . context ( "Cap file not found" ) ?;
262272
263- if let Some ( hwmon_path) = & self . hwmon_path {
264- let mut files = Vec :: with_capacity ( 1 ) ;
273+ debug ! ( "writing value '{contents}' to '{}'" , path. display( ) ) ;
265274
266- let entries = fs:: read_dir ( hwmon_path) ?;
267- for entry in entries. flatten ( ) {
268- if let Some ( name) = entry. file_name ( ) . to_str ( ) {
269- if name. starts_with ( file_prefix) && name. ends_with ( file_suffix) {
270- if let Some ( infix) = name
271- . strip_prefix ( file_prefix)
272- . and_then ( |name| name. strip_suffix ( file_suffix) )
273- {
274- if !infix. contains ( '_' ) {
275- files. push ( entry. path ( ) ) ;
276- }
277- }
278- }
279- }
280- }
281- files. sort_unstable ( ) ;
282-
283- if let Some ( entry) = files. first ( ) {
284- self . write_file ( entry, contents)
285- } else {
286- Err ( anyhow ! ( "File not found" ) )
287- }
288- } else {
289- Err ( anyhow ! ( "No hwmon available" ) )
290- }
275+ self . write_file ( path, contents)
291276 }
292277
293278 fn get_drm_info_i915 ( & self ) -> IntelDrmInfo {
@@ -579,28 +564,17 @@ impl IntelGpuController {
579564
580565 #[ allow( clippy:: cast_precision_loss) ]
581566 fn get_power_cap ( & self ) -> Option < f64 > {
582- self . read_hwmon_file (
583- & [ "power1_cap" , "power2_cap" , "power1_max" , "power2_max" ] ,
584- true ,
585- )
586- . map ( |value| value / 1_000_000 )
587- . map ( |value| value as f64 ) // Placeholder max value
567+ self . read_hwmon_file ( POWER_CAP_NAMES , true )
568+ . map ( |value| value / 1_000_000 )
569+ . map ( |value| value as f64 )
588570 }
589571
590572 #[ allow( clippy:: cast_precision_loss) ]
591573 fn get_power_cap_max ( & self ) -> Option < f64 > {
592- self . read_hwmon_file (
593- & [
594- "power1_rated_max" ,
595- "power2_rated_max" ,
596- "power1_crit" ,
597- "power2_crit" ,
598- ] ,
599- true ,
600- )
601- . map ( |cap| cap / 1_000_000 )
602- . map ( |value| value as f64 )
603- . or_else ( || self . get_power_cap ( ) . map ( |_| FALLBACK_MAX_POWER_CAP ) )
574+ self . read_hwmon_file ( MAX_POWER_CAP_NAMES , true )
575+ . map ( |cap| cap / 1_000_000 )
576+ . map ( |value| value as f64 )
577+ . or_else ( || self . get_power_cap ( ) . map ( |_| FALLBACK_MAX_POWER_CAP ) )
604578 }
605579}
606580
@@ -665,7 +639,7 @@ impl GpuController for IntelGpuController {
665639 }
666640
667641 if let Some ( cap) = config. power_cap {
668- self . write_hwmon_file ( "power" , "_max" , & ( ( cap * 1_000_000.0 ) as u64 ) . to_string ( ) )
642+ self . write_hwmon_file ( POWER_CAP_NAMES , & ( ( cap * 1_000_000.0 ) as u64 ) . to_string ( ) )
669643 . context ( "Could not set power cap" ) ?;
670644 }
671645
0 commit comments