6
votes

I have been learning Kernel programming and taking the Eudyptula challenge, and task 5 requires me to modify a hello world module from an earlier task to be automatically loaded when a USB keyboard is plugged, and unloaded when the keyboard is unplugged.

Now, for the sake of it, I will not be posting my code here, because that would be a huge spoiler for this task and would ruin the fun of it for others. Basically, what it does is:

  1. Creates a struct usb_device_id array with one entry that binds my module to any usb keyboard
  2. Creates a struct usb_driver and initializes the proper fields; in particular, it references the usb device id table array that I created previously
  3. Uses the macro MODULE_DEVICE_TABLE to register the driver.

The register / unregister routines are working. I get the expected debugging messages when I manually load and unload the module.

I copied the module to /lib/modules/$(uname -r) and ran depmod -a. The module is added to modules.alias and modules.dep, but nothing happens when I plug / unplug the keyboard.

Further research showed that I should have a modules.usbmap file generated by depmod where the kernel keeps a mapping between devices and drivers to load. I don't have this file anywhere in my folders tree. I also don't have a modules.pcimap. I have checked the kernel configuration to make sure that loadable module support is enabled, as well as hotplugging support - they are.

This is Kubuntu 14.04 with self-compiled 3.16.0-rc5 kernel. What am I missing? I have gone through the kernel configuration and checked the most obvious options. I'm kind of stuck here. Any ideas?

2

2 Answers

4
votes

You might be missing two things:

1.) An USB keyboard is typically not just a generic USB device, but a HID class device. Linux treats USB HID devices as a separate subclass. Have you taken this into account?

2.) modules.usbmap and modules.pcimap exist with some older versions of module/pci/usb utilities only. With modern versions, the information equivalent to what used to be in those files is included in modules.alias instead. Your research materials may have been obsolete.

0
votes

Here are my suggestions..

  1. Try registering by using vendor_id, product_id and check whether you are registering the for the correct hardware device.

You can try writing a rule in

/etc/udev/rules.d/10-local.rules

make sure it is identifying your hardware correctly. Following commands may help you:

udevadm monitor or udevadm monitor --env
udevadm info -a -p [/devices/pci0000:00/0000:00:1a.0/usb1/1-1 -> this has to be get from above command]
  1. Make sure you rmmod your module, clean all logs [sudo dmesg -c] and plug in the hardware.