Turning off power to usb port. Or turn off power to entire usb subsystem

kernelpower-managementusb

I have a usb lamp which I specifically bought in order to turn it off programmatically at a certain time, thus I need to remove the power to its usb port.

I believe I have a usb-hub at usb6. The lamp is connected to one of the ports in this hub:

#myhost$ lsusb 
Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub
Bus 002 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 003 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 004 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 005 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 006 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 007 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 008 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub
...
...
Bus 008 Device 006: ID 050d:0234 Belkin Components F5U234 USB 2.0 4-Port Hub

Here's what I've tried:

Two solutions are here, the first suggests:

echo disabled > /sys/bus/usb/devices/usb1/power/wakeup 
echo suspend > /sys/bus/usb/devices/usb1/power/level  # turn off

but I get write error: Invalid argument when trying to write to /sys/bus/usb/devices/usb1/power/level:

$sudo bash -c 'echo disabled > /sys/bus/usb/devices/usb6/power/wakeup'
$echo suspend|sudo tee /sys/bus/usb/devices/usb6/power/level suspend
tee: /sys/bus/usb/devices/usb6/power/level: Invalid argument
$sudo bash -c 'echo suspend> /sys/bus/usb/devices/usb6/power/level'bash: line 0: echo: write error: Invalid argument

The second solution:

sudo bash -c 'echo 0 > /sys/bus/usb/devices/usb6/power/autosuspend_delay_ms; echo auto > /sys/bus/usb/devices/usb6/power/control'

which does turn off power to the usb-hub device.

I was also trying to follow this:

But the output of lsusb -t just hangs:

$lsusb -t
4-1:0.0: No such file or directory
4-1:0.1: No such file or directory
^C

Which prevents me from using this method to get the '2-1.1' part to this:

echo '2-1.1' > /sys/bus/usb/drivers/usb/unbind

Is there an alternative way of getting this information?

Alternatively, is there a way to shut off power to the entire usb subsystem? Something like modprobe -r usb_etc?

My kernel is:

$uname -r
3.2.0-4-amd64

Best Answer

You could use my tool uhubctl - command line utility to control USB power per port for compatible USB hubs.

It works only on hubs that support per-port power switching, but note that many modern motherboards have USB hubs that support this feature.

To compile:

git clone https://github.com/mvp/uhubctl
cd uhubctl
make

To install system-wide as /usr/sbin/uhubctl:

sudo make install

To list status of all hubs, their locations and ports that can be controlled by uhubctl:

sudo uhubctl

(you can avoid using sudo if you configure udev USB permissions).

To turn off power on port 5 of single compatible hub:

sudo uhubctl -a 0 -p 5

If you have more than one compatible hub connected, use -l to specify hub location to control it:

sudo uhubctl -a 0 -p 5 -l 3-1.2

To toggle power off then on:

sudo uhubctl -a 2 -p 5

Note that USB 3.0 hubs are also supported, and quite a few new USB 3.0 hubs actually work well.

Read more here.

Related Question