forked from linrunner/TLP
-
Notifications
You must be signed in to change notification settings - Fork 0
/
tlp-usblist
executable file
·124 lines (104 loc) · 3.54 KB
/
tlp-usblist
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
#!/usr/bin/perl
# tlp-usblist - list usb device info with autosuspend attributes
#
# Copyright (c) 2016 Thomas Koch <linrunner at gmx.net>
# This software is licensed under the GPL v2 or later.
package tlp_usblist;
use strict;
use warnings;
# --- Constants
use constant USBD => "/sys/bus/usb/devices";
# --- Global vars
my %usbdevices;
my $udev;
my $no_runtimepm = 0;
# --- Subroutines
# Read content from a sysfile
# $_[0]: input file
# return: content / empty string if nonexistent or not readable
sub catsysf {
my $sysval = "";
if (open (SYSF, "$_[0]")) {
chomp ($sysval = <SYSF>);
close (SYSF);
}
return $sysval;
}
# Read device driver from DEVICE/uevent
# $_[0]: (sub)device base path
# return: driver / empty string if uevent nonexistent or not readable
sub getdriver {
my $driver = "";
if ( open (SYSF, "$_[0]/uevent") ) {
# read file line by line
while (<SYSF>) {
# match line content and return DRIVER= value
if ( s/^DRIVER=(.*)/$1/ ) {
chomp ($driver = $_);
last; # break loop
}
}
close (SYSF);
}
return $driver
}
# Get drivers associated with USB device by iterating subdevices
# $_[0]: device base path
# return: driver list / "no driver" if none found
sub usbdriverlist {
my $driverlist = "";
my $subdev;
# iterate subdevices
foreach $subdev (glob "$_[0]/*:*") {
# get subdevice driver
my $driver = getdriver ("$subdev");
if ( $driver ) {
if (index ($driverlist, $driver) == -1) {
if ($driverlist) { $driverlist = $driverlist . ", " . $driver; }
else { $driverlist = $driver; }
} # if index
} # if $driver
} # foreach $subdev
if (! $driverlist) { $driverlist = "no driver"; }
return $driverlist
}
# --- MAIN
# Check if Runtime PM is enabled
$no_runtimepm = 1 if ( ! glob USBD . "/*/power/autosuspend*");
# Read USB device tree attributes as arrays into %usbdevices hash, indexed by Bus_Device
foreach $udev (grep { ! /:/ } glob USBD . "/*") {
my ($asf, $asv);
my ($cnf, $cnv);
my $usbv = "(autosuspend not available)";
# get device id
my $usbk = sprintf ("%03d_%03d", catsysf ("$udev/busnum"), catsysf ("$udev/devnum") );
# look for autosuspend_delay_ms then autosuspend (deprecated)
foreach $asf ( "autosuspend_delay_ms", "autosuspend" ) {
if ( length ( $asv = catsysf ("$udev/power/$asf") ) ) {
# autosuspend* exists --> check for control then level (deprecated)
foreach $cnf ( "control", "level" ) {
if ( $cnv = catsysf ("$udev/power/$cnf") ) {
if ( $asf eq "autosuspend_delay_ms" ) {
$usbv = sprintf ("%s = %-5s %s = %5d", $cnf, $cnv . ",", $asf, $asv);
} else {
$usbv = sprintf ("%s = %-5s %s = %2d", $cnf, $cnv . ",", $asf, $asv);
}
last; # break loop
}
}
last; # break loop
}
}
# save formatted result in hash
@{$usbdevices{$usbk}} = ($udev, $usbv);
}
# Output device list with attributes and drivers
foreach (`lsusb 2> /dev/null`) {
my ($bus, $dev, $usbid, $desc) = /Bus (\S+) Device (\S+): ID (\S+)[ ]+(.*)/;
my $usbk = $bus . "_" . $dev;
$desc ||= "<unknown>";
print "Bus $bus Device $dev ID $usbid $usbdevices{$usbk}[1] -- $desc ("
. usbdriverlist ($usbdevices{$usbk}[0]) . ")\n";
}
exit 4 if ( $no_runtimepm == 1 );
exit 0;