How can I prevent linux from initializing a USB HID device - linux

I have a USB HID device that can work in two different modes. The selection of modes is based on the sequence of USB enumeration/initialization packets sent to it.
I am using a Raspberry Pi 3 running Raspbian, however I also see the same issue if I compile my code for my desktop Ubuntu distro.
The issue I have is that linux is recognizing the USB device as a HID device and then sending the sequence of commands that it deems necessary to start the device, and this works correctly and starts the device in "Mode 1".
However I need to start the device in "Mode 2" and to do this I need to send a slightly different set of enumeration/initialization commands.
I am new to linux but very experienced with LibUSB and LibUSBDotNet under windows and can get the behavior I desire under windows.
Windows has similar behaviour to linux in that it will enumerate, recognise the device as a USB HID device and then initialise it as it deems fit resulting in the device going into "Mode 1". To prevent windows doing this I can create a LibUSB filter driver for the device, which then replaces the default driver, so windows will now do the initial enumeration, realise that the VID and PID of the device are managed by the LibUSB filter driver (rather than the windows HID driver) and then stop enumeration/initialization - this allows my code to take over and complete the initialization into "Mode 2".
How can I stop Linux from fully enumerating/initializing this device (as I do with windows). Perhaps I need to do something with udev rules or something, but I would have no idea what as I am new to linux.
Any help greatly appreciated

you have right, you have to play with the udev rules.
First of all you have to identify your device. Find the idProduct and the idVendor of your device. You can use:
lsusb
Then in the rules.d folder (/etc/udev/rules.d) create a new file with the name:
10-my-usb.rules
In this file add this line
SUBSYSTEM=="usb",ATTRS{idVendor}=="XXXX", ATTRS{idProduct}=="XXXX", MODE="666", GROUP+="plugdev"
Replace the XXXX with the value you get before
Then restart your udev rules:
sudo udevadm trigger
Then unplug and replug normally you can use it

Related

how to know if a USB device is plugged into the embedded Linux system

I'm new to the embedded Linux world. I'm using Nvidia Jetson Nano as my embedded SOC.
Now I need my application to do some specific thing, for example, show an icon, as long as a USB disk is plugged into the embedded board. How can I know if such a USB disk is plugged in?
I need to know the approach for knowing the as long as a USB disk is plugged in
You can check all USB devices that are plugged in with the commands :
$ lsusb
Or with the command :
$ ls /dev/ttyUSB
You could then check if one of the listed devices (/dev/ttyUSB0 for example) is in the list and do your action.
What programming language are you using for your application ? There must be libraries that can help you check easily if a USB is connected/disconnected

How to detect when a usb cable is connected/disconnected on the device side in Linux 2.6.37?

I have a embedded device that runs linux 2.6.37.
I want my application to know when the USB is connected.
Currently I can achieve this by pooling
/sys/devices/platform/musb/musb-hdrc.0/vbus.
However this approach does not distinguish between a USB charger or a USB host.
I found this udev approach but I don't think it's available in my version of the kernel. because I did not find any USB related nodes in my /dev. This discussing also shows that it might not be feasible, ether.
I also found linux hotplug and tried the netlink example, but I didn't see any output running the example when I connect/disconnect the USB cable.
What I want to do is to detect connection type on the device, when USB is connected, and prepare (unmount file system) and switch to g_file_storage if device is connected to a host, and do nothing if device is connect to a charger.
How shall I achieve this?
To achieve that, you can use the inotify(7) feature, available in all linux kernels to be awaken as soon as some device node gets created in /sys.
To know what type of device you have, you have to read the usb info from proper usb ioctl call (or if you are not a kernel interface expert, using the libusb interface) to get the device vendor, device id and device class fields coming from the device. Normally, the hotplug software gets informed on these clase of events (via a special socket). The most probably reason you don't get the device properly initialized is some misconfiguration in the config files for udev system, which normally has one entry for each possible device vendor/device id pair and allows it to load the appropiate device driver to control it. The process continues with the device driver module creating dynamically the actual devices, and they'll appear in the /dev/ filesystem as a consequence of some other kernel event to udevd.
Read apropiate documents in <linux_src>/Documentation (this directory directory belongs to the linux kernel source code, so you'll probably need to install it), and udevd(8) man pages to be able to add a new usb.
On 2.6.37 kernel, this could be done by polling
/sys/devices/platform/musb-omap2430.0/musb-hdrc.0/mode
If handshake with host is successful then it will read as "peripheral", if fail it'll be "idle".

Linux Virtual USB device driver

My goal is to create a virtual USB char device (not block device) for Linux 2.6.32 and above (I use debian squeeze) that would be recognize by the system.
I would like that this device be listed with lsusb as a normal USB device, and that every application could use libusb in order to open the device, and send control message, and make bulk write/read. But behind this virtual device, it's behavior would be set by my application. I want to set it's product ID, it's vendor ID, answer to USB status, and bulk read.
I've read some posts about how to use USB/IP in order to create a virtual USB device, and that's exactly what I want to do
Installation and emulation of virtual USB Device
http://breaking-the-system.blogspot.fr/2014/08/emulating-usb-devices-in-python-with-no.html
But unfortunately, when I tried with 2.6.32 kernel and above, I didn't succeed making it work. So I looked at how to create a kernel module that would create the virtual device :
http://pete.akeo.ie/2011/08/writing-linux-device-driver-for-kernels.html
This one looks great also, but the sample provided doest not indicate how to make it an USB device.
I've seen some post talking about it with windows but none that could help me with Linux.
I would like to avoid buying some USB programmable cards when it can be done with software.
Have anyone any leads on how to make the first methods works under newer kernel, or convert the sample code of the second method for making an USB device ?
I have fixed the code of http://breaking-the-system.blogspot.fr/2014/08/emulating-usb-devices-in-python-with-no.html (first method using USB/IP) to work with linux 4.3.
In the original code are missing USB requests like set configuration and get status. Without the implementation of all USB requests used for the OS driver the code will not work.
The fixed code can be downloaded in https://github.com/lcgamboa/USB-Emulation .
I guess raw-gadget kernel module is the thing that you want?
you can check the dummy_hcd and tests directory inside the repo, it will guide you how to create a virtual USB device

USB not detected by i.mx 287 EVK (FreeScale) board

I am using i.mx 287 EVK from freescale for my application development.
I am ported linux kernel and rootfs successfully.
But the problem is my hardware does't detect the USB stick if connected.
Nothing changes in /dev directory nor anything appears in log (dmesg).
Kindly help me resolve it.
Hardware has both usb host and device ports.
Basic things i would check :
Check with other USB.
Connect a USB Mouse or USB keyboard. Check if they are working. Check if the devices are getting power or not.
If you are not getting the power, definitely there is a problem with the kernel configuration.
Do make menuconfig from the linux folder, go to USB drivers section and enable all the flags that are needed for a USB pendrive to work.
Easy method would be to take the configuration file(kconfig) of a working linux kernel, copy it inside your kernel, compile it and run it. It should work
ITs been a while that i did the above things. But this should help you out of your current problem.

How can I figure out which tty file points to which USB-to-Serial device?

I have two legacy machines connected to a Linux box with USB using the ftdi_sio driver, to /dev/ttyUSB0 and /dev/ttyUSB1. The Linux box is relaying and analyzing the traffic between the machines. When the Linux box boots up, the machines are connected to the files pretty much randomly. The problem is to know which one is which.
I could just ask the devices, of course, but I'd like to avoid the risk of malfunction due to sending wrong data to the wrong device. Is there a way to figure out, for example, the id of the device connected to a tty file?
Check this Using Linux USB page.
/proc/bus/usb/devices lists information about the devices currently attached to the USB bus. This is very useful when trying to figure out if the device is correctly enumerated.
Maybe you can use the output from lsusb -v and look at iProduct + iSerial to determine the order the devices are attached.

Resources