Oct 17, 2014

Getting Scanbuttond to work with Canon Lide 110 and 210 under Ubuntu

I recently purchased the Lide 110 and tried to get the scanner buttons working on my ubuntu home server using a tool called scanbuttond. But after a day of trying to compile everything, I figured two things:
1. The genesys backend that is available from older versions of scanbuttond works only with lower versions of the Canon Lide series, including Lide 100 and 200.

2. The USB protocol and handshake have changed in the Lide 110 and Lide 210. So even if you manage to get it all compiled, the old genesys backend no longer works.

So I started to dig into the various information on the internet and have finally figured  a way to get this working. I thought it would be useful to share with people who need to get this combination working. 

1.       First of all, download the latest version of scanbuttond from the official website.  Extract the file above to a directory where you can compile.
wget http://downloads.sourceforge.net/project/scanbuttond/scanbuttond/0.2.3/scanbuttond-0.2.3.tar.gz
tar -zxzf scanbuttond-0.2.3.tar.gz
cd scanbuttond-0.2.3
2.       You now need to get the old version of scanbuttond, patch and copy the files genesys.c and genesys.h from the old package to the "backends" directory from point 1.

If you are not comfortable doing this manually, just copy these two pre-patched files into the “backends" directory where you extracted the current scanbutton. Skip 3 and 4 if you do this.
cd backends
wget https://dl.dropboxusercontent.com/u/6329778/genesys/genesys.
wget  https://dl.dropboxusercontent.com/u/6329778/genesys/genesys.h

3.   This is the new code that is changed in genesys.c to support Lide 110 and Lide 210.

    static int supported_usb_devices[NUM_SUPPORTED_USB_DEVICES][3] = {
        // vendor, product, num_buttons
        { 0x04a9, 0x1909, 15 }, // CanoScan LiDE 110 (only 4 real buttons)
        { 0x04a9, 0x190a, 15 }  // CanoScan LiDE 210 (only 4 real buttons)
    };
    
    static char* usb_device_descriptions[NUM_SUPPORTED_USB_DEVICES][2] = {
        { "Canon", "CanoScan LiDE 110" },
        { "Canon", "CanoScan LiDE 210" }
    };
The reason to remove support for other canon scanners is because the usb handshake is fundamentally different for these two scanners and there is no sense in keeping support for old scanners that do not work with this code.

4.    And the logic for the USB handshake that has now changed.

    int scanbtnd_get_button(scanner_t* scanner)
    {
       unsigned char bytes[2];
       int num_bytes;
       int button = 0;
      
       if (!scanner->is_open)
          return -EINVAL;

       num_bytes = libusb_control_msg((libusb_device_t*)scanner->internal_dev_ptr,
                               0xc0, 0x0c, 0x008e, 0x3122, (void *)bytes, 0x0002);
      
       if (num_bytes != 2) {
          syslog(LOG_WARNING, "genesys-backend: communication error: read length:%d, num_bytes);
          return 0;
       }
      
       return (bytes[0] ^ 0x1f) & 0x1f;
    }

5.       This is the slightly tricky part as it depends on your machine, getting scanbuttond to compile with the new changes. You have to change the makefiles to use genesys as a extra backend :

cd scanbuttond-0.2.3\backends
rm -f Makefile.am Makefile.in meta.conf
wget https://dl.dropboxusercontent.com/u/6329778/genesys/Makefile.am
wget https://dl.dropboxusercontent.com/u/6329778/genesys/Makefile.in
wget https://dl.dropboxusercontent.com/u/6329778/genesys/meta.conf

Now compile the source code:
cd scanbuttond-0.2.3
./configure --prefix=/usr --sysconfdir=/etc
make
make install

6.       If all goes well in the compile and install, you are ready to rock and roll !
Run scanbuttond with this command:
scanbuttond --foreground --backend=/usr/lib/libscanbtnd-backend_genesys.so
tail –f /var/log/syslog
Start pressing buttons on the scanner and you should see the results in the console.

For your reference, this is my /etc/scanbuttond/buttonpressed.sh
#!/bin/sh
# This script is started by scanbuttond whenever a scanner button has been pressed.
# Scanbuttond passes the following parameters to us:
# $1 ... the button number
# $2 ... the scanner's SANE device name, which comes in handy if there are two or
#        more scanners. In this case we can pass the device name to SANE programs
#        like scanimage.

SCANFILE="/ScannedFiles/$(date +%Y%m%d-%H%M%S)"

case $1 in
        1)
                #echo "Auto Scan has been pressed on $2"
                scanimage --format tiff --mode Color --depth 8 --resolution 150 -l 0 -t 0 | convert tiff:- $SCANFILE.jpg
                ;;
        2)
                #echo "Copy has been pressed on $2"
                scanimage --format tiff --mode Color --depth 8 --resolution 200 -l 0 -t 0 -x 215mm -y 297mm | convert tiff:- $SCANFILE.jpg
                lpr -o scaling=100 -o media=A4 -T SCANNER -P EPSON_Color $SCANFILE.jpg
                ;;
        4)
                #echo "Email has been pressed on $2. Make a small size jpg and pdf"
                scanimage --format tiff --mode Color --depth 8 --resolution 100 -l 0 -t 0 | convert tiff:- $SCANFILE.jpg
                convert -quality 75 -compress jpeg $SCANFILE.jpg $SCANFILE.pdf
                ;;
        8)
                #echo "PDF has been pressed on $2"
                scanimage --format tiff --mode Color --depth 8 --resolution 200 -l 0 -t 0 -x 215mm -y 297mm > $SCANFILE.tiff
                convert -quality 90 -compress jpeg $SCANFILE.tiff $SCANFILE.pdf
                rm -f $SCANFILE.tiff
                ;;
esac

That is all ! Have scanbuttond start automatically by adding this line in your /etc/rc.local
scanbuttond --pollingdelay 3000000 --backend=/usr/lib/libscanbtnd-backend_genesys.so
Enjoy !

Want your own website ? Take a look at Terabyte Websites. They take care of building, hosting and maintaining your website.