lkml.org 
[lkml]   [1997]   [Jul]   [26]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    Date
    From
    SubjectPS/2 Intellimouse Patch
    This is a patch for drivers/char/psaux.c, 2.1.47.  I'd appreciate any
    input or comments. The patch gives users a couple of options if they
    happen to be stuck with the Microsoft Intellimouse (the mutant mouse
    with the little wheel in place of the third button), of the PS/2
    persuasion. The reason this is kernel code is firstly, that the
    mouse needs to be initialized before the wheel will do anything.
    Prior to initialization it behaves like a standard 2-button PS/2
    mouse. To initialize, set the sampling rate to 200, then 100, then
    80 (weird, huh?). Afterwards, it generates 4 bytes per mouse event
    rather than 3. Clicking the wheel is just like a middle-button click,
    and turning the wheel modifies the 4th byte (0x01 or 0xff, depending
    on the direction it was turned in). #defining INTELLIMOUSE will modify
    psaux_init() to initialize the mouse properly.

    The other modification is to aux_interrupt(). Since gpm, AccelX, etc.
    have no idea how to talk to this guy, #defining INTELLIMOUSE_EMULATE_PS2
    will cause aux_interrupt() to drop every 4th byte read rather than stick
    it into the queue. Turning the wheel does nothing, but at least you can
    use it as a 3-button mouse.

    It might be stated that this monstrosity :) doesn't deserve kernel code,
    but consider the reason I wrote it. I was helping the admin at my school
    set up a new CS lab, all Linux boxes. We were stuck with 40 Gateway
    machines that shipped with these mice, and had to use AccelX for support
    of the graphics boards they came with. Buying 40 new mice wasn't an
    option. I'm sure there are others in similar situations.

    I didn't reverse-engineer it, just wrote the code. It was the guy who
    wrote the PS/2 driver for FreeBSD (Kazutaka Yokota) who figured out how
    to initialize it. Anyway, here it is, any suggestions are most welcome.

    ------------------8<----------------8<-------------8<-------------------
    --- /usr/src/linux-2.1.47/drivers/char/psaux.c Fri Jul 25 04:46:52 1997
    +++ psaux.c Sat Jul 26 00:43:30 1997
    @@ -36,24 +36,6 @@

    /* #define INITIALIZE_DEVICE */

    -/*
    - * The following two #defines are for the PS/2 Intellimouse. The first
    - * one (INTELLIMOUSE) initializes the mouse properly. The second one
    - * (INTELLIMOUSE_EMULATE_PS2) causes the mouse to behave like a standard
    - * 3 button PS/2 mouse; clicking the wheel is just like a middle-button
    - * click on a standard mouse, but turning the wheel does nothing.
    - */
    -
    -/* #define INTELLIMOUSE */
    -/* #define INTELLIMOUSE_EMULATE_PS2 */
    -
    -#ifdef INTELLIMOUSE_EMULATE_PS2
    -#define INTELLIMOUSE
    -#endif
    -#ifdef INTELLIMOUSE
    -#define INITIALIZE_DEVICE
    -#endif
    -
    #include <linux/module.h>

    #include <linux/sched.h>
    @@ -231,30 +213,13 @@

    static void aux_interrupt(int cpl, void *dev_id, struct pt_regs * regs)
    {
    -#ifdef INTELLIMOUSE_EMULATE_PS2
    - static unsigned int called = 0;
    - unsigned char byte;
    -#endif /* INTELLIMOUSE_EMULATE_PS2 */
    int head = queue->head;
    int maxhead = (queue->tail-1) & (AUX_BUF_SIZE-1);

    if ((inb(KBD_STATUS_REG) & AUX_STAT_OBF) != AUX_STAT_OBF)
    return;

    -#ifdef INTELLIMOUSE_EMULATE_PS2
    - /* Discard every 4th byte for proper emulation. */
    - byte = inb(KBD_DATA_REG);
    - called++;
    -
    - if(!(called % 4)) {
    - called = 0;
    - return;
    - }
    -
    - add_mouse_randomness(queue->buf[head] = byte);
    -#else /* INTELLIMOUSE_EMULATE_PS2 */
    add_mouse_randomness(queue->buf[head] = inb(KBD_DATA_REG));
    -#endif /* INTELLIMOUSE_EMULATE_PS2 */
    if (head != maxhead) {
    head++;
    head &= AUX_BUF_SIZE-1;
    @@ -660,14 +625,6 @@
    aux_write_ack(AUX_SET_RES);
    aux_write_ack(3); /* 8 counts per mm */
    aux_write_ack(AUX_SET_SCALE21); /* 2:1 scaling */
    -#ifdef INTELLIMOUSE
    - aux_write_ack(AUX_SET_SAMPLE);
    - aux_write_ack(200);
    - aux_write_ack(AUX_SET_SAMPLE);
    - aux_write_ack(100);
    - aux_write_ack(AUX_SET_SAMPLE);
    - aux_write_ack(80);
    -#endif /* INTELLIMOUSE */
    poll_aux_status_nosleep();
    #endif /* INITIALIZE_DEVICE */
    outb_p(KBD_CCMD_MOUSE_DISABLE, KBD_CNTL_REG); /* Disable Aux device */
    ------------------8<----------------8<-------------8<-------------------
    Michael Funk
    <mwfunk@uncc.campus.mci.net>
    <mwfunk@uncc.edu>






    \
     
     \ /
      Last update: 2005-03-22 13:40    [W:4.124 / U:0.024 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site