Sunday, June 14, 2020

Rebuilding the USB serial driver to allow for DMX (250000) baud

Rebuilding the USB serial driver to allow for DMX (250000) baud

I wanted to play with a new light and wanted to just use a standard USB serial device. In the past I'd just patched the driver, but that no longer appears possible. (This is a good thing, I was always surprised that used to be able to do this) This meant building the driver. This *should* be simple, but it wasn't. This outlines how to to rebuild the serial driver for Raspbian.

The sequence for building the driver should be simple:
1. Get the source for the driver
2. Get the kernel headers
3. Create a simple Makefile
4. Build
5. Serve

I mainly ran into issues getting the correct headers.

Get the source for the driver

uname -r will tell you the version of the kernel:
  $ uname -r
  4.9.35-v7+

Now you can pull in the source directly from github, updating the version number. Pull in the c file and the header:

  wget https://raw.githubusercontent.com/raspberrypi/linux/rpi-4.9.y/drivers/usb/serial/pl2303.c
  wget https://raw.githubusercontent.com/raspberrypi/linux/rpi-4.9.y/drivers/usb/serial/pl2303.h


Get the kernel headers (Raspbian)

apt install is used to pull in the kernel headers. 

  apt install raspberrypi-kernel-headers

For my installation, the headers getting pulled in didn't match the running kernel. The kernel version was actually quite far ahead. You should ensure that you're up-to-date first

  apt-get update
  apt-get upgrade
  init 6

or in my case:

  apt remove raspberrypi-kernel-headers
  apt-get update
  apt-get install --reinstall raspberrypi-bootloader raspberrypi-kernel
  init 6
Once rebooted:
  apt install raspberrypi-kernel-headers

Check that you have the correct headers. If you have the 'build' directory, then you should be good.

  ls -l /lib/modules/$(uname -r)/build

Create the Makefile

 I'm building pl2303.ko, so all my Makefile needs to contain is:

   obj-m   := pl2303.o

Yes - that's all.

Build

With the headers in place and the Makefile in place, this is all you should have to do to build:

  make -C /lib/modules/$(uname -r)/build M=$PWD modules

Serve

You may need to remove the current module:

  rmmod pl2303

Now you can install your new module:

 insmod pl2303.ko

250000 Baud


The reason for having to build a driver were to be able to set the Baud to 250000 for my DMX device. Linux still has preconceived notions about baud rate, and 250000 isn't one of them, so you'll not be able to easily set the speed you want. I have some existing code (dmx) that sets the baud rate to 500000 with the expectation that the driver will set it to the next closest speed. I used to patch the driver to make this closest (lower) speed to be 250000, but that doesn't work anymore.

       if (baud == 500000) baud=250000;

I added the above line into the driver code - if the baud requested is 500000, then set the baud to 250000. To put this in context:

        /*
         * Use direct method for supported baud rates, otherwise use divisors.
         */
        if (baud == 500000) baud=250000;
        baud_sup = pl2303_get_supported_baud_rate(baud);

        if (baud == baud_sup)
                baud = pl2303_encode_baud_rate_direct(buf, baud);
        else
                baud = pl2303_encode_baud_rate_divisor(buf, baud);

This means that if 500k baud is selected it will change the request to 250k. The 'if ' section (baud_sup) will fail and the baud rate will be set using pl2303_encode_baud_rate_divisor.

That's all.

REF: https://raspberrypi.stackexchange.com/questions/63879/installed-kernel-headers-and-uname-r-differ REF: https://www.youtube.com/watch?v=Zn8mEZXr6nE&list=PL2GL6HVUQAuksbptmKC7X4zruZlIl59is REF: https://www.raspberrypi.org/documentation/raspbian/updating.md







No comments:

Post a Comment