• Published on | Jun 24, 2014 | by FozzTexx

Youre not missing USB drivers, Linux hates your keyboard

Many years ago I decided that I wanted to build my own Linux kernel in order to make my own mini PXE boot kernel. I’ve done lots of kernel compiles over the years in order to enable and disable certain things, but had never built a kernel with my own empty config file. I also wanted to see if I could embed an initial filesystem right into the kernel so that I would have just a single file to work with instead of a separate initrd.

Starting with an empty config file was pretty scary since it can take a lot of digging through menu after menu to try to figure out what things need to be turned on to support various kinds of hardware. Since I was planning to use the kernel as a sort of “rescue" system, I wanted the most necessary drivers compiled in instead of as modules.

I started adding in hard drive controllers and ethernet drivers and was able to boot up into a shell and type things on a PS/2 keyboard. But many computers I use only have a USB keyboard. Back through the menus I went hunting down all the various bits and pieces necessary to get a USB keyboard working.

For the most part USB keyboards worked well. But occasionally I would find a computer where the USB keyboard wouldn’t work and I would have to go find a PS/2 keyboard and plug it in. If I had time I would dig through the PCI ids and try to figure out what USB controller it was using so that next time around I could have it already compiled into the kernel. Sometimes though it seemed like there was just no USB driver that would work.

The problem with USB keyboards not working on some computers has plagued me for years. Last weekend I was messing with setting up another computer using my netboot kernel and again I just couldn’t get the USB keyboard to work. Searching on the internet provided no useful answers. This time though I decided I was going to beat my head on it until I figured out which USB controller was in the computer and which driver it needed.

With every USB controller imaginable compiled into the kernel, I still could not get a USB keyboard working. Thinking maybe it was because I was using a USB KVM, I tried plugging the keyboard directly into the computer. Nope. But I did see some USB status messages appear on the console. Hmmm...

I went and grabbed the nearest USB keyboard I could find: an old Apple one. Plugged it in and it worked fine! What’s going on here? My next thought was maybe it didn’t like my keyboard because it was using some funky internal hub that let it combine the mouse and the keyboard together, and maybe I didn’t have USB hub support in the kernel. I tried booting into Knoppix to see if in the early stages my keyboard would work, and it worked fine. I also noticed that it was printing pretty much the exact same status messages on the console when I plugged and unplugged the keyboard.

For some reason when I went back into the kernel config menu, I decided to go dig through the HID menu this time since I felt I had exhausted all of the USB options. One of the choices in there is “Special HID drivers.” Well, it’s just a keyboard, but I can’t find anything else, so I checked it out. After going down a little ways I saw it: “Logitech devices.”

What the heck? Someone on the Linux team pulled an Apple! They’re specifically checking the brand and preventing a Logitech keyboard from acting as a generic HID keyboard! I know what you’re saying, “well maybe Logitech is weird and needs a special driver?” If that were true then a PC BIOS wouldn’t be able to let you go in and make changes without having support for a Logitech keyboard. No, a Logitech keyboard can definitely act as an HID keyboard without needing special support. Whoever worked on the HID keyboard module went out of their way to block Logitech keyboards. Maybe a special driver might be needed to add support for extra Logitech features, but when that support isn’t compiled in, the HID keyboard should not block use of Logitech keyboards!

I’m glad I finally got it figured out. Thinking back, I'm pretty sure every time I had a USB keyboard that didn't work, it was a Logitech branded one. At least now I don’t have to make sure to keep a PS/2 keyboard in my rescue kit.

Commenting disabled for spambots

+1  Posted by Joakim L. Gilje • Jun.26.2014 at 05.48 • Reply

There is indeed a "blacklist" where the generic hid-driver backs of because there is a specific driver. But there is also a way to disable this list. Load the hid-module with ignorespecialdrivers=1, and it should treat all hid-devices as generic devices.

+1  Posted by FozzTexx • Jun.26.2014 at 13.39 • Reply

I shouldn't need to do something special though. If the Logitech driver hasn't been included then it should default to not blacklisting it. And since I'm compiling the hid module into the kernel, I can't load it with a special flag at runtime.

+1  Posted by Joakim L. Gilje • Jun.27.2014 at 05.09 • Reply

Well, I partly disagree with your first statement. As for your second statement, you can. The equivalent would be to add hid.ignorespecialdrivers=1 (in general, module_name.parameter=value) to the kernel arguments at boot time.