]> www.pilppa.org Git - linux-2.6-omap-h63xx.git/commitdiff
Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/djbw/xscaleiop
authorRussell King <rmk@dyn-67.arm.linux.org.uk>
Tue, 28 Oct 2008 09:55:45 +0000 (09:55 +0000)
committerRussell King <rmk+kernel@arm.linux.org.uk>
Tue, 28 Oct 2008 09:55:45 +0000 (09:55 +0000)
61 files changed:
Documentation/DocBook/deviceiobook.tmpl
Documentation/DocBook/kernel-api.tmpl
Documentation/DocBook/kernel-hacking.tmpl
Documentation/DocBook/mcabook.tmpl
Documentation/hwmon/lm90
Documentation/input/elantech.txt [new file with mode: 0644]
Makefile
drivers/Makefile
drivers/acpi/button.c
drivers/acpi/processor_perflib.c
drivers/acpi/sleep/main.c
drivers/acpi/toshiba_acpi.c
drivers/char/amiserial.c
drivers/dma/ioat_dma.c
drivers/hid/Kconfig
drivers/hid/hid-apple.c
drivers/hid/hid-core.c
drivers/hid/hid-gyration.c
drivers/hid/hid-ids.h
drivers/hid/hid-lg.c
drivers/hid/hid-sony.c
drivers/hid/hidraw.c
drivers/hid/usbhid/hid-core.c
drivers/hid/usbhid/hiddev.c
drivers/hwmon/abituguru3.c
drivers/hwmon/adt7473.c
drivers/hwmon/hwmon-vid.c
drivers/hwmon/lm90.c
drivers/hwmon/w83781d.c
drivers/ide/icside.c
drivers/ide/rapide.c
drivers/idle/Kconfig
drivers/idle/i7300_idle.c
drivers/input/mouse/Kconfig
drivers/input/mouse/Makefile
drivers/input/mouse/elantech.c [new file with mode: 0644]
drivers/input/mouse/elantech.h [new file with mode: 0644]
drivers/input/mouse/psmouse-base.c
drivers/input/mouse/psmouse.h
drivers/input/serio/i8042-x86ia64io.h
drivers/leds/leds-hp-disk.c
drivers/md/md.c
drivers/mfd/Kconfig
drivers/mfd/Makefile
drivers/mmc/host/mmci.c
drivers/net/r8169.c
drivers/pci/pci-acpi.c
fs/compat.c
fs/eventpoll.c
fs/ext3/dir.c
fs/ext4/dir.c
fs/select.c
include/linux/hid.h
include/linux/i7300_idle.h [new file with mode: 0644]
include/linux/raid/md_k.h
init/main.c
kernel/cgroup.c
kernel/stop_machine.c
net/wireless/Kconfig
scripts/kconfig/confdata.c
scripts/kernel-doc

index 9ee6f3cbb4148b8363208328912c119dc7ee71b5..60d6e0b81bd97e8cb528d6edbeb7af839eeb8563 100644 (file)
@@ -316,7 +316,7 @@ CPU B:  spin_unlock_irqrestore(&amp;dev_lock, flags)
 
   <chapter id="pubfunctions">
      <title>Public Functions Provided</title>
-!Iinclude/asm-x86/io_32.h
+!Iarch/x86/include/asm/io_32.h
 !Elib/iomap.c
   </chapter>
 
index 9d0058e788e53430f1b33bf8ff40d3ff4f6f67b1..5818ff75786abf9a853706794f1f33f6238786cb 100644 (file)
@@ -45,8 +45,8 @@
      </sect1>
 
      <sect1><title>Atomic and pointer manipulation</title>
-!Iinclude/asm-x86/atomic_32.h
-!Iinclude/asm-x86/unaligned.h
+!Iarch/x86/include/asm/atomic_32.h
+!Iarch/x86/include/asm/unaligned.h
      </sect1>
 
      <sect1><title>Delaying, scheduling, and timer routines</title>
@@ -119,7 +119,7 @@ X!Ilib/string.c
 !Elib/string.c
      </sect1>
      <sect1><title>Bit Operations</title>
-!Iinclude/asm-x86/bitops.h
+!Iarch/x86/include/asm/bitops.h
      </sect1>
   </chapter>
 
@@ -155,7 +155,7 @@ X!Ilib/string.c
 !Emm/slab.c
      </sect1>
      <sect1><title>User Space Memory Access</title>
-!Iinclude/asm-x86/uaccess_32.h
+!Iarch/x86/include/asm/uaccess_32.h
 !Earch/x86/lib/usercopy_32.c
      </sect1>
      <sect1><title>More Memory Management Functions</title>
@@ -265,7 +265,7 @@ X!Earch/x86/kernel/mca_32.c
 -->
        </sect2>
        <sect2><title>MCA Bus DMA</title>
-!Iinclude/asm-x86/mca_dma.h
+!Iarch/x86/include/asm/mca_dma.h
        </sect2>
      </sect1>
   </chapter>
index ae15d55350ec8bf93e2eb79dac2ee730cd6de054..a50d6cd58573b63be92acbc7f5ea06d0b884844f 100644 (file)
@@ -1239,7 +1239,7 @@ static struct block_device_operations opt_fops = {
   </para>
 
   <para>
-   <filename>include/asm-x86/delay_32.h:</filename>
+   <filename>arch/x86/include/asm/delay.h:</filename>
   </para>
   <programlisting>
 #define ndelay(n) (__builtin_constant_p(n) ? \
@@ -1265,7 +1265,7 @@ static struct block_device_operations opt_fops = {
 </programlisting>
 
   <para>
-   <filename>include/asm-x86/uaccess_32.h:</filename>
+   <filename>arch/x86/include/asm/uaccess_32.h:</filename>
   </para>
 
   <programlisting>
index 529a53dc13899e1f780516c2ee80f90f1df58cd6..499eddc2d0792396d6598fbdd7ad08d3c86aaa77 100644 (file)
 
   <chapter id="dmafunctions">
      <title>DMA Functions Provided</title>
-!Iinclude/asm-x86/mca_dma.h
+!Iarch/x86/include/asm/mca_dma.h
   </chapter>
 
 </book>
index e0d5206d1de347d5d4aeb332f0511443e13beae5..0e8411710238ff3c0a58c1f373031f3f7447ce5c 100644 (file)
@@ -8,7 +8,7 @@ Supported chips:
     Datasheet: Publicly available at the National Semiconductor website
                http://www.national.com/pf/LM/LM90.html
   * National Semiconductor LM89
-    Prefix: 'lm99'
+    Prefix: 'lm89' (no auto-detection)
     Addresses scanned: I2C 0x4c and 0x4d
     Datasheet: Publicly available at the National Semiconductor website
                http://www.national.com/mpf/LM/LM89.html
diff --git a/Documentation/input/elantech.txt b/Documentation/input/elantech.txt
new file mode 100644 (file)
index 0000000..a10c3b6
--- /dev/null
@@ -0,0 +1,405 @@
+Elantech Touchpad Driver
+========================
+
+       Copyright (C) 2007-2008 Arjan Opmeer <arjan@opmeer.net>
+
+       Extra information for hardware version 1 found and
+       provided by Steve Havelka
+
+       Version 2 (EeePC) hardware support based on patches
+       received from Woody at Xandros and forwarded to me
+       by user StewieGriffin at the eeeuser.com forum
+
+
+Contents
+~~~~~~~~
+
+ 1. Introduction
+ 2. Extra knobs
+ 3. Hardware version 1
+    3.1 Registers
+    3.2 Native relative mode 4 byte packet format
+    3.3 Native absolute mode 4 byte packet format
+ 4. Hardware version 2
+    4.1 Registers
+    4.2 Native absolute mode 6 byte packet format
+        4.2.1 One finger touch
+        4.2.2 Two finger touch
+
+
+
+1. Introduction
+   ~~~~~~~~~~~~
+
+Currently the Linux Elantech touchpad driver is aware of two different
+hardware versions unimaginatively called version 1 and version 2. Version 1
+is found in "older" laptops and uses 4 bytes per packet. Version 2 seems to
+be introduced with the EeePC and uses 6 bytes per packet.
+
+The driver tries to support both hardware versions and should be compatible
+with the Xorg Synaptics touchpad driver and its graphical configuration
+utilities.
+
+Additionally the operation of the touchpad can be altered by adjusting the
+contents of some of its internal registers. These registers are represented
+by the driver as sysfs entries under /sys/bus/serio/drivers/psmouse/serio?
+that can be read from and written to.
+
+Currently only the registers for hardware version 1 are somewhat understood.
+Hardware version 2 seems to use some of the same registers but it is not
+known whether the bits in the registers represent the same thing or might
+have changed their meaning.
+
+On top of that, some register settings have effect only when the touchpad is
+in relative mode and not in absolute mode. As the Linux Elantech touchpad
+driver always puts the hardware into absolute mode not all information
+mentioned below can be used immediately. But because there is no freely
+available Elantech documentation the information is provided here anyway for
+completeness sake.
+
+
+/////////////////////////////////////////////////////////////////////////////
+
+
+2. Extra knobs
+   ~~~~~~~~~~~
+
+Currently the Linux Elantech touchpad driver provides two extra knobs under
+/sys/bus/serio/drivers/psmouse/serio? for the user.
+
+* debug
+
+   Turn different levels of debugging ON or OFF.
+
+   By echoing "0" to this file all debugging will be turned OFF.
+
+   Currently a value of "1" will turn on some basic debugging and a value of
+   "2" will turn on packet debugging. For hardware version 1 the default is
+   OFF. For version 2 the default is "1".
+
+   Turning packet debugging on will make the driver dump every packet
+   received to the syslog before processing it. Be warned that this can
+   generate quite a lot of data!
+
+* paritycheck
+
+   Turns parity checking ON or OFF.
+
+   By echoing "0" to this file parity checking will be turned OFF. Any
+   non-zero value will turn it ON. For hardware version 1 the default is ON.
+   For version 2 the default it is OFF.
+
+   Hardware version 1 provides basic data integrity verification by
+   calculating a parity bit for the last 3 bytes of each packet. The driver
+   can check these bits and reject any packet that appears corrupted. Using
+   this knob you can bypass that check.
+
+   It is not known yet whether hardware version 2 provides the same parity
+   bits. Hence checking is disabled by default. Currently even turning it on
+   will do nothing.
+
+
+/////////////////////////////////////////////////////////////////////////////
+
+
+3. Hardware version 1
+   ==================
+
+3.1 Registers
+    ~~~~~~~~~
+
+By echoing a hexadecimal value to a register it contents can be altered.
+
+For example:
+
+   echo -n 0x16 > reg_10
+
+* reg_10
+
+   bit   7   6   5   4   3   2   1   0
+         B   C   T   D   L   A   S   E
+
+         E: 1 = enable smart edges unconditionally
+         S: 1 = enable smart edges only when dragging
+         A: 1 = absolute mode (needs 4 byte packets, see reg_11)
+         L: 1 = enable drag lock (see reg_22)
+         D: 1 = disable dynamic resolution
+         T: 1 = disable tapping
+         C: 1 = enable corner tap
+         B: 1 = swap left and right button
+
+* reg_11
+
+   bit   7   6   5   4   3   2   1   0
+         1   0   0   H   V   1   F   P
+
+         P: 1 = enable parity checking for relative mode
+         F: 1 = enable native 4 byte packet mode
+         V: 1 = enable vertical scroll area
+         H: 1 = enable horizontal scroll area
+
+* reg_20
+
+         single finger width?
+
+* reg_21
+
+         scroll area width (small: 0x40 ... wide: 0xff)
+
+* reg_22
+
+         drag lock time out (short: 0x14 ... long: 0xfe;
+                             0xff = tap again to release)
+
+* reg_23
+
+         tap make timeout?
+
+* reg_24
+
+         tap release timeout?
+
+* reg_25
+
+         smart edge cursor speed (0x02 = slow, 0x03 = medium, 0x04 = fast)
+
+* reg_26
+
+         smart edge activation area width?
+
+
+3.2 Native relative mode 4 byte packet format
+    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+byte 0:
+   bit   7   6   5   4   3   2   1   0
+         c   c  p2  p1   1   M   R   L
+
+         L, R, M = 1 when Left, Right, Middle mouse button pressed
+            some models have M as byte 3 odd parity bit
+         when parity checking is enabled (reg_11, P = 1):
+            p1..p2 = byte 1 and 2 odd parity bit
+         c = 1 when corner tap detected
+
+byte 1:
+   bit   7   6   5   4   3   2   1   0
+        dx7 dx6 dx5 dx4 dx3 dx2 dx1 dx0
+
+         dx7..dx0 = x movement;   positive = right, negative = left
+         byte 1 = 0xf0 when corner tap detected
+
+byte 2:
+   bit   7   6   5   4   3   2   1   0
+        dy7 dy6 dy5 dy4 dy3 dy2 dy1 dy0
+
+         dy7..dy0 = y movement;   positive = up,    negative = down
+
+byte 3:
+   parity checking enabled (reg_11, P = 1):
+
+      bit   7   6   5   4   3   2   1   0
+            w   h  n1  n0  ds3 ds2 ds1 ds0
+
+            normally:
+               ds3..ds0 = scroll wheel amount and direction
+                          positive = down or left
+                          negative = up or right
+            when corner tap detected:
+               ds0 = 1 when top right corner tapped
+               ds1 = 1 when bottom right corner tapped
+               ds2 = 1 when bottom left corner tapped
+               ds3 = 1 when top left corner tapped
+            n1..n0 = number of fingers on touchpad
+               only models with firmware 2.x report this, models with
+               firmware 1.x seem to map one, two and three finger taps
+               directly to L, M and R mouse buttons
+            h = 1 when horizontal scroll action
+            w = 1 when wide finger touch?
+
+   otherwise (reg_11, P = 0):
+
+      bit   7   6   5   4   3   2   1   0
+           ds7 ds6 ds5 ds4 ds3 ds2 ds1 ds0
+
+            ds7..ds0 = vertical scroll amount and direction
+                       negative = up
+                       positive = down
+
+
+3.3 Native absolute mode 4 byte packet format
+    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+byte 0:
+   firmware version 1.x:
+
+      bit   7   6   5   4   3   2   1   0
+            D   U  p1  p2   1  p3   R   L
+
+            L, R = 1 when Left, Right mouse button pressed
+            p1..p3 = byte 1..3 odd parity bit
+            D, U = 1 when rocker switch pressed Up, Down
+
+   firmware version 2.x:
+
+      bit   7   6   5   4   3   2   1   0
+           n1  n0  p2  p1   1  p3   R   L
+
+            L, R = 1 when Left, Right mouse button pressed
+            p1..p3 = byte 1..3 odd parity bit
+            n1..n0 = number of fingers on touchpad
+
+byte 1:
+   firmware version 1.x:
+
+      bit   7   6   5   4   3   2   1   0
+            f   0  th  tw  x9  x8  y9  y8
+
+            tw = 1 when two finger touch
+            th = 1 when three finger touch
+            f  = 1 when finger touch
+
+   firmware version 2.x:
+
+      bit   7   6   5   4   3   2   1   0
+            .   .   .   .  x9  x8  y9  y8
+
+byte 2:
+   bit   7   6   5   4   3   2   1   0
+        x7  x6  x5  x4  x3  x2  x1  x0
+
+         x9..x0 = absolute x value (horizontal)
+
+byte 3:
+   bit   7   6   5   4   3   2   1   0
+        y7  y6  y5  y4  y3  y2  y1  y0
+
+         y9..y0 = absolute y value (vertical)
+
+
+/////////////////////////////////////////////////////////////////////////////
+
+
+4. Hardware version 2
+   ==================
+
+
+4.1 Registers
+    ~~~~~~~~~
+
+By echoing a hexadecimal value to a register it contents can be altered.
+
+For example:
+
+   echo -n 0x56 > reg_10
+
+* reg_10
+
+   bit   7   6   5   4   3   2   1   0
+         0   1   0   1   0   1   D   0
+
+         D: 1 = enable drag and drop
+
+* reg_11
+
+   bit   7   6   5   4   3   2   1   0
+         1   0   0   0   S   0   1   0
+
+         S: 1 = enable vertical scroll
+
+* reg_21
+
+         unknown (0x00)
+
+* reg_22
+
+         drag and drop release time out (short: 0x70 ... long 0x7e;
+                                   0x7f = never i.e. tap again to release)
+
+
+4.2 Native absolute mode 6 byte packet format
+    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+4.2.1 One finger touch
+      ~~~~~~~~~~~~~~~~
+
+byte 0:
+
+   bit   7   6   5   4   3   2   1   0
+        n1  n0   .   .   .   .   R   L
+
+         L, R = 1 when Left, Right mouse button pressed
+         n1..n0 = numbers of fingers on touchpad
+
+byte 1:
+
+   bit   7   6   5   4   3   2   1   0
+        x15 x14 x13 x12 x11 x10 x9  x8
+
+byte 2:
+
+   bit   7   6   5   4   3   2   1   0
+        x7  x6  x5  x4  x4  x2  x1  x0
+
+         x15..x0 = absolute x value (horizontal)
+
+byte 3:
+
+   bit   7   6   5   4   3   2   1   0
+         .   .   .   .   .   .   .   .
+
+byte 4:
+
+   bit   7   6   5   4   3   2   1   0
+        y15 y14 y13 y12 y11 y10 y8  y8
+
+byte 5:
+
+   bit   7   6   5   4   3   2   1   0
+        y7  y6  y5  y4  y3  y2  y1  y0
+
+         y15..y0 = absolute y value (vertical)
+
+
+4.2.2 Two finger touch
+      ~~~~~~~~~~~~~~~~
+
+byte 0:
+
+   bit   7   6   5   4   3   2   1   0
+        n1  n0  ay8 ax8  .   .   R   L
+
+         L, R = 1 when Left, Right mouse button pressed
+         n1..n0 = numbers of fingers on touchpad
+
+byte 1:
+
+   bit   7   6   5   4   3   2   1   0
+        ax7 ax6 ax5 ax4 ax3 ax2 ax1 ax0
+
+         ax8..ax0 = first finger absolute x value
+
+byte 2:
+
+   bit   7   6   5   4   3   2   1   0
+        ay7 ay6 ay5 ay4 ay3 ay2 ay1 ay0
+
+         ay8..ay0 = first finger absolute y value
+
+byte 3:
+
+   bit   7   6   5   4   3   2   1   0
+         .   .  by8 bx8  .   .   .   .
+
+byte 4:
+
+   bit   7   6   5   4   3   2   1   0
+        bx7 bx6 bx5 bx4 bx3 bx2 bx1 bx0
+
+         bx8..bx0 = second finger absolute x value
+
+byte 5:
+
+   bit   7   6   5   4   3   2   1   0
+        by7 by8 by5 by4 by3 by2 by1 by0
+
+         by8..by0 = second finger absolute y value
index 8e540515cb9714cf32d4c8401e9fd9fd182123eb..e9c5d47f31cdb42f8b98fc28065446a85fe7d2f6 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -1,7 +1,7 @@
 VERSION = 2
 PATCHLEVEL = 6
 SUBLEVEL = 28
-EXTRAVERSION = -rc1
+EXTRAVERSION = -rc2
 NAME = Killer Bat of Doom
 
 # *DOCUMENTATION*
index 2503f7b99b2fdc70edf3648d365c7a2c35e85eaa..fceb71a741c3ca5a71131a487ea24a8cd63fb243 100644 (file)
@@ -56,6 +56,7 @@ obj-$(CONFIG_MAC)             += macintosh/
 obj-$(CONFIG_ATA_OVER_ETH)     += block/aoe/
 obj-$(CONFIG_PARIDE)           += block/paride/
 obj-$(CONFIG_TC)               += tc/
+obj-$(CONFIG_UWB)              += uwb/
 obj-$(CONFIG_USB)              += usb/
 obj-$(CONFIG_USB_MUSB_HDRC)    += usb/musb/
 obj-$(CONFIG_PCI)              += usb/
@@ -101,4 +102,3 @@ obj-$(CONFIG_SSB)           += ssb/
 obj-$(CONFIG_VIRTIO)           += virtio/
 obj-$(CONFIG_REGULATOR)                += regulator/
 obj-$(CONFIG_STAGING)          += staging/
-obj-$(CONFIG_UWB)              += uwb/
index 9d568d417eaa48e2e76624a0a2e505499c3aedcb..cb046c3fc3f2bd15da05dfd3939cda28d4949599 100644 (file)
@@ -262,6 +262,7 @@ static int acpi_lid_send_state(struct acpi_button *button)
                return -ENODEV;
        /* input layer checks if event is redundant */
        input_report_switch(button->input, SW_LID, !state);
+       input_sync(button->input);
        return 0;
 }
 
@@ -285,8 +286,8 @@ static void acpi_button_notify(acpi_handle handle, u32 event, void *data)
                        input_report_key(input, keycode, 1);
                        input_sync(input);
                        input_report_key(input, keycode, 0);
+                       input_sync(input);
                }
-               input_sync(input);
 
                acpi_bus_generate_proc_event(button->device, event,
                                        ++button->pushed);
index dc98f7a6f2c49bfb701716f330fc70dff13012a5..dbcf260ea93fce4d65b59dcd90c85d70f868c1b5 100644 (file)
 
 #include <asm/uaccess.h>
 #endif
+
+#ifdef CONFIG_X86
 #include <asm/cpufeature.h>
+#endif
 
 #include <acpi/acpi_bus.h>
 #include <acpi/processor.h>
@@ -360,11 +363,13 @@ static int acpi_processor_get_performance_info(struct acpi_processor *pr)
         * the BIOS is older than the CPU and does not know its frequencies
         */
  update_bios:
+#ifdef CONFIG_X86
        if (ACPI_SUCCESS(acpi_get_handle(pr->handle, "_PPC", &handle))){
                if(boot_cpu_has(X86_FEATURE_EST))
                        printk(KERN_WARNING FW_BUG "BIOS needs update for CPU "
                               "frequency support\n");
        }
+#endif
        return result;
 }
 
index 26571bafb158a66380308ff04381f0744aa98325..80c0868d0480e76a0eced99a00a163f98114353c 100644 (file)
@@ -163,6 +163,8 @@ static void acpi_pm_end(void)
        acpi_target_sleep_state = ACPI_STATE_S0;
        acpi_sleep_tts_switch(acpi_target_sleep_state);
 }
+#else /* !CONFIG_ACPI_SLEEP */
+#define acpi_target_sleep_state        ACPI_STATE_S0
 #endif /* CONFIG_ACPI_SLEEP */
 
 #ifdef CONFIG_SUSPEND
index 2a632f8b7a053911723a9259155a464ccb745aa8..66aac06f2ac5abd47ec7e5ecf7267f2b3c6e30aa 100644 (file)
@@ -371,6 +371,7 @@ static void bt_poll_rfkill(struct input_polled_dev *poll_dev)
                                   RFKILL_STATE_HARD_BLOCKED);
                input_report_switch(poll_dev->input, SW_RFKILL_ALL,
                                    new_rfk_state);
+               input_sync(poll_dev->input);
        }
 }
 
@@ -842,6 +843,7 @@ static int __init toshiba_acpi_init(void)
        set_bit(EV_SW, toshiba_acpi.poll_dev->input->evbit);
        set_bit(SW_RFKILL_ALL, toshiba_acpi.poll_dev->input->swbit);
        input_report_switch(toshiba_acpi.poll_dev->input, SW_RFKILL_ALL, TRUE);
+       input_sync(toshiba_acpi.poll_dev->input);
 
        ret = input_register_polled_device(toshiba_acpi.poll_dev);
        if (ret) {
index 98821f97583c680b9ddc222d8c15e9909c0feb6b..b97aebd7aeb8d84af42f72291b06ecb3dcb6dff8 100644 (file)
@@ -2071,12 +2071,13 @@ module_init(rs_init)
 module_exit(rs_exit)
 
 
+#if defined(CONFIG_SERIAL_CONSOLE) && !defined(MODULE)
+
 /*
  * ------------------------------------------------------------
  * Serial console driver
  * ------------------------------------------------------------
  */
-#ifdef CONFIG_SERIAL_CONSOLE
 
 static void amiga_serial_putc(char c)
 {
@@ -2130,6 +2131,7 @@ static int __init amiserial_console_init(void)
        return 0;
 }
 console_initcall(amiserial_console_init);
-#endif
+
+#endif /* CONFIG_SERIAL_CONSOLE && !MODULE */
 
 MODULE_LICENSE("GPL");
index 43b8cefad2c6ddfb57276e53a6ce19710677ea5a..b0438c4f0c305128b9ab5111de2311d193c259b5 100644 (file)
@@ -33,6 +33,7 @@
 #include <linux/delay.h>
 #include <linux/dma-mapping.h>
 #include <linux/workqueue.h>
+#include <linux/i7300_idle.h>
 #include "ioatdma.h"
 #include "ioatdma_registers.h"
 #include "ioatdma_hw.h"
@@ -171,8 +172,10 @@ static int ioat_dma_enumerate_channels(struct ioatdma_device *device)
        xfercap_scale = readb(device->reg_base + IOAT_XFERCAP_OFFSET);
        xfercap = (xfercap_scale == 0 ? -1 : (1UL << xfercap_scale));
 
-#if CONFIG_I7300_IDLE_IOAT_CHANNEL
-       device->common.chancnt--;
+#ifdef  CONFIG_I7300_IDLE_IOAT_CHANNEL
+       if (i7300_idle_platform_probe(NULL, NULL) == 0) {
+               device->common.chancnt--;
+       }
 #endif
        for (i = 0; i < device->common.chancnt; i++) {
                ioat_chan = kzalloc(sizeof(*ioat_chan), GFP_KERNEL);
index f5999a91614e668aade684ccbb89fcaf5e1eba86..b4fd8ca701a44d4ff32d3f2bedb6b3c8b706f72d 100644 (file)
@@ -247,7 +247,6 @@ config HID_SUNPLUS
 
 config THRUSTMASTER_FF
        tristate "ThrustMaster devices support"
-       default m
        depends on USB_HID
        select INPUT_FF_MEMLESS
        help
@@ -256,7 +255,6 @@ config THRUSTMASTER_FF
 
 config ZEROPLUS_FF
        tristate "Zeroplus based game controller support"
-       default m
        depends on USB_HID
        select INPUT_FF_MEMLESS
        help
index fd7f896b34f7982ff0b5499d050e828bed45cb0d..c6ab4ba60c52a296035b6d23cf7b0e9c4f0b4970 100644 (file)
@@ -312,13 +312,6 @@ static int apple_probe(struct hid_device *hdev,
        unsigned int connect_mask = HID_CONNECT_DEFAULT;
        int ret;
 
-       /* return something else or move to hid layer? device will reside
-          allocated */
-       if (id->bus == BUS_USB && (quirks & APPLE_IGNORE_MOUSE) &&
-                       to_usb_interface(hdev->dev.parent)->cur_altsetting->
-                       desc.bInterfaceProtocol == USB_INTERFACE_PROTOCOL_MOUSE)
-               return -ENODEV;
-
        asc = kzalloc(sizeof(*asc), GFP_KERNEL);
        if (asc == NULL) {
                dev_err(&hdev->dev, "can't alloc apple descriptor\n");
@@ -367,38 +360,32 @@ static const struct hid_device_id apple_devices[] = {
                .driver_data = APPLE_MIGHTYMOUSE | APPLE_INVERT_HWHEEL },
 
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_FOUNTAIN_ANSI),
-               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_FOUNTAIN_ISO),
-               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER_ANSI),
-               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER_ISO),
                .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE | APPLE_ISO_KEYBOARD },
+                       APPLE_ISO_KEYBOARD },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER_JIS),
-               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER3_ANSI),
-               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER3_ISO),
                .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE | APPLE_ISO_KEYBOARD },
+                       APPLE_ISO_KEYBOARD },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER3_JIS),
                .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE | APPLE_RDESC_JIS },
+                       APPLE_RDESC_JIS },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_ANSI),
-               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_ISO),
                .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE | APPLE_ISO_KEYBOARD },
+                       APPLE_ISO_KEYBOARD },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_JIS),
                .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE | APPLE_RDESC_JIS},
+                       APPLE_RDESC_JIS },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_ANSI),
                .driver_data = APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_ISO),
@@ -406,14 +393,12 @@ static const struct hid_device_id apple_devices[] = {
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_JIS),
                .driver_data = APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_HF_ANSI),
-               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_HF_ISO),
-               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_HF_JIS),
                .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE | APPLE_RDESC_JIS },
+                       APPLE_RDESC_JIS },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_ANSI),
                .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_ISO),
@@ -422,25 +407,21 @@ static const struct hid_device_id apple_devices[] = {
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_JIS),
                .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING_ANSI),
-               .driver_data = APPLE_HAS_FN | APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING_ISO),
-               .driver_data = APPLE_HAS_FN | APPLE_ISO_KEYBOARD |
-                       APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_HAS_FN | APPLE_ISO_KEYBOARD },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING_JIS),
-               .driver_data = APPLE_HAS_FN | APPLE_IGNORE_MOUSE | APPLE_RDESC_JIS },
+               .driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING2_ANSI),
-               .driver_data = APPLE_HAS_FN | APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING2_ISO),
-               .driver_data = APPLE_HAS_FN | APPLE_ISO_KEYBOARD |
-                       APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_HAS_FN | APPLE_ISO_KEYBOARD },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING2_JIS),
-               .driver_data = APPLE_HAS_FN | APPLE_IGNORE_MOUSE | APPLE_RDESC_JIS },
+               .driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_FOUNTAIN_TP_ONLY),
-               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN },
        { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER1_TP_ONLY),
-               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN |
-                       APPLE_IGNORE_MOUSE },
+               .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN },
 
        /* Apple wireless Mighty Mouse */
        { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, 0x030c),
index 721a36d97582010674e5a4c81faf0be457441d18..743e6f8cb20273c903d2177e9298f5d58d12fb3b 100644 (file)
@@ -1264,6 +1264,7 @@ static const struct hid_device_id hid_blacklist[] = {
        { HID_USB_DEVICE(USB_VENDOR_ID_DELL, USB_DEVICE_ID_DELL_SK8115) },
        { HID_USB_DEVICE(USB_VENDOR_ID_EZKEY, USB_DEVICE_ID_BTC_8193) },
        { HID_USB_DEVICE(USB_VENDOR_ID_GYRATION, USB_DEVICE_ID_GYRATION_REMOTE) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_GYRATION, USB_DEVICE_ID_GYRATION_REMOTE_2) },
        { HID_USB_DEVICE(USB_VENDOR_ID_LABTEC, USB_DEVICE_ID_LABTEC_WIRELESS_KEYBOARD) },
        { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_MX3000_RECEIVER) },
        { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_S510_RECEIVER) },
@@ -1275,8 +1276,6 @@ static const struct hid_device_id hid_blacklist[] = {
        { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_KBD) },
        { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_ELITE_KBD) },
        { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_CORDLESS_DESKTOP_LX500) },
-       { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_LX3) },
-       { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_V150) },
        { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_EXTREME_3D) },
        { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_WHEEL) },
        { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_RUMBLEPAD) },
@@ -1295,6 +1294,7 @@ static const struct hid_device_id hid_blacklist[] = {
        { HID_USB_DEVICE(USB_VENDOR_ID_PETALYNX, USB_DEVICE_ID_PETALYNX_MAXTER_REMOTE) },
        { HID_USB_DEVICE(USB_VENDOR_ID_SAMSUNG, USB_DEVICE_ID_SAMSUNG_IR_REMOTE) },
        { HID_USB_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_PS3_CONTROLLER) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_VAIO_VGX_MOUSE) },
        { HID_USB_DEVICE(USB_VENDOR_ID_SUNPLUS, USB_DEVICE_ID_SUNPLUS_WDESKTOP) },
 
        { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, 0x030c) },
@@ -1406,6 +1406,7 @@ static const struct hid_device_id hid_ignore_list[] = {
        { HID_USB_DEVICE(USB_VENDOR_ID_AIRCABLE, USB_DEVICE_ID_AIRCABLE1) },
        { HID_USB_DEVICE(USB_VENDOR_ID_ALCOR, USB_DEVICE_ID_ALCOR_USBRS232) },
        { HID_USB_DEVICE(USB_VENDOR_ID_ASUS, USB_DEVICE_ID_ASUS_LCM)},
+       { HID_USB_DEVICE(USB_VENDOR_ID_ASUS, USB_DEVICE_ID_ASUS_LCM2)},
        { HID_USB_DEVICE(USB_VENDOR_ID_BERKSHIRE, USB_DEVICE_ID_BERKSHIRE_PCWD) },
        { HID_USB_DEVICE(USB_VENDOR_ID_CIDC, 0x0103) },
        { HID_USB_DEVICE(USB_VENDOR_ID_CYGNAL, USB_DEVICE_ID_CYGNAL_RADIO_SI470X) },
@@ -1541,6 +1542,40 @@ static const struct hid_device_id hid_ignore_list[] = {
        { }
 };
 
+/**
+ * hid_mouse_ignore_list - mouse devices which should not be handled by the hid layer
+ *
+ * There are composite devices for which we want to ignore only a certain
+ * interface. This is a list of devices for which only the mouse interface will
+ * be ignored. This allows a dedicated driver to take care of the interface.
+ */
+static const struct hid_device_id hid_mouse_ignore_list[] = {
+       /* appletouch driver */
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_FOUNTAIN_ANSI) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_FOUNTAIN_ISO) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER_ANSI) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER_ISO) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER_JIS) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER3_ANSI) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER3_ISO) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER3_JIS) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_ANSI) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_ISO) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_JIS) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_HF_ANSI) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_HF_ISO) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_HF_JIS) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING_ANSI) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING_ISO) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING_JIS) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING2_ANSI) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING2_ISO) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING2_JIS) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_FOUNTAIN_TP_ONLY) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER1_TP_ONLY) },
+       { }
+};
+
 static bool hid_ignore(struct hid_device *hdev)
 {
        switch (hdev->vendor) {
@@ -1557,6 +1592,10 @@ static bool hid_ignore(struct hid_device *hdev)
                break;
        }
 
+       if (hdev->type == HID_TYPE_USBMOUSE &&
+                       hid_match_id(hdev, hid_mouse_ignore_list))
+               return true;
+
        return !!hid_match_id(hdev, hid_ignore_list);
 }
 
index ac5120f542ccdfcaa4806716961d48e2192d6ffc..04a0afec52acede3f6dd087ef7cd576f23e9c60a 100644 (file)
@@ -4,9 +4,9 @@
  *  Copyright (c) 1999 Andreas Gal
  *  Copyright (c) 2000-2005 Vojtech Pavlik <vojtech@suse.cz>
  *  Copyright (c) 2005 Michael Haboustak <mike-@cinci.rr.com> for Concept2, Inc
- *  Copyright (c) 2006-2007 Jiri Kosina
  *  Copyright (c) 2007 Paul Walmsley
  *  Copyright (c) 2008 Jiri Slaby
+ *  Copyright (c) 2006-2008 Jiri Kosina
  */
 
 /*
@@ -40,6 +40,7 @@ static int gyration_input_mapping(struct hid_device *hdev, struct hid_input *hi,
        case 0x025: gy_map_key_clear(KEY_PVR);          break;
        case 0x046: gy_map_key_clear(KEY_MEDIA);        break;
        case 0x047: gy_map_key_clear(KEY_MP3);          break;
+       case 0x048: gy_map_key_clear(KEY_MEDIA);        break;
        case 0x049: gy_map_key_clear(KEY_CAMERA);       break;
        case 0x04a: gy_map_key_clear(KEY_VIDEO);        break;
 
@@ -68,6 +69,7 @@ static int gyration_event(struct hid_device *hdev, struct hid_field *field,
 
 static const struct hid_device_id gyration_devices[] = {
        { HID_USB_DEVICE(USB_VENDOR_ID_GYRATION, USB_DEVICE_ID_GYRATION_REMOTE) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_GYRATION, USB_DEVICE_ID_GYRATION_REMOTE_2) },
        { }
 };
 MODULE_DEVICE_TABLE(hid, gyration_devices);
index d9a1ba920c238f5e188353049ea3825985b6adcb..a0d6a6cb1842fd03a51738a379303e35c52aa1e7 100644 (file)
@@ -89,6 +89,7 @@
 
 #define USB_VENDOR_ID_ASUS             0x0b05
 #define USB_DEVICE_ID_ASUS_LCM         0x1726
+#define USB_DEVICE_ID_ASUS_LCM2                0x175b
 
 #define USB_VENDOR_ID_ATEN             0x0557
 #define USB_DEVICE_ID_ATEN_UC100KM     0x2004
 
 #define USB_VENDOR_ID_GYRATION         0x0c16
 #define USB_DEVICE_ID_GYRATION_REMOTE  0x0002
+#define USB_DEVICE_ID_GYRATION_REMOTE_2 0x0003
 
 #define USB_VENDOR_ID_HAPP             0x078b
 #define USB_DEVICE_ID_UGCI_DRIVING     0x0010
 #define USB_DEVICE_ID_LD_MACHINETEST   0x2040
 
 #define USB_VENDOR_ID_LOGITECH         0x046d
-#define USB_DEVICE_ID_LOGITECH_LX3     0xc044
-#define USB_DEVICE_ID_LOGITECH_V150    0xc047
 #define USB_DEVICE_ID_LOGITECH_RECEIVER        0xc101
 #define USB_DEVICE_ID_LOGITECH_HARMONY_FIRST  0xc110
 #define USB_DEVICE_ID_LOGITECH_HARMONY_LAST 0xc14f
 #define USB_DEVICE_ID_SAMSUNG_IR_REMOTE        0x0001
 
 #define USB_VENDOR_ID_SONY                     0x054c
+#define USB_DEVICE_ID_SONY_VAIO_VGX_MOUSE      0x024b
 #define USB_DEVICE_ID_SONY_PS3_CONTROLLER      0x0268
 
 #define USB_VENDOR_ID_SOUNDGRAPH       0x15c2
index 406d8c82abf1476a1cc35a123ec89f501b9a5edb..2bae340eafe2829b3fd97302d36a66b8b100f95f 100644 (file)
@@ -287,11 +287,6 @@ static const struct hid_device_id lg_devices[] = {
        { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_CORDLESS_DESKTOP_LX500),
                .driver_data = LG_IGNORE_DOUBLED_WHEEL | LG_EXPANDED_KEYMAP },
 
-       { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_LX3),
-               .driver_data = LG_INVERT_HWHEEL },
-       { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_V150),
-               .driver_data = LG_INVERT_HWHEEL },
-
        { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_EXTREME_3D),
                .driver_data = LG_NOGET },
        { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_WHEEL),
index 3af8095a7de19639a1018bf3817118d28501081a..86e563b8d6447a81fd924a1e45f9cdb37ebac48f 100644 (file)
@@ -4,9 +4,9 @@
  *  Copyright (c) 1999 Andreas Gal
  *  Copyright (c) 2000-2005 Vojtech Pavlik <vojtech@suse.cz>
  *  Copyright (c) 2005 Michael Haboustak <mike-@cinci.rr.com> for Concept2, Inc
- *  Copyright (c) 2006-2007 Jiri Kosina
  *  Copyright (c) 2007 Paul Walmsley
  *  Copyright (c) 2008 Jiri Slaby
+ *  Copyright (c) 2006-2008 Jiri Kosina
  */
 
 /*
 
 #include "hid-ids.h"
 
+#define VAIO_RDESC_CONSTANT 0x0001
+
+struct sony_sc {
+       unsigned long quirks;
+};
+
+/* Sony Vaio VGX has wrongly mouse pointer declared as constant */
+static void sony_report_fixup(struct hid_device *hdev, __u8 *rdesc,
+               unsigned int rsize)
+{
+       struct sony_sc *sc = hid_get_drvdata(hdev);
+
+       if ((sc->quirks & VAIO_RDESC_CONSTANT) &&
+                       rsize >= 56 && rdesc[54] == 0x81 && rdesc[55] == 0x07) {
+               dev_info(&hdev->dev, "Fixing up Sony Vaio VGX report "
+                               "descriptor\n");
+               rdesc[55] = 0x06;
+       }
+}
+
 /*
  * Sending HID_REQ_GET_REPORT changes the operation mode of the ps3 controller
  * to "operational".  Without this, the ps3 controller will not report any
@@ -56,6 +76,17 @@ static int sony_set_operational(struct hid_device *hdev)
 static int sony_probe(struct hid_device *hdev, const struct hid_device_id *id)
 {
        int ret;
+       unsigned long quirks = id->driver_data;
+       struct sony_sc *sc;
+
+       sc = kzalloc(sizeof(*sc), GFP_KERNEL);
+       if (sc == NULL) {
+               dev_err(&hdev->dev, "can't alloc apple descriptor\n");
+               return -ENOMEM;
+       }
+
+       sc->quirks = quirks;
+       hid_set_drvdata(hdev, sc);
 
        ret = hid_parse(hdev);
        if (ret) {
@@ -78,11 +109,20 @@ static int sony_probe(struct hid_device *hdev, const struct hid_device_id *id)
 err_stop:
        hid_hw_stop(hdev);
 err_free:
+       kfree(sc);
        return ret;
 }
 
+static void sony_remove(struct hid_device *hdev)
+{
+       hid_hw_stop(hdev);
+       kfree(hid_get_drvdata(hdev));
+}
+
 static const struct hid_device_id sony_devices[] = {
        { HID_USB_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_PS3_CONTROLLER) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_VAIO_VGX_MOUSE),
+               .driver_data = VAIO_RDESC_CONSTANT },
        { }
 };
 MODULE_DEVICE_TABLE(hid, sony_devices);
@@ -91,6 +131,8 @@ static struct hid_driver sony_driver = {
        .name = "sony",
        .id_table = sony_devices,
        .probe = sony_probe,
+       .remove = sony_remove,
+       .report_fixup = sony_report_fixup,
 };
 
 static int sony_init(void)
index af3edb98df435f2c3fa22fde81350d4f15dcd286..894d52e05bf9cd995586250011e8401227bd043a 100644 (file)
@@ -264,6 +264,7 @@ static long hidraw_ioctl(struct file *file, unsigned int cmd,
                default:
                        ret = -ENOTTY;
        }
+       unlock_kernel();
        return ret;
 }
 
@@ -403,7 +404,7 @@ out:
        return result;
 }
 
-void __exit hidraw_exit(void)
+void hidraw_exit(void)
 {
        dev_t dev_id = MKDEV(hidraw_major, 0);
 
index 705a43cdeea4251d89b8585f37b4c098cc4fe1b7..42bdd83444c1db874b259416bdf47ce81c6c3f58 100644 (file)
@@ -972,6 +972,9 @@ static int hid_probe(struct usb_interface *intf, const struct usb_device_id *id)
        hid->vendor = le16_to_cpu(dev->descriptor.idVendor);
        hid->product = le16_to_cpu(dev->descriptor.idProduct);
        hid->name[0] = 0;
+       if (intf->cur_altsetting->desc.bInterfaceProtocol ==
+                       USB_INTERFACE_PROTOCOL_MOUSE)
+               hid->type = HID_TYPE_USBMOUSE;
 
        if (dev->manufacturer)
                strlcpy(hid->name, dev->manufacturer, sizeof(hid->name));
index babd65dd46ad4eefa066c4e842288144f2941ab8..3ac320785fc58212d38334c2a87f35b130c66a45 100644 (file)
@@ -436,8 +436,7 @@ static noinline int hiddev_ioctl_usage(struct hiddev *hiddev, unsigned int cmd,
                if (copy_to_user(user_arg, uref, sizeof(*uref)))
                        goto fault;
 
-               kfree(uref_multi);
-               return 0;
+               goto goodreturn;
 
        default:
                if (cmd != HIDIOCGUSAGE &&
index d9e7a49d6cbf089da4f14f054695bf6be727200e..70bb854086dff42890369b6ab67347c013d93d68 100644 (file)
@@ -178,7 +178,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "+3.3V",              10, 0, 20, 1, 0 },
                { "5VSB",               11, 0, 30, 1, 0 },
                { "CPU",                24, 1, 1, 1, 0 },
-               { "System ",            25, 1, 1, 1, 0 },
+               { "System",             25, 1, 1, 1, 0 },
                { "PWM",                26, 1, 1, 1, 0 },
                { "CPU Fan",            32, 2, 60, 1, 0 },
                { "NB Fan",             33, 2, 60, 1, 0 },
@@ -200,7 +200,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "+3.3V",              10, 0, 20, 1, 0 },
                { "5VSB",               11, 0, 30, 1, 0 },
                { "CPU",                24, 1, 1, 1, 0 },
-               { "System ",            25, 1, 1, 1, 0 },
+               { "System",             25, 1, 1, 1, 0 },
                { "PWM1",               26, 1, 1, 1, 0 },
                { "PWM2",               27, 1, 1, 1, 0 },
                { "PWM3",               28, 1, 1, 1, 0 },
@@ -229,7 +229,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "+3.3V",              10, 0, 20, 1, 0 },
                { "5VSB",               11, 0, 30, 1, 0 },
                { "CPU",                24, 1, 1, 1, 0 },
-               { "System ",            25, 1, 1, 1, 0 },
+               { "System",             25, 1, 1, 1, 0 },
                { "PWM",                26, 1, 1, 1, 0 },
                { "CPU Fan",            32, 2, 60, 1, 0 },
                { "NB Fan",             33, 2, 60, 1, 0 },
@@ -250,7 +250,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "+3.3V",              10, 0, 20, 1, 0 },
                { "5VSB",               11, 0, 30, 1, 0 },
                { "CPU",                24, 1, 1, 1, 0 },
-               { "System ",            25, 1, 1, 1, 0 },
+               { "System",             25, 1, 1, 1, 0 },
                { "PWM",                26, 1, 1, 1, 0 },
                { "CPU Fan",            32, 2, 60, 1, 0 },
                { "NB Fan",             33, 2, 60, 1, 0 },
@@ -342,7 +342,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "+3.3V",              10, 0, 20, 1, 0 },
                { "5VSB",               11, 0, 30, 1, 0 },
                { "CPU",                24, 1, 1, 1, 0 },
-               { "System ",            25, 1, 1, 1, 0 },
+               { "System",             25, 1, 1, 1, 0 },
                { "PWM1",               26, 1, 1, 1, 0 },
                { "PWM2",               27, 1, 1, 1, 0 },
                { "PWM3",               28, 1, 1, 1, 0 },
@@ -371,7 +371,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "+3.3V",              10, 0, 20, 1, 0 },
                { "5VSB",               11, 0, 30, 1, 0 },
                { "CPU",                24, 1, 1, 1, 0 },
-               { "System ",            25, 1, 1, 1, 0 },
+               { "System",             25, 1, 1, 1, 0 },
                { "PWM",                26, 1, 1, 1, 0 },
                { "CPU Fan",            32, 2, 60, 1, 0 },
                { "NB Fan",             33, 2, 60, 1, 0 },
@@ -402,7 +402,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "AUX3 Fan",           36, 2, 60, 1, 0 },
                { NULL, 0, 0, 0, 0, 0 } }
        },
-       { 0x0016, NULL /* AW9D-MAX, need DMI string */, {
+       { 0x0016, "AW9D-MAX       (Intel i975-ICH7)", {
                { "CPU Core",            0, 0, 10, 1, 0 },
                { "DDR2",                1, 0, 20, 1, 0 },
                { "DDR2 VTT",            2, 0, 10, 1, 0 },
@@ -416,7 +416,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "+3.3V",              10, 0, 20, 1, 0 },
                { "5VSB",               11, 0, 30, 1, 0 },
                { "CPU",                24, 1, 1, 1, 0 },
-               { "System ",            25, 1, 1, 1, 0 },
+               { "System",             25, 1, 1, 1, 0 },
                { "PWM1",               26, 1, 1, 1, 0 },
                { "PWM2",               27, 1, 1, 1, 0 },
                { "PWM3",               28, 1, 1, 1, 0 },
@@ -446,7 +446,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "ATX +3.3V",          10, 0, 20, 1, 0 },
                { "ATX 5VSB",           11, 0, 30, 1, 0 },
                { "CPU",                24, 1, 1, 1, 0 },
-               { "System ",            26, 1, 1, 1, 0 },
+               { "System",             26, 1, 1, 1, 0 },
                { "PWM",                27, 1, 1, 1, 0 },
                { "CPU FAN",            32, 2, 60, 1, 0 },
                { "SYS FAN",            34, 2, 60, 1, 0 },
@@ -469,7 +469,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "+3.3V",              10, 0, 20, 1, 0 },
                { "5VSB",               11, 0, 30, 1, 0 },
                { "CPU",                24, 1, 1, 1, 0 },
-               { "System ",            25, 1, 1, 1, 0 },
+               { "System",             25, 1, 1, 1, 0 },
                { "PWM Phase1",         26, 1, 1, 1, 0 },
                { "PWM Phase2",         27, 1, 1, 1, 0 },
                { "PWM Phase3",         28, 1, 1, 1, 0 },
@@ -487,7 +487,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "DDR2",               13, 0, 20, 1, 0 },
                { "DDR2 VTT",           14, 0, 10, 1, 0 },
                { "CPU VTT",             3, 0, 20, 1, 0 },
-               { "NB 1.2V ",            4, 0, 10, 1, 0 },
+               { "NB 1.2V",             4, 0, 10, 1, 0 },
                { "SB 1.5V",             6, 0, 10, 1, 0 },
                { "HyperTransport",      5, 0, 10, 1, 0 },
                { "ATX +12V (24-Pin)",  12, 0, 60, 1, 0 },
@@ -496,7 +496,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "ATX +3.3V",          10, 0, 20, 1, 0 },
                { "ATX 5VSB",           11, 0, 30, 1, 0 },
                { "CPU",                24, 1, 1, 1, 0 },
-               { "System ",            25, 1, 1, 1, 0 },
+               { "System",             25, 1, 1, 1, 0 },
                { "PWM Phase1",         26, 1, 1, 1, 0 },
                { "PWM Phase2",         27, 1, 1, 1, 0 },
                { "PWM Phase3",         28, 1, 1, 1, 0 },
@@ -523,8 +523,8 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = {
                { "+3.3V",              10, 0, 20, 1, 0 },
                { "5VSB",               11, 0, 30, 1, 0 },
                { "CPU",                24, 1, 1, 1, 0 },
-               { "System ",            25, 1, 1, 1, 0 },
-               { "PWM ",               26, 1, 1, 1, 0 },
+               { "System",             25, 1, 1, 1, 0 },
+               { "PWM",                26, 1, 1, 1, 0 },
                { "PWM Phase2",         27, 1, 1, 1, 0 },
                { "PWM Phase3",         28, 1, 1, 1, 0 },
                { "PWM Phase4",         29, 1, 1, 1, 0 },
@@ -947,7 +947,7 @@ static int __devinit abituguru3_probe(struct platform_device *pdev)
        if (!abituguru3_motherboards[i].dmi_name) {
                printk(KERN_WARNING ABIT_UGURU3_NAME ": this motherboard was "
                        "not detected using DMI. Please send the output of "
-                       "\"dmidecode\" to the abituguru3 maintainer"
+                       "\"dmidecode\" to the abituguru3 maintainer "
                        "(see MAINTAINERS)\n");
        }
 #endif
index 3a0b63136479d7c4c701dc8eb6e3652e033c1831..b9a8ea30c99c822542682017fc40a4c83e99b4f7 100644 (file)
@@ -319,35 +319,24 @@ out:
 }
 
 /*
- * On this chip, voltages are given as a count of steps between a minimum
- * and maximum voltage, not a direct voltage.
+ * Conversions
  */
-static const int volt_convert_table[][2] = {
-       {2997, 3},
-       {4395, 4},
+
+/* IN are scaled acording to built-in resistors */
+static const int adt7473_scaling[] = {  /* .001 Volts */
+       2250, 3300
 };
+#define SCALE(val, from, to)   (((val) * (to) + ((from) / 2)) / (from))
 
 static int decode_volt(int volt_index, u8 raw)
 {
-       int cmax = volt_convert_table[volt_index][0];
-       int cmin = volt_convert_table[volt_index][1];
-       return ((raw * (cmax - cmin)) / 255) + cmin;
+       return SCALE(raw, 192, adt7473_scaling[volt_index]);
 }
 
 static u8 encode_volt(int volt_index, int cooked)
 {
-       int cmax = volt_convert_table[volt_index][0];
-       int cmin = volt_convert_table[volt_index][1];
-       u8 x;
-
-       if (cooked > cmax)
-               cooked = cmax;
-       else if (cooked < cmin)
-               cooked = cmin;
-
-       x = ((cooked - cmin) * 255) / (cmax - cmin);
-
-       return x;
+       int raw = SCALE(cooked, adt7473_scaling[volt_index], 192);
+       return SENSORS_LIMIT(raw, 0, 255);
 }
 
 static ssize_t show_volt_min(struct device *dev,
index c54eff92be4a6c4e6f45c1bf0d394fbc1c1f4655..bfc296145bba359572b5ed7f8b8fa7da23ec0773 100644 (file)
@@ -180,6 +180,7 @@ static struct vrm_model vrm_models[] = {
        {X86_VENDOR_AMD, 0x6, ANY, ANY, 90},            /* Athlon Duron etc */
        {X86_VENDOR_AMD, 0xF, 0x3F, ANY, 24},           /* Athlon 64, Opteron */
        {X86_VENDOR_AMD, 0xF, ANY, ANY, 25},            /* NPT family 0Fh */
+       {X86_VENDOR_AMD, 0x10, ANY, ANY, 25},           /* NPT family 10h */
        {X86_VENDOR_INTEL, 0x6, 0x9, ANY, 13},          /* Pentium M (130 nm) */
        {X86_VENDOR_INTEL, 0x6, 0xB, ANY, 85},          /* Tualatin */
        {X86_VENDOR_INTEL, 0x6, 0xD, ANY, 13},          /* Pentium M (90 nm) */
index 3edeebc0b8355361532becdcb246d6493924be44..96a7018667261a947c913ab667433facc35d7782 100644 (file)
@@ -12,9 +12,9 @@
  * made by National Semiconductor. Both have an increased remote
  * temperature measurement accuracy (1 degree), and the LM99
  * additionally shifts remote temperatures (measured and limits) by 16
- * degrees, which allows for higher temperatures measurement. The
- * driver doesn't handle it since it can be done easily in user-space.
+ * degrees, which allows for higher temperatures measurement.
  * Note that there is no way to differentiate between both chips.
+ * When device is auto-detected, the driver will assume an LM99.
  *
  * This driver also supports the LM86, another sensor chip made by
  * National Semiconductor. It is exactly similar to the LM90 except it
@@ -169,8 +169,8 @@ static const struct i2c_device_id lm90_id[] = {
        { "adt7461", adt7461 },
        { "lm90", lm90 },
        { "lm86", lm86 },
-       { "lm89", lm99 },
-       { "lm99", lm99 },       /* Missing temperature offset */
+       { "lm89", lm86 },
+       { "lm99", lm99 },
        { "max6646", max6646 },
        { "max6647", max6646 },
        { "max6649", max6646 },
@@ -366,6 +366,10 @@ static ssize_t show_temp8(struct device *dev, struct device_attribute *devattr,
        else
                temp = temp_from_s8(data->temp8[attr->index]);
 
+       /* +16 degrees offset for temp2 for the LM99 */
+       if (data->kind == lm99 && attr->index == 3)
+               temp += 16000;
+
        return sprintf(buf, "%d\n", temp);
 }
 
@@ -385,6 +389,10 @@ static ssize_t set_temp8(struct device *dev, struct device_attribute *devattr,
        long val = simple_strtol(buf, NULL, 10);
        int nr = attr->index;
 
+       /* +16 degrees offset for temp2 for the LM99 */
+       if (data->kind == lm99 && attr->index == 3)
+               val -= 16000;
+
        mutex_lock(&data->update_lock);
        if (data->kind == adt7461)
                data->temp8[nr] = temp_to_u8_adt7461(data, val);
@@ -411,6 +419,10 @@ static ssize_t show_temp11(struct device *dev, struct device_attribute *devattr,
        else
                temp = temp_from_s16(data->temp11[attr->index]);
 
+       /* +16 degrees offset for temp2 for the LM99 */
+       if (data->kind == lm99 &&  attr->index <= 2)
+               temp += 16000;
+
        return sprintf(buf, "%d\n", temp);
 }
 
@@ -432,6 +444,10 @@ static ssize_t set_temp11(struct device *dev, struct device_attribute *devattr,
        long val = simple_strtol(buf, NULL, 10);
        int nr = attr->index;
 
+       /* +16 degrees offset for temp2 for the LM99 */
+       if (data->kind == lm99 && attr->index <= 2)
+               val -= 16000;
+
        mutex_lock(&data->update_lock);
        if (data->kind == adt7461)
                data->temp11[nr] = temp_to_u16_adt7461(data, val);
@@ -461,9 +477,15 @@ static ssize_t show_temphyst(struct device *dev, struct device_attribute *devatt
 
        if (data->kind == adt7461)
                temp = temp_from_u8_adt7461(data, data->temp8[attr->index]);
+       else if (data->kind == max6646)
+               temp = temp_from_u8(data->temp8[attr->index]);
        else
                temp = temp_from_s8(data->temp8[attr->index]);
 
+       /* +16 degrees offset for temp2 for the LM99 */
+       if (data->kind == lm99 && attr->index == 3)
+               temp += 16000;
+
        return sprintf(buf, "%d\n", temp - temp_from_s8(data->temp_hyst));
 }
 
@@ -473,12 +495,19 @@ static ssize_t set_temphyst(struct device *dev, struct device_attribute *dummy,
        struct i2c_client *client = to_i2c_client(dev);
        struct lm90_data *data = i2c_get_clientdata(client);
        long val = simple_strtol(buf, NULL, 10);
-       long hyst;
+       int temp;
 
        mutex_lock(&data->update_lock);
-       hyst = temp_from_s8(data->temp8[2]) - val;
+       if (data->kind == adt7461)
+               temp = temp_from_u8_adt7461(data, data->temp8[2]);
+       else if (data->kind == max6646)
+               temp = temp_from_u8(data->temp8[2]);
+       else
+               temp = temp_from_s8(data->temp8[2]);
+
+       data->temp_hyst = hyst_to_reg(temp - val);
        i2c_smbus_write_byte_data(client, LM90_REG_W_TCRIT_HYST,
-                                 hyst_to_reg(hyst));
+                                 data->temp_hyst);
        mutex_unlock(&data->update_lock);
        return count;
 }
@@ -682,6 +711,15 @@ static int lm90_detect(struct i2c_client *new_client, int kind,
                                } else
                                if ((chip_id & 0xF0) == 0x30) { /* LM89/LM99 */
                                        kind = lm99;
+                                       dev_info(&adapter->dev,
+                                                "Assuming LM99 chip at "
+                                                "0x%02x\n", address);
+                                       dev_info(&adapter->dev,
+                                                "If it is an LM89, pass "
+                                                "force_lm86=%d,0x%02x when "
+                                                "loading the lm90 driver\n",
+                                                i2c_adapter_id(adapter),
+                                                address);
                                } else
                                if (address == 0x4C
                                 && (chip_id & 0xF0) == 0x10) { /* LM86 */
index d4d1b859d4f1df2a9262fd3a22629de4eb484292..fc12bd412e3a4917b5645339d3dd388af8f0d3a3 100644 (file)
@@ -1968,7 +1968,7 @@ exit:
        return res;
 }
 
-static void __exit
+static void
 w83781d_isa_unregister(void)
 {
        if (pdev) {
@@ -2017,7 +2017,7 @@ w83781d_isa_register(void)
        return 0;
 }
 
-static void __exit
+static void
 w83781d_isa_unregister(void)
 {
 }
index 76bdc9a27f6f7ae91bbdd0ad4635fb169229a27c..2d848010499dfed1997e0f0eed459cb0cff847ec 100644 (file)
@@ -690,9 +690,9 @@ static int __init icside_init(void)
        return ecard_register_driver(&icside_driver);
 }
 
-static void __exit icside_exit(void);
+static void __exit icside_exit(void)
 {
-       ecard_unregister_driver(&icside_driver);
+       ecard_remove_driver(&icside_driver);
 }
 
 MODULE_AUTHOR("Russell King <rmk@arm.linux.org.uk>");
index 78d27d9ae4303ab6ee1dd4d2860445b80ea69a2d..d5003ca69801684bdc71e65db78767a41445c42e 100644 (file)
@@ -11,7 +11,7 @@
 
 #include <asm/ecard.h>
 
-static struct const ide_port_info rapide_port_info = {
+static const struct ide_port_info rapide_port_info = {
        .host_flags             = IDE_HFLAG_MMIO | IDE_HFLAG_NO_DMA,
 };
 
@@ -97,7 +97,7 @@ static int __init rapide_init(void)
 
 static void __exit rapide_exit(void)
 {
-       ecard_unregister_driver(&rapide_driver);
+       ecard_remove_driver(&rapide_driver);
 }
 
 MODULE_LICENSE("GPL");
index f5b26dd579e4251d6dc822c52431062fb13958d4..108264de0ac9061c3f5901813bfbd5139153752a 100644 (file)
@@ -5,12 +5,13 @@ config I7300_IDLE_IOAT_CHANNEL
        bool
 
 config I7300_IDLE
-       tristate "Intel chipset idle power saving driver"
+       tristate "Intel chipset idle memory power saving driver"
        select I7300_IDLE_IOAT_CHANNEL
-       depends on X86_64
+       depends on X86_64 && EXPERIMENTAL
        help
-         Enable idle power savings with certain Intel server chipsets.
-         The chipset must have I/O AT support, such as the Intel 7300.
-         The power savings depends on the type and quantity of DRAM devices.
+         Enable memory power savings when idle with certain Intel server
+         chipsets. The chipset must have I/O AT support, such as the
+         Intel 7300. The power savings depends on the type and quantity of
+         DRAM devices.
 
 endmenu
index 59d1bbc3cd3c2756a126348ca0163ac863543db7..fb176f6ef9f8a153f4c53c8787dbaef18af5862a 100644 (file)
@@ -25,6 +25,7 @@
 #include <linux/delay.h>
 #include <linux/debugfs.h>
 #include <linux/stop_machine.h>
+#include <linux/i7300_idle.h>
 
 #include <asm/idle.h>
 
@@ -34,6 +35,8 @@
 #define I7300_IDLE_DRIVER_VERSION      "1.55"
 #define I7300_PRINT                    "i7300_idle:"
 
+#define MAX_STOP_RETRIES       10
+
 static int debug;
 module_param_named(debug, debug, uint, 0644);
 MODULE_PARM_DESC(debug, "Enable debug printks in this driver");
@@ -46,12 +49,12 @@ MODULE_PARM_DESC(debug, "Enable debug printks in this driver");
  *  0 = No throttling
  *  1 = Throttle when > 4 activations per eval window (Maximum throttling)
  *  2 = Throttle when > 8 activations
- *  168 = Throttle when > 168 activations (Minimum throttling)
+ *  168 = Throttle when > 672 activations (Minimum throttling)
  */
-#define MAX_THRTLWLIMIT                168
-static uint i7300_idle_thrtlowlm = 1;
-module_param_named(thrtlwlimit, i7300_idle_thrtlowlm, uint, 0644);
-MODULE_PARM_DESC(thrtlwlimit,
+#define MAX_THROTTLE_LOW_LIMIT         168
+static uint throttle_low_limit = 1;
+module_param_named(throttle_low_limit, throttle_low_limit, uint, 0644);
+MODULE_PARM_DESC(throttle_low_limit,
                "Value for THRTLOWLM activation field "
                "(0 = disable throttle, 1 = Max throttle, 168 = Min throttle)");
 
@@ -110,9 +113,9 @@ static int i7300_idle_ioat_start(void)
 static void i7300_idle_ioat_stop(void)
 {
        int i;
-       u8 sts;
+       u64 sts;
 
-       for (i = 0; i < 5; i++) {
+       for (i = 0; i < MAX_STOP_RETRIES; i++) {
                writeb(IOAT_CHANCMD_RESET,
                        ioat_chanbase + IOAT1_CHANCMD_OFFSET);
 
@@ -126,9 +129,10 @@ static void i7300_idle_ioat_stop(void)
 
        }
 
-       if (i == 5)
-               dprintk("failed to suspend+reset I/O AT after 5 retries\n");
-
+       if (i == MAX_STOP_RETRIES) {
+               dprintk("failed to stop I/O AT after %d retries\n",
+                       MAX_STOP_RETRIES);
+       }
 }
 
 /* Test I/O AT by copying 1024 byte from 2k to 1k */
@@ -275,7 +279,7 @@ static void __exit i7300_idle_ioat_exit(void)
        i7300_idle_ioat_stop();
 
        /* Wait for a while for the channel to halt before releasing */
-       for (i = 0; i < 10; i++) {
+       for (i = 0; i < MAX_STOP_RETRIES; i++) {
                writeb(IOAT_CHANCMD_RESET,
                       ioat_chanbase + IOAT1_CHANCMD_OFFSET);
 
@@ -389,9 +393,9 @@ static void i7300_idle_start(void)
        new_ctl = i7300_idle_thrtctl_saved & ~DIMM_THRTCTL_THRMHUNT;
        pci_write_config_byte(fbd_dev, DIMM_THRTCTL, new_ctl);
 
-       limit = i7300_idle_thrtlowlm;
-       if (unlikely(limit > MAX_THRTLWLIMIT))
-               limit = MAX_THRTLWLIMIT;
+       limit = throttle_low_limit;
+       if (unlikely(limit > MAX_THROTTLE_LOW_LIMIT))
+               limit = MAX_THROTTLE_LOW_LIMIT;
 
        pci_write_config_byte(fbd_dev, DIMM_THRTLOW, limit);
 
@@ -440,7 +444,7 @@ static int i7300_idle_notifier(struct notifier_block *nb, unsigned long val,
        static ktime_t idle_begin_time;
        static int time_init = 1;
 
-       if (!i7300_idle_thrtlowlm)
+       if (!throttle_low_limit)
                return 0;
 
        if (unlikely(time_init)) {
@@ -505,77 +509,8 @@ static struct notifier_block i7300_idle_nb = {
        .notifier_call = i7300_idle_notifier,
 };
 
-/*
- * I/O AT controls (PCI bus 0 device 8 function 0)
- * DIMM controls (PCI bus 0 device 16 function 1)
- */
-#define IOAT_BUS 0
-#define IOAT_DEVFN PCI_DEVFN(8, 0)
-#define MEMCTL_BUS 0
-#define MEMCTL_DEVFN PCI_DEVFN(16, 1)
-
-struct fbd_ioat {
-       unsigned int vendor;
-       unsigned int ioat_dev;
-};
-
-/*
- * The i5000 chip-set has the same hooks as the i7300
- * but support is disabled by default because this driver
- * has not been validated on that platform.
- */
-#define SUPPORT_I5000 0
-
-static const struct fbd_ioat fbd_ioat_list[] = {
-       {PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_IOAT_CNB},
-#if SUPPORT_I5000
-       {PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_IOAT},
-#endif
-       {0, 0}
-};
-
-/* table of devices that work with this driver */
-static const struct pci_device_id pci_tbl[] = {
-       { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_FBD_CNB) },
-#if SUPPORT_I5000
-       { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_5000_ERR) },
-#endif
-       { } /* Terminating entry */
-};
-
 MODULE_DEVICE_TABLE(pci, pci_tbl);
 
-/* Check for known platforms with I/O-AT */
-static int __init i7300_idle_platform_probe(void)
-{
-       int i;
-
-       fbd_dev = pci_get_bus_and_slot(MEMCTL_BUS, MEMCTL_DEVFN);
-       if (!fbd_dev)
-               return -ENODEV;
-
-       for (i = 0; pci_tbl[i].vendor != 0; i++) {
-               if (fbd_dev->vendor == pci_tbl[i].vendor &&
-                   fbd_dev->device == pci_tbl[i].device) {
-                       break;
-               }
-       }
-       if (pci_tbl[i].vendor == 0)
-               return -ENODEV;
-
-       ioat_dev = pci_get_bus_and_slot(IOAT_BUS, IOAT_DEVFN);
-       if (!ioat_dev)
-               return -ENODEV;
-
-       for (i = 0; fbd_ioat_list[i].vendor != 0; i++) {
-               if (ioat_dev->vendor == fbd_ioat_list[i].vendor &&
-                   ioat_dev->device == fbd_ioat_list[i].ioat_dev) {
-                       return 0;
-               }
-       }
-       return -ENODEV;
-}
-
 int stats_open_generic(struct inode *inode, struct file *fp)
 {
        fp->private_data = inode->i_private;
@@ -617,7 +552,7 @@ static int __init i7300_idle_init(void)
        cpus_clear(idle_cpumask);
        total_us = 0;
 
-       if (i7300_idle_platform_probe())
+       if (i7300_idle_platform_probe(&fbd_dev, &ioat_dev))
                return -ENODEV;
 
        if (i7300_idle_thrt_save())
index f488b6852baf78840c31fccf413ca63445965ac2..4e993425977558b4a79d408f023149d6b492339c 100644 (file)
@@ -25,8 +25,8 @@ config MOUSE_PS2
          mice with wheels and extra buttons, Microsoft, Logitech or Genius
          compatible.
 
-         Synaptics TouchPad users might be interested in a specialized
-         XFree86 driver at:
+         Synaptics, ALPS or Elantech TouchPad users might be interested
+         in a specialized Xorg/XFree86 driver at:
                <http://w1.894.telia.com/~u89404340/touchpad/index.html>
          and a new version of GPM at:
                <http://www.geocities.com/dt_or/gpm/gpm.html>
@@ -87,6 +87,27 @@ config MOUSE_PS2_TRACKPOINT
 
          If unsure, say Y.
 
+config MOUSE_PS2_ELANTECH
+       bool "Elantech PS/2 protocol extension"
+       depends on MOUSE_PS2
+       help
+         Say Y here if you have an Elantech PS/2 touchpad connected
+         to your system.
+
+         Note that if you enable this driver you will need an updated
+         X.org Synaptics driver that does not require ABS_PRESSURE
+         reports from the touchpad (i.e. post 1.5.0 version). You can
+         grab a patch for the driver here:
+
+         http://userweb.kernel.org/~dtor/synaptics-no-abspressure.patch
+
+         If unsure, say N.
+
+         This driver exposes some configuration registers via sysfs
+         entries. For further information,
+         see <file:Documentation/input/elantech.txt>.
+
+
 config MOUSE_PS2_TOUCHKIT
        bool "eGalax TouchKit PS/2 protocol extension"
        depends on MOUSE_PS2
index 8e6e690978016b0dfae3f89276e05273764665b5..96f1dd8037f8dfa19562e8d7a200321b6e3c02d5 100644 (file)
@@ -21,6 +21,7 @@ obj-$(CONFIG_MOUSE_GPIO)      += gpio_mouse.o
 psmouse-objs := psmouse-base.o synaptics.o
 
 psmouse-$(CONFIG_MOUSE_PS2_ALPS)       += alps.o
+psmouse-$(CONFIG_MOUSE_PS2_ELANTECH)   += elantech.o
 psmouse-$(CONFIG_MOUSE_PS2_OLPC)       += hgpk.o
 psmouse-$(CONFIG_MOUSE_PS2_LOGIPS2PP)  += logips2pp.o
 psmouse-$(CONFIG_MOUSE_PS2_LIFEBOOK)   += lifebook.o
diff --git a/drivers/input/mouse/elantech.c b/drivers/input/mouse/elantech.c
new file mode 100644 (file)
index 0000000..b9a25d5
--- /dev/null
@@ -0,0 +1,674 @@
+/*
+ * Elantech Touchpad driver (v5)
+ *
+ * Copyright (C) 2007-2008 Arjan Opmeer <arjan@opmeer.net>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published
+ * by the Free Software Foundation.
+ *
+ * Trademarks are the property of their respective owners.
+ */
+
+#include <linux/delay.h>
+#include <linux/module.h>
+#include <linux/input.h>
+#include <linux/serio.h>
+#include <linux/libps2.h>
+#include "psmouse.h"
+#include "elantech.h"
+
+#define elantech_debug(format, arg...)                         \
+       do {                                                    \
+               if (etd->debug)                                 \
+                       printk(KERN_DEBUG format, ##arg);       \
+       } while (0)
+
+/*
+ * Send a Synaptics style sliced query command
+ */
+static int synaptics_send_cmd(struct psmouse *psmouse, unsigned char c,
+                               unsigned char *param)
+{
+       if (psmouse_sliced_command(psmouse, c) ||
+           ps2_command(&psmouse->ps2dev, param, PSMOUSE_CMD_GETINFO)) {
+               pr_err("elantech.c: synaptics_send_cmd query 0x%02x failed.\n", c);
+               return -1;
+       }
+
+       return 0;
+}
+
+/*
+ * A retrying version of ps2_command
+ */
+static int elantech_ps2_command(struct psmouse *psmouse,
+                               unsigned char *param, int command)
+{
+       struct ps2dev *ps2dev = &psmouse->ps2dev;
+       struct elantech_data *etd = psmouse->private;
+       int rc;
+       int tries = ETP_PS2_COMMAND_TRIES;
+
+       do {
+               rc = ps2_command(ps2dev, param, command);
+               if (rc == 0)
+                       break;
+               tries--;
+               elantech_debug("elantech.c: retrying ps2 command 0x%02x (%d).\n",
+                       command, tries);
+               msleep(ETP_PS2_COMMAND_DELAY);
+       } while (tries > 0);
+
+       if (rc)
+               pr_err("elantech.c: ps2 command 0x%02x failed.\n", command);
+
+       return rc;
+}
+
+/*
+ * Send an Elantech style special command to read a value from a register
+ */
+static int elantech_read_reg(struct psmouse *psmouse, unsigned char reg,
+                               unsigned char *val)
+{
+       struct elantech_data *etd = psmouse->private;
+       unsigned char param[3];
+       int rc = 0;
+
+       if (reg < 0x10 || reg > 0x26)
+               return -1;
+
+       if (reg > 0x11 && reg < 0x20)
+               return -1;
+
+       switch (etd->hw_version) {
+       case 1:
+               if (psmouse_sliced_command(psmouse, ETP_REGISTER_READ) ||
+                   psmouse_sliced_command(psmouse, reg) ||
+                   ps2_command(&psmouse->ps2dev, param, PSMOUSE_CMD_GETINFO)) {
+                       rc = -1;
+               }
+               break;
+
+       case 2:
+               if (elantech_ps2_command(psmouse,  NULL, ETP_PS2_CUSTOM_COMMAND) ||
+                   elantech_ps2_command(psmouse,  NULL, ETP_REGISTER_READ) ||
+                   elantech_ps2_command(psmouse,  NULL, ETP_PS2_CUSTOM_COMMAND) ||
+                   elantech_ps2_command(psmouse,  NULL, reg) ||
+                   elantech_ps2_command(psmouse, param, PSMOUSE_CMD_GETINFO)) {
+                       rc = -1;
+               }
+               break;
+       }
+
+       if (rc)
+               pr_err("elantech.c: failed to read register 0x%02x.\n", reg);
+       else
+               *val = param[0];
+
+       return rc;
+}
+
+/*
+ * Send an Elantech style special command to write a register with a value
+ */
+static int elantech_write_reg(struct psmouse *psmouse, unsigned char reg,
+                               unsigned char val)
+{
+       struct elantech_data *etd = psmouse->private;
+       int rc = 0;
+
+       if (reg < 0x10 || reg > 0x26)
+               return -1;
+
+       if (reg > 0x11 && reg < 0x20)
+               return -1;
+
+       switch (etd->hw_version) {
+       case 1:
+               if (psmouse_sliced_command(psmouse, ETP_REGISTER_WRITE) ||
+                   psmouse_sliced_command(psmouse, reg) ||
+                   psmouse_sliced_command(psmouse, val) ||
+                   ps2_command(&psmouse->ps2dev, NULL, PSMOUSE_CMD_SETSCALE11)) {
+                       rc = -1;
+               }
+               break;
+
+       case 2:
+               if (elantech_ps2_command(psmouse, NULL, ETP_PS2_CUSTOM_COMMAND) ||
+                   elantech_ps2_command(psmouse, NULL, ETP_REGISTER_WRITE) ||
+                   elantech_ps2_command(psmouse, NULL, ETP_PS2_CUSTOM_COMMAND) ||
+                   elantech_ps2_command(psmouse, NULL, reg) ||
+                   elantech_ps2_command(psmouse, NULL, ETP_PS2_CUSTOM_COMMAND) ||
+                   elantech_ps2_command(psmouse, NULL, val) ||
+                   elantech_ps2_command(psmouse, NULL, PSMOUSE_CMD_SETSCALE11)) {
+                       rc = -1;
+               }
+               break;
+       }
+
+       if (rc)
+               pr_err("elantech.c: failed to write register 0x%02x with value 0x%02x.\n",
+                       reg, val);
+
+       return rc;
+}
+
+/*
+ * Dump a complete mouse movement packet to the syslog
+ */
+static void elantech_packet_dump(unsigned char *packet, int size)
+{
+       int     i;
+
+       printk(KERN_DEBUG "elantech.c: PS/2 packet [");
+       for (i = 0; i < size; i++)
+               printk("%s0x%02x ", (i) ? ", " : " ", packet[i]);
+       printk("]\n");
+}
+
+/*
+ * Interpret complete data packets and report absolute mode input events for
+ * hardware version 1. (4 byte packets)
+ */
+static void elantech_report_absolute_v1(struct psmouse *psmouse)
+{
+       struct input_dev *dev = psmouse->dev;
+       struct elantech_data *etd = psmouse->private;
+       unsigned char *packet = psmouse->packet;
+       int fingers;
+
+       if (etd->fw_version_maj == 0x01) {
+               /* byte 0:  D   U  p1  p2   1  p3   R   L
+                  byte 1:  f   0  th  tw  x9  x8  y9  y8 */
+               fingers = ((packet[1] & 0x80) >> 7) +
+                               ((packet[1] & 0x30) >> 4);
+       } else {
+               /* byte 0: n1  n0  p2  p1   1  p3   R   L
+                  byte 1:  0   0   0   0  x9  x8  y9  y8 */
+               fingers = (packet[0] & 0xc0) >> 6;
+       }
+
+       input_report_key(dev, BTN_TOUCH, fingers != 0);
+
+       /* byte 2: x7  x6  x5  x4  x3  x2  x1  x0
+          byte 3: y7  y6  y5  y4  y3  y2  y1  y0 */
+       if (fingers) {
+               input_report_abs(dev, ABS_X,
+                       ((packet[1] & 0x0c) << 6) | packet[2]);
+               input_report_abs(dev, ABS_Y, ETP_YMAX_V1 -
+                       (((packet[1] & 0x03) << 8) | packet[3]));
+       }
+
+       input_report_key(dev, BTN_TOOL_FINGER, fingers == 1);
+       input_report_key(dev, BTN_TOOL_DOUBLETAP, fingers == 2);
+       input_report_key(dev, BTN_TOOL_TRIPLETAP, fingers == 3);
+       input_report_key(dev, BTN_LEFT, packet[0] & 0x01);
+       input_report_key(dev, BTN_RIGHT, packet[0] & 0x02);
+
+       if ((etd->fw_version_maj == 0x01) &&
+           (etd->capabilities & ETP_CAP_HAS_ROCKER)) {
+               /* rocker up */
+               input_report_key(dev, BTN_FORWARD, packet[0] & 0x40);
+               /* rocker down */
+               input_report_key(dev, BTN_BACK, packet[0] & 0x80);
+       }
+
+       input_sync(dev);
+}
+
+/*
+ * Interpret complete data packets and report absolute mode input events for
+ * hardware version 2. (6 byte packets)
+ */
+static void elantech_report_absolute_v2(struct psmouse *psmouse)
+{
+       struct input_dev *dev = psmouse->dev;
+       unsigned char *packet = psmouse->packet;
+       int fingers, x1, y1, x2, y2;
+
+       /* byte 0: n1  n0   .   .   .   .   R   L */
+       fingers = (packet[0] & 0xc0) >> 6;
+       input_report_key(dev, BTN_TOUCH, fingers != 0);
+
+       switch (fingers) {
+       case 1:
+               /* byte 1: x15 x14 x13 x12 x11 x10 x9  x8
+                  byte 2: x7  x6  x5  x4  x4  x2  x1  x0 */
+               input_report_abs(dev, ABS_X, (packet[1] << 8) | packet[2]);
+               /* byte 4: y15 y14 y13 y12 y11 y10 y8  y8
+                  byte 5: y7  y6  y5  y4  y3  y2  y1  y0 */
+               input_report_abs(dev, ABS_Y, ETP_YMAX_V2 -
+                       ((packet[4] << 8) | packet[5]));
+               break;
+
+       case 2:
+               /* The coordinate of each finger is reported separately with
+                  a lower resolution for two finger touches */
+               /* byte 0:  .   .  ay8 ax8  .   .   .   .
+                  byte 1: ax7 ax6 ax5 ax4 ax3 ax2 ax1 ax0 */
+               x1 = ((packet[0] & 0x10) << 4) | packet[1];
+               /* byte 2: ay7 ay6 ay5 ay4 ay3 ay2 ay1 ay0 */
+               y1 = ETP_2FT_YMAX - (((packet[0] & 0x20) << 3) | packet[2]);
+               /* byte 3:  .   .  by8 bx8  .   .   .   .
+                  byte 4: bx7 bx6 bx5 bx4 bx3 bx2 bx1 bx0 */
+               x2 = ((packet[3] & 0x10) << 4) | packet[4];
+               /* byte 5: by7 by8 by5 by4 by3 by2 by1 by0 */
+               y2 = ETP_2FT_YMAX - (((packet[3] & 0x20) << 3) | packet[5]);
+               /* For compatibility with the X Synaptics driver scale up one
+                  coordinate and report as ordinary mouse movent */
+               input_report_abs(dev, ABS_X, x1 << 2);
+               input_report_abs(dev, ABS_Y, y1 << 2);
+               /* For compatibility with the proprietary X Elantech driver
+                  report both coordinates as hat coordinates */
+               input_report_abs(dev, ABS_HAT0X, x1);
+               input_report_abs(dev, ABS_HAT0Y, y1);
+               input_report_abs(dev, ABS_HAT1X, x2);
+               input_report_abs(dev, ABS_HAT1Y, y2);
+               break;
+       }
+
+       input_report_key(dev, BTN_TOOL_FINGER, fingers == 1);
+       input_report_key(dev, BTN_TOOL_DOUBLETAP, fingers == 2);
+       input_report_key(dev, BTN_TOOL_TRIPLETAP, fingers == 3);
+       input_report_key(dev, BTN_LEFT, packet[0] & 0x01);
+       input_report_key(dev, BTN_RIGHT, packet[0] & 0x02);
+
+       input_sync(dev);
+}
+
+static int elantech_check_parity_v1(struct psmouse *psmouse)
+{
+       struct elantech_data *etd = psmouse->private;
+       unsigned char *packet = psmouse->packet;
+       unsigned char p1, p2, p3;
+
+       /* Parity bits are placed differently */
+       if (etd->fw_version_maj == 0x01) {
+               /* byte 0:  D   U  p1  p2   1  p3   R   L */
+               p1 = (packet[0] & 0x20) >> 5;
+               p2 = (packet[0] & 0x10) >> 4;
+       } else {
+               /* byte 0: n1  n0  p2  p1   1  p3   R   L */
+               p1 = (packet[0] & 0x10) >> 4;
+               p2 = (packet[0] & 0x20) >> 5;
+       }
+
+       p3 = (packet[0] & 0x04) >> 2;
+
+       return etd->parity[packet[1]] == p1 &&
+              etd->parity[packet[2]] == p2 &&
+              etd->parity[packet[3]] == p3;
+}
+
+/*
+ * Process byte stream from mouse and handle complete packets
+ */
+static psmouse_ret_t elantech_process_byte(struct psmouse *psmouse)
+{
+       struct elantech_data *etd = psmouse->private;
+
+       if (psmouse->pktcnt < psmouse->pktsize)
+               return PSMOUSE_GOOD_DATA;
+
+       if (etd->debug > 1)
+               elantech_packet_dump(psmouse->packet, psmouse->pktsize);
+
+       switch (etd->hw_version) {
+       case 1:
+               if (etd->paritycheck && !elantech_check_parity_v1(psmouse))
+                       return PSMOUSE_BAD_DATA;
+
+               elantech_report_absolute_v1(psmouse);
+               break;
+
+       case 2:
+               /* We don't know how to check parity in protocol v2 */
+               elantech_report_absolute_v2(psmouse);
+               break;
+       }
+
+       return PSMOUSE_FULL_PACKET;
+}
+
+/*
+ * Put the touchpad into absolute mode
+ */
+static int elantech_set_absolute_mode(struct psmouse *psmouse)
+{
+       struct elantech_data *etd = psmouse->private;
+       unsigned char val;
+       int tries = ETP_READ_BACK_TRIES;
+       int rc = 0;
+
+       switch (etd->hw_version) {
+       case 1:
+               etd->reg_10 = 0x16;
+               etd->reg_11 = 0x8f;
+               if (elantech_write_reg(psmouse, 0x10, etd->reg_10) ||
+                   elantech_write_reg(psmouse, 0x11, etd->reg_11)) {
+                       rc = -1;
+               }
+               break;
+
+       case 2:
+                                       /* Windows driver values */
+               etd->reg_10 = 0x54;
+               etd->reg_11 = 0x88;     /* 0x8a */
+               etd->reg_21 = 0x60;     /* 0x00 */
+               if (elantech_write_reg(psmouse, 0x10, etd->reg_10) ||
+                   elantech_write_reg(psmouse, 0x11, etd->reg_11) ||
+                   elantech_write_reg(psmouse, 0x21, etd->reg_21)) {
+                       rc = -1;
+                       break;
+               }
+               /*
+                * Read back reg 0x10. The touchpad is probably initalising
+                * and not ready until we read back the value we just wrote.
+                */
+               do {
+                       rc = elantech_read_reg(psmouse, 0x10, &val);
+                       if (rc == 0)
+                               break;
+                       tries--;
+                       elantech_debug("elantech.c: retrying read (%d).\n",
+                               tries);
+                       msleep(ETP_READ_BACK_DELAY);
+               } while (tries > 0);
+               if (rc)
+                       pr_err("elantech.c: failed to read back register 0x10.\n");
+               break;
+       }
+
+       if (rc)
+               pr_err("elantech.c: failed to initialise registers.\n");
+
+       return rc;
+}
+
+/*
+ * Set the appropriate event bits for the input subsystem
+ */
+static void elantech_set_input_params(struct psmouse *psmouse)
+{
+       struct input_dev *dev = psmouse->dev;
+       struct elantech_data *etd = psmouse->private;
+
+       __set_bit(EV_KEY, dev->evbit);
+       __set_bit(EV_ABS, dev->evbit);
+
+       __set_bit(BTN_LEFT, dev->keybit);
+       __set_bit(BTN_RIGHT, dev->keybit);
+
+       __set_bit(BTN_TOUCH, dev->keybit);
+       __set_bit(BTN_TOOL_FINGER, dev->keybit);
+       __set_bit(BTN_TOOL_DOUBLETAP, dev->keybit);
+       __set_bit(BTN_TOOL_TRIPLETAP, dev->keybit);
+
+       switch (etd->hw_version) {
+       case 1:
+               /* Rocker button */
+               if ((etd->fw_version_maj == 0x01) &&
+                   (etd->capabilities & ETP_CAP_HAS_ROCKER)) {
+                       __set_bit(BTN_FORWARD, dev->keybit);
+                       __set_bit(BTN_BACK, dev->keybit);
+               }
+               input_set_abs_params(dev, ABS_X, ETP_XMIN_V1, ETP_XMAX_V1, 0, 0);
+               input_set_abs_params(dev, ABS_Y, ETP_YMIN_V1, ETP_YMAX_V1, 0, 0);
+               break;
+
+       case 2:
+               input_set_abs_params(dev, ABS_X, ETP_XMIN_V2, ETP_XMAX_V2, 0, 0);
+               input_set_abs_params(dev, ABS_Y, ETP_YMIN_V2, ETP_YMAX_V2, 0, 0);
+               input_set_abs_params(dev, ABS_HAT0X, ETP_2FT_XMIN, ETP_2FT_XMAX, 0, 0);
+               input_set_abs_params(dev, ABS_HAT0Y, ETP_2FT_YMIN, ETP_2FT_YMAX, 0, 0);
+               input_set_abs_params(dev, ABS_HAT1X, ETP_2FT_XMIN, ETP_2FT_XMAX, 0, 0);
+               input_set_abs_params(dev, ABS_HAT1Y, ETP_2FT_YMIN, ETP_2FT_YMAX, 0, 0);
+               break;
+       }
+}
+
+struct elantech_attr_data {
+       size_t          field_offset;
+       unsigned char   reg;
+};
+
+/*
+ * Display a register value by reading a sysfs entry
+ */
+static ssize_t elantech_show_int_attr(struct psmouse *psmouse, void *data,
+                                       char *buf)
+{
+       struct elantech_data *etd = psmouse->private;
+       struct elantech_attr_data *attr = data;
+       unsigned char *reg = (unsigned char *) etd + attr->field_offset;
+       int rc = 0;
+
+       if (attr->reg)
+               rc = elantech_read_reg(psmouse, attr->reg, reg);
+
+       return sprintf(buf, "0x%02x\n", (attr->reg && rc) ? -1 : *reg);
+}
+
+/*
+ * Write a register value by writing a sysfs entry
+ */
+static ssize_t elantech_set_int_attr(struct psmouse *psmouse,
+                                    void *data, const char *buf, size_t count)
+{
+       struct elantech_data *etd = psmouse->private;
+       struct elantech_attr_data *attr = data;
+       unsigned char *reg = (unsigned char *) etd + attr->field_offset;
+       unsigned long value;
+       int err;
+
+       err = strict_strtoul(buf, 16, &value);
+       if (err)
+               return err;
+
+       if (value > 0xff)
+               return -EINVAL;
+
+       /* Do we need to preserve some bits for version 2 hardware too? */
+       if (etd->hw_version == 1) {
+               if (attr->reg == 0x10)
+                       /* Force absolute mode always on */
+                       value |= ETP_R10_ABSOLUTE_MODE;
+               else if (attr->reg == 0x11)
+                       /* Force 4 byte mode always on */
+                       value |= ETP_R11_4_BYTE_MODE;
+       }
+
+       if (!attr->reg || elantech_write_reg(psmouse, attr->reg, value) == 0)
+               *reg = value;
+
+       return count;
+}
+
+#define ELANTECH_INT_ATTR(_name, _register)                            \
+       static struct elantech_attr_data elantech_attr_##_name = {      \
+               .field_offset = offsetof(struct elantech_data, _name),  \
+               .reg = _register,                                       \
+       };                                                              \
+       PSMOUSE_DEFINE_ATTR(_name, S_IWUSR | S_IRUGO,                   \
+                           &elantech_attr_##_name,                     \
+                           elantech_show_int_attr,                     \
+                           elantech_set_int_attr)
+
+ELANTECH_INT_ATTR(reg_10, 0x10);
+ELANTECH_INT_ATTR(reg_11, 0x11);
+ELANTECH_INT_ATTR(reg_20, 0x20);
+ELANTECH_INT_ATTR(reg_21, 0x21);
+ELANTECH_INT_ATTR(reg_22, 0x22);
+ELANTECH_INT_ATTR(reg_23, 0x23);
+ELANTECH_INT_ATTR(reg_24, 0x24);
+ELANTECH_INT_ATTR(reg_25, 0x25);
+ELANTECH_INT_ATTR(reg_26, 0x26);
+ELANTECH_INT_ATTR(debug, 0);
+ELANTECH_INT_ATTR(paritycheck, 0);
+
+static struct attribute *elantech_attrs[] = {
+       &psmouse_attr_reg_10.dattr.attr,
+       &psmouse_attr_reg_11.dattr.attr,
+       &psmouse_attr_reg_20.dattr.attr,
+       &psmouse_attr_reg_21.dattr.attr,
+       &psmouse_attr_reg_22.dattr.attr,
+       &psmouse_attr_reg_23.dattr.attr,
+       &psmouse_attr_reg_24.dattr.attr,
+       &psmouse_attr_reg_25.dattr.attr,
+       &psmouse_attr_reg_26.dattr.attr,
+       &psmouse_attr_debug.dattr.attr,
+       &psmouse_attr_paritycheck.dattr.attr,
+       NULL
+};
+
+static struct attribute_group elantech_attr_group = {
+       .attrs = elantech_attrs,
+};
+
+/*
+ * Use magic knock to detect Elantech touchpad
+ */
+int elantech_detect(struct psmouse *psmouse, int set_properties)
+{
+       struct ps2dev *ps2dev = &psmouse->ps2dev;
+       unsigned char param[3];
+
+       ps2_command(&psmouse->ps2dev, NULL, PSMOUSE_CMD_RESET_DIS);
+
+       if (ps2_command(ps2dev,  NULL, PSMOUSE_CMD_DISABLE) ||
+           ps2_command(ps2dev,  NULL, PSMOUSE_CMD_SETSCALE11) ||
+           ps2_command(ps2dev,  NULL, PSMOUSE_CMD_SETSCALE11) ||
+           ps2_command(ps2dev,  NULL, PSMOUSE_CMD_SETSCALE11) ||
+           ps2_command(ps2dev, param, PSMOUSE_CMD_GETINFO)) {
+               pr_err("elantech.c: sending Elantech magic knock failed.\n");
+               return -1;
+       }
+
+       /*
+        * Report this in case there are Elantech models that use a different
+        * set of magic numbers
+        */
+       if (param[0] != 0x3c || param[1] != 0x03 || param[2] != 0xc8) {
+               pr_info("elantech.c: unexpected magic knock result 0x%02x, 0x%02x, 0x%02x.\n",
+                       param[0], param[1], param[2]);
+               return -1;
+       }
+
+       if (set_properties) {
+               psmouse->vendor = "Elantech";
+               psmouse->name = "Touchpad";
+       }
+
+       return 0;
+}
+
+/*
+ * Clean up sysfs entries when disconnecting
+ */
+static void elantech_disconnect(struct psmouse *psmouse)
+{
+       sysfs_remove_group(&psmouse->ps2dev.serio->dev.kobj,
+                          &elantech_attr_group);
+       kfree(psmouse->private);
+       psmouse->private = NULL;
+}
+
+/*
+ * Put the touchpad back into absolute mode when reconnecting
+ */
+static int elantech_reconnect(struct psmouse *psmouse)
+{
+       if (elantech_detect(psmouse, 0))
+               return -1;
+
+       if (elantech_set_absolute_mode(psmouse)) {
+               pr_err("elantech.c: failed to put touchpad back into absolute mode.\n");
+               return -1;
+       }
+
+       return 0;
+}
+
+/*
+ * Initialize the touchpad and create sysfs entries
+ */
+int elantech_init(struct psmouse *psmouse)
+{
+       struct elantech_data *etd;
+       int i, error;
+       unsigned char param[3];
+
+       etd = kzalloc(sizeof(struct elantech_data), GFP_KERNEL);
+       psmouse->private = etd;
+       if (!etd)
+               return -1;
+
+       etd->parity[0] = 1;
+       for (i = 1; i < 256; i++)
+               etd->parity[i] = etd->parity[i & (i - 1)] ^ 1;
+
+       /*
+        * Find out what version hardware this is
+        */
+       if (synaptics_send_cmd(psmouse, ETP_FW_VERSION_QUERY, param)) {
+               pr_err("elantech.c: failed to query firmware version.\n");
+               goto init_fail;
+       }
+       pr_info("elantech.c: Elantech version query result 0x%02x, 0x%02x, 0x%02x.\n",
+               param[0], param[1], param[2]);
+       etd->fw_version_maj = param[0];
+       etd->fw_version_min = param[2];
+
+       /*
+        * Assume every version greater than this is new EeePC style
+        * hardware with 6 byte packets
+        */
+       if (etd->fw_version_maj >= 0x02 && etd->fw_version_min >= 0x30) {
+               etd->hw_version = 2;
+               /* For now show extra debug information */
+               etd->debug = 1;
+               /* Don't know how to do parity checking for version 2 */
+               etd->paritycheck = 0;
+       } else {
+               etd->hw_version = 1;
+               etd->paritycheck = 1;
+       }
+       pr_info("elantech.c: assuming hardware version %d, firmware version %d.%d\n",
+               etd->hw_version, etd->fw_version_maj, etd->fw_version_min);
+
+       if (synaptics_send_cmd(psmouse, ETP_CAPABILITIES_QUERY, param)) {
+               pr_err("elantech.c: failed to query capabilities.\n");
+               goto init_fail;
+       }
+       pr_info("elantech.c: Synaptics capabilities query result 0x%02x, 0x%02x, 0x%02x.\n",
+               param[0], param[1], param[2]);
+       etd->capabilities = param[0];
+
+       if (elantech_set_absolute_mode(psmouse)) {
+               pr_err("elantech.c: failed to put touchpad into absolute mode.\n");
+               goto init_fail;
+       }
+
+       elantech_set_input_params(psmouse);
+
+       error = sysfs_create_group(&psmouse->ps2dev.serio->dev.kobj,
+                                  &elantech_attr_group);
+       if (error) {
+               pr_err("elantech.c: failed to create sysfs attributes, error: %d.\n",
+                       error);
+               goto init_fail;
+       }
+
+       psmouse->protocol_handler = elantech_process_byte;
+       psmouse->disconnect = elantech_disconnect;
+       psmouse->reconnect = elantech_reconnect;
+       psmouse->pktsize = etd->hw_version == 2 ? 6 : 4;
+
+       return 0;
+
+ init_fail:
+       kfree(etd);
+       return -1;
+}
diff --git a/drivers/input/mouse/elantech.h b/drivers/input/mouse/elantech.h
new file mode 100644 (file)
index 0000000..bee282b
--- /dev/null
@@ -0,0 +1,124 @@
+/*
+ * Elantech Touchpad driver (v5)
+ *
+ * Copyright (C) 2007-2008 Arjan Opmeer <arjan@opmeer.net>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published
+ * by the Free Software Foundation.
+ *
+ * Trademarks are the property of their respective owners.
+ */
+
+#ifndef _ELANTECH_H
+#define _ELANTECH_H
+
+/*
+ * Command values for Synaptics style queries
+ */
+#define ETP_FW_VERSION_QUERY           0x01
+#define ETP_CAPABILITIES_QUERY         0x02
+
+/*
+ * Command values for register reading or writing
+ */
+#define ETP_REGISTER_READ              0x10
+#define ETP_REGISTER_WRITE             0x11
+
+/*
+ * Hardware version 2 custom PS/2 command value
+ */
+#define ETP_PS2_CUSTOM_COMMAND         0xf8
+
+/*
+ * Times to retry a ps2_command and millisecond delay between tries
+ */
+#define ETP_PS2_COMMAND_TRIES          3
+#define ETP_PS2_COMMAND_DELAY          500
+
+/*
+ * Times to try to read back a register and millisecond delay between tries
+ */
+#define ETP_READ_BACK_TRIES            5
+#define ETP_READ_BACK_DELAY            2000
+
+/*
+ * Register bitmasks for hardware version 1
+ */
+#define ETP_R10_ABSOLUTE_MODE          0x04
+#define ETP_R11_4_BYTE_MODE            0x02
+
+/*
+ * Capability bitmasks
+ */
+#define ETP_CAP_HAS_ROCKER             0x04
+
+/*
+ * One hard to find application note states that X axis range is 0 to 576
+ * and Y axis range is 0 to 384 for harware version 1.
+ * Edge fuzz might be necessary because of bezel around the touchpad
+ */
+#define ETP_EDGE_FUZZ_V1               32
+
+#define ETP_XMIN_V1                    (  0 + ETP_EDGE_FUZZ_V1)
+#define ETP_XMAX_V1                    (576 - ETP_EDGE_FUZZ_V1)
+#define ETP_YMIN_V1                    (  0 + ETP_EDGE_FUZZ_V1)
+#define ETP_YMAX_V1                    (384 - ETP_EDGE_FUZZ_V1)
+
+/*
+ * It seems the resolution for hardware version 2 doubled.
+ * Hence the X and Y ranges are doubled too.
+ * The bezel around the pad also appears to be smaller
+ */
+#define ETP_EDGE_FUZZ_V2               8
+
+#define ETP_XMIN_V2                    (   0 + ETP_EDGE_FUZZ_V2)
+#define ETP_XMAX_V2                    (1152 - ETP_EDGE_FUZZ_V2)
+#define ETP_YMIN_V2                    (   0 + ETP_EDGE_FUZZ_V2)
+#define ETP_YMAX_V2                    ( 768 - ETP_EDGE_FUZZ_V2)
+
+/*
+ * For two finger touches the coordinate of each finger gets reported
+ * separately but with reduced resolution.
+ */
+#define ETP_2FT_FUZZ                   4
+
+#define ETP_2FT_XMIN                   (  0 + ETP_2FT_FUZZ)
+#define ETP_2FT_XMAX                   (288 - ETP_2FT_FUZZ)
+#define ETP_2FT_YMIN                   (  0 + ETP_2FT_FUZZ)
+#define ETP_2FT_YMAX                   (192 - ETP_2FT_FUZZ)
+
+struct elantech_data {
+       unsigned char reg_10;
+       unsigned char reg_11;
+       unsigned char reg_20;
+       unsigned char reg_21;
+       unsigned char reg_22;
+       unsigned char reg_23;
+       unsigned char reg_24;
+       unsigned char reg_25;
+       unsigned char reg_26;
+       unsigned char debug;
+       unsigned char capabilities;
+       unsigned char fw_version_maj;
+       unsigned char fw_version_min;
+       unsigned char hw_version;
+       unsigned char paritycheck;
+       unsigned char parity[256];
+};
+
+#ifdef CONFIG_MOUSE_PS2_ELANTECH
+int elantech_detect(struct psmouse *psmouse, int set_properties);
+int elantech_init(struct psmouse *psmouse);
+#else
+static inline int elantech_detect(struct psmouse *psmouse, int set_properties)
+{
+       return -ENOSYS;
+}
+static inline int elantech_init(struct psmouse *psmouse)
+{
+       return -ENOSYS;
+}
+#endif /* CONFIG_MOUSE_PS2_ELANTECH */
+
+#endif
index 126e977e199e00764d3f2ab32aafbd0e26fbe7e8..f8f86de694bbe6cdeced1097d0ac57a4aebab44c 100644 (file)
@@ -29,6 +29,7 @@
 #include "lifebook.h"
 #include "trackpoint.h"
 #include "touchkit_ps2.h"
+#include "elantech.h"
 
 #define DRIVER_DESC    "PS/2 mouse driver"
 
@@ -650,6 +651,19 @@ static int psmouse_extensions(struct psmouse *psmouse,
                max_proto = PSMOUSE_IMEX;
        }
 
+/*
+ * Try Elantech touchpad.
+ */
+       if (max_proto > PSMOUSE_IMEX &&
+                       elantech_detect(psmouse, set_properties) == 0) {
+               if (!set_properties || elantech_init(psmouse) == 0)
+                       return PSMOUSE_ELANTECH;
+/*
+ * Init failed, try basic relative protocols
+ */
+               max_proto = PSMOUSE_IMEX;
+       }
+
        if (max_proto > PSMOUSE_IMEX) {
                if (genius_detect(psmouse, set_properties) == 0)
                        return PSMOUSE_GENPS;
@@ -789,6 +803,15 @@ static const struct psmouse_protocol psmouse_protocols[] = {
                .detect         = hgpk_detect,
        },
 #endif
+#ifdef CONFIG_MOUSE_PS2_ELANTECH
+       {
+               .type           = PSMOUSE_ELANTECH,
+               .name           = "ETPS/2",
+               .alias          = "elantech",
+               .detect         = elantech_detect,
+               .init           = elantech_init,
+       },
+ #endif
        {
                .type           = PSMOUSE_CORTRON,
                .name           = "CortronPS/2",
index 8b608a1cdd12171135f3ca2ec0c7a6487728711a..54ed267894bdfaf466a3fc6732bd2252636218b3 100644 (file)
@@ -90,6 +90,7 @@ enum psmouse_type {
        PSMOUSE_TOUCHKIT_PS2,
        PSMOUSE_CORTRON,
        PSMOUSE_HGPK,
+       PSMOUSE_ELANTECH,
        PSMOUSE_AUTO            /* This one should always be last */
 };
 
index a321aea2c7b5f4dad1a9822539d2b3abb7700dfc..eec375cd10e6ef89546e8a51314bf647411a47ea 100644 (file)
@@ -135,6 +135,14 @@ static struct dmi_system_id __initdata i8042_dmi_noloop_table[] = {
                        DMI_MATCH(DMI_PRODUCT_VERSION, "5a"),
                },
        },
+       {
+               .ident = "Blue FB5601",
+               .matches = {
+                       DMI_MATCH(DMI_SYS_VENDOR, "blue"),
+                       DMI_MATCH(DMI_PRODUCT_NAME, "FB5601"),
+                       DMI_MATCH(DMI_PRODUCT_VERSION, "M606"),
+               },
+       },
        { }
 };
 
index 53a25b1c2dae8096d071d8ee2927d4bd8f644020..74645ab15660626379bfc6b5261bfc4e1ef5dd1c 100644 (file)
@@ -49,7 +49,7 @@ static struct acpi_hpled adev;
 
 static acpi_status hpled_acpi_write(acpi_handle handle, int reg)
 {
-       unsigned long ret; /* Not used when writing */
+       unsigned long long ret; /* Not used when writing */
        union acpi_object in_obj[1];
        struct acpi_object_list args = { 1, in_obj };
 
index c1a837ca193c26c4c74af8c975b76201005c2533..b4162f6f1b79eb5844ac989a59d9084c3a3bd725 100644 (file)
@@ -222,6 +222,9 @@ static void mddev_put(mddev_t *mddev)
                list_del(&mddev->all_mddevs);
                spin_unlock(&all_mddevs_lock);
                blk_cleanup_queue(mddev->queue);
+               if (mddev->sysfs_state)
+                       sysfs_put(mddev->sysfs_state);
+               mddev->sysfs_state = NULL;
                kobject_put(&mddev->kobj);
        } else
                spin_unlock(&all_mddevs_lock);
@@ -1459,6 +1462,8 @@ static int bind_rdev_to_array(mdk_rdev_t * rdev, mddev_t * mddev)
                kobject_del(&rdev->kobj);
                goto fail;
        }
+       rdev->sysfs_state = sysfs_get_dirent(rdev->kobj.sd, "state");
+
        list_add_rcu(&rdev->same_set, &mddev->disks);
        bd_claim_by_disk(rdev->bdev, rdev->bdev->bd_holder, mddev->gendisk);
        return 0;
@@ -1488,7 +1493,8 @@ static void unbind_rdev_from_array(mdk_rdev_t * rdev)
        printk(KERN_INFO "md: unbind<%s>\n", bdevname(rdev->bdev,b));
        rdev->mddev = NULL;
        sysfs_remove_link(&rdev->kobj, "block");
-
+       sysfs_put(rdev->sysfs_state);
+       rdev->sysfs_state = NULL;
        /* We need to delay this, otherwise we can deadlock when
         * writing to 'remove' to "dev/state".  We also need
         * to delay it due to rcu usage.
@@ -1923,8 +1929,8 @@ state_store(mdk_rdev_t *rdev, const char *buf, size_t len)
 
                err = 0;
        }
-       if (!err)
-               sysfs_notify(&rdev->kobj, NULL, "state");
+       if (!err && rdev->sysfs_state)
+               sysfs_notify_dirent(rdev->sysfs_state);
        return err ? err : len;
 }
 static struct rdev_sysfs_entry rdev_state =
@@ -2019,7 +2025,7 @@ slot_store(mdk_rdev_t *rdev, const char *buf, size_t len)
                        rdev->raid_disk = -1;
                        return err;
                } else
-                       sysfs_notify(&rdev->kobj, NULL, "state");
+                       sysfs_notify_dirent(rdev->sysfs_state);
                sprintf(nm, "rd%d", rdev->raid_disk);
                if (sysfs_create_link(&rdev->mddev->kobj, &rdev->kobj, nm))
                        printk(KERN_WARNING
@@ -2036,7 +2042,7 @@ slot_store(mdk_rdev_t *rdev, const char *buf, size_t len)
                clear_bit(Faulty, &rdev->flags);
                clear_bit(WriteMostly, &rdev->flags);
                set_bit(In_sync, &rdev->flags);
-               sysfs_notify(&rdev->kobj, NULL, "state");
+               sysfs_notify_dirent(rdev->sysfs_state);
        }
        return len;
 }
@@ -2770,7 +2776,7 @@ array_state_store(mddev_t *mddev, const char *buf, size_t len)
        if (err)
                return err;
        else {
-               sysfs_notify(&mddev->kobj, NULL, "array_state");
+               sysfs_notify_dirent(mddev->sysfs_state);
                return len;
        }
 }
@@ -3457,6 +3463,11 @@ static struct kobject *md_probe(dev_t dev, int *part, void *data)
        disk->fops = &md_fops;
        disk->private_data = mddev;
        disk->queue = mddev->queue;
+       /* Allow extended partitions.  This makes the
+        * 'mdp' device redundant, but we can really
+        * remove it now.
+        */
+       disk->flags |= GENHD_FL_EXT_DEVT;
        add_disk(disk);
        mddev->gendisk = disk;
        error = kobject_init_and_add(&mddev->kobj, &md_ktype,
@@ -3465,8 +3476,10 @@ static struct kobject *md_probe(dev_t dev, int *part, void *data)
        if (error)
                printk(KERN_WARNING "md: cannot register %s/md - name in use\n",
                       disk->disk_name);
-       else
+       else {
                kobject_uevent(&mddev->kobj, KOBJ_ADD);
+               mddev->sysfs_state = sysfs_get_dirent(mddev->kobj.sd, "array_state");
+       }
        return NULL;
 }
 
@@ -3477,7 +3490,7 @@ static void md_safemode_timeout(unsigned long data)
        if (!atomic_read(&mddev->writes_pending)) {
                mddev->safemode = 1;
                if (mddev->external)
-                       set_bit(MD_NOTIFY_ARRAY_STATE, &mddev->flags);
+                       sysfs_notify_dirent(mddev->sysfs_state);
        }
        md_wakeup_thread(mddev->thread);
 }
@@ -3578,7 +3591,7 @@ static int do_md_run(mddev_t * mddev)
                                return -EINVAL;
                        }
                }
-               sysfs_notify(&rdev->kobj, NULL, "state");
+               sysfs_notify_dirent(rdev->sysfs_state);
        }
 
        md_probe(mddev->unit, NULL, NULL);
@@ -3740,7 +3753,7 @@ static int do_md_run(mddev_t * mddev)
 
        mddev->changed = 1;
        md_new_event(mddev);
-       sysfs_notify(&mddev->kobj, NULL, "array_state");
+       sysfs_notify_dirent(mddev->sysfs_state);
        sysfs_notify(&mddev->kobj, NULL, "sync_action");
        sysfs_notify(&mddev->kobj, NULL, "degraded");
        kobject_uevent(&disk_to_dev(mddev->gendisk)->kobj, KOBJ_CHANGE);
@@ -3767,7 +3780,7 @@ static int restart_array(mddev_t *mddev)
        set_bit(MD_RECOVERY_NEEDED, &mddev->recovery);
        md_wakeup_thread(mddev->thread);
        md_wakeup_thread(mddev->sync_thread);
-       sysfs_notify(&mddev->kobj, NULL, "array_state");
+       sysfs_notify_dirent(mddev->sysfs_state);
        return 0;
 }
 
@@ -3847,7 +3860,7 @@ static int do_md_stop(mddev_t * mddev, int mode, int is_open)
                        module_put(mddev->pers->owner);
                        mddev->pers = NULL;
                        /* tell userspace to handle 'inactive' */
-                       sysfs_notify(&mddev->kobj, NULL, "array_state");
+                       sysfs_notify_dirent(mddev->sysfs_state);
 
                        set_capacity(disk, 0);
                        mddev->changed = 1;
@@ -3933,7 +3946,7 @@ static int do_md_stop(mddev_t * mddev, int mode, int is_open)
                        mdname(mddev));
        err = 0;
        md_new_event(mddev);
-       sysfs_notify(&mddev->kobj, NULL, "array_state");
+       sysfs_notify_dirent(mddev->sysfs_state);
 out:
        return err;
 }
@@ -4297,7 +4310,7 @@ static int add_new_disk(mddev_t * mddev, mdu_disk_info_t *info)
                if (err)
                        export_rdev(rdev);
                else
-                       sysfs_notify(&rdev->kobj, NULL, "state");
+                       sysfs_notify_dirent(rdev->sysfs_state);
 
                md_update_sb(mddev, 1);
                if (mddev->degraded)
@@ -4938,7 +4951,7 @@ static int md_ioctl(struct block_device *bdev, fmode_t mode,
        if (_IOC_TYPE(cmd) == MD_MAJOR && mddev->ro && mddev->pers) {
                if (mddev->ro == 2) {
                        mddev->ro = 0;
-                       sysfs_notify(&mddev->kobj, NULL, "array_state");
+                       sysfs_notify_dirent(mddev->sysfs_state);
                        set_bit(MD_RECOVERY_NEEDED, &mddev->recovery);
                        md_wakeup_thread(mddev->thread);
                } else {
@@ -5612,7 +5625,7 @@ void md_write_start(mddev_t *mddev, struct bio *bi)
                spin_unlock_irq(&mddev->write_lock);
        }
        if (did_change)
-               sysfs_notify(&mddev->kobj, NULL, "array_state");
+               sysfs_notify_dirent(mddev->sysfs_state);
        wait_event(mddev->sb_wait,
                   !test_bit(MD_CHANGE_CLEAN, &mddev->flags) &&
                   !test_bit(MD_CHANGE_PENDING, &mddev->flags));
@@ -5655,7 +5668,7 @@ int md_allow_write(mddev_t *mddev)
                        mddev->safemode = 1;
                spin_unlock_irq(&mddev->write_lock);
                md_update_sb(mddev, 0);
-               sysfs_notify(&mddev->kobj, NULL, "array_state");
+               sysfs_notify_dirent(mddev->sysfs_state);
        } else
                spin_unlock_irq(&mddev->write_lock);
 
@@ -6048,9 +6061,6 @@ void md_check_recovery(mddev_t *mddev)
        if (mddev->bitmap)
                bitmap_daemon_work(mddev->bitmap);
 
-       if (test_and_clear_bit(MD_NOTIFY_ARRAY_STATE, &mddev->flags))
-               sysfs_notify(&mddev->kobj, NULL, "array_state");
-
        if (mddev->ro)
                return;
 
@@ -6103,7 +6113,7 @@ void md_check_recovery(mddev_t *mddev)
                                mddev->safemode = 0;
                        spin_unlock_irq(&mddev->write_lock);
                        if (did_change)
-                               sysfs_notify(&mddev->kobj, NULL, "array_state");
+                               sysfs_notify_dirent(mddev->sysfs_state);
                }
 
                if (mddev->flags)
@@ -6111,7 +6121,7 @@ void md_check_recovery(mddev_t *mddev)
 
                rdev_for_each(rdev, rtmp, mddev)
                        if (test_and_clear_bit(StateChanged, &rdev->flags))
-                               sysfs_notify(&rdev->kobj, NULL, "state");
+                               sysfs_notify_dirent(rdev->sysfs_state);
 
 
                if (test_bit(MD_RECOVERY_RUNNING, &mddev->recovery) &&
@@ -6221,7 +6231,7 @@ void md_check_recovery(mddev_t *mddev)
 
 void md_wait_for_blocked_rdev(mdk_rdev_t *rdev, mddev_t *mddev)
 {
-       sysfs_notify(&rdev->kobj, NULL, "state");
+       sysfs_notify_dirent(rdev->sysfs_state);
        wait_event_timeout(rdev->blocked_wait,
                           !test_bit(Blocked, &rdev->flags),
                           msecs_to_jiffies(5000));
index 5a79d2d4cdaeaff90e0306a651dea21ba95e79f8..b550267c8d5ed0df8e1d36015b2aca62f0c5d80a 100644 (file)
@@ -103,8 +103,20 @@ config MFD_TC6393XB
        help
          Support for Toshiba Mobile IO Controller TC6393XB
 
+config PMIC_DA903X
+       bool "Dialog Semiconductor DA9030/DA9034 PMIC Support"
+       depends on I2C=y
+       help
+         Say yes here to support for Dialog Semiconductor DA9030 (a.k.a
+         ARAVA) and DA9034 (a.k.a MICCO), these are Power Management IC
+         usually found on PXA processors-based platforms. This includes
+         the I2C driver and the core APIs _only_, you have to select
+         individual components like LCD backlight, voltage regulators,
+         LEDs and battery-charger under the corresponding menus.
+
 config MFD_WM8400
        tristate "Support Wolfson Microelectronics WM8400"
+       depends on I2C
        help
          Support for the Wolfson Microelecronics WM8400 PMIC and audio
          CODEC.  This driver adds provides common support for accessing
index 0acefe8aff8729921ab5953c4a518e7450454cad..9a5ad8af9116327e07369ba81c80a9e8e00ec882 100644 (file)
@@ -30,3 +30,5 @@ ifeq ($(CONFIG_SA1100_ASSABET),y)
 obj-$(CONFIG_MCP_UCB1200)      += ucb1x00-assabet.o
 endif
 obj-$(CONFIG_UCB1400_CORE)     += ucb1400_core.o
+
+obj-$(CONFIG_PMIC_DA903X)      += da903x.o
\ No newline at end of file
index 696cf3647ceb3e61c6a9f41bf5ffae889c11ffef..2fadf323c696d381f1fe23fb062e108c1e97a59f 100644 (file)
@@ -391,6 +391,7 @@ static irqreturn_t mmci_irq(int irq, void *dev_id)
 static void mmci_request(struct mmc_host *mmc, struct mmc_request *mrq)
 {
        struct mmci_host *host = mmc_priv(mmc);
+       unsigned long flags;
 
        WARN_ON(host->mrq != NULL);
 
@@ -402,7 +403,7 @@ static void mmci_request(struct mmc_host *mmc, struct mmc_request *mrq)
                return;
        }
 
-       spin_lock_irq(&host->lock);
+       spin_lock_irqsave(&host->lock, flags);
 
        host->mrq = mrq;
 
@@ -411,7 +412,7 @@ static void mmci_request(struct mmc_host *mmc, struct mmc_request *mrq)
 
        mmci_start_command(host, mrq->cmd, 0);
 
-       spin_unlock_irq(&host->lock);
+       spin_unlock_irqrestore(&host->lock, flags);
 }
 
 static void mmci_set_ios(struct mmc_host *mmc, struct mmc_ios *ios)
index 2b4e975770f3a950d982f4f084d4ff81f8c94301..4b7cb389dc4989edaf2f70ce9da55420484767bd 100644 (file)
@@ -1915,92 +1915,6 @@ static void rtl_disable_msi(struct pci_dev *pdev, struct rtl8169_private *tp)
        }
 }
 
-static int rtl_eeprom_read(struct pci_dev *pdev, int cap, int addr, __le32 *val)
-{
-       int ret, count = 100;
-       u16 status = 0;
-       u32 value;
-
-       ret = pci_write_config_word(pdev, cap + PCI_VPD_ADDR, addr);
-       if (ret < 0)
-               return ret;
-
-       do {
-               udelay(10);
-               ret = pci_read_config_word(pdev, cap + PCI_VPD_ADDR, &status);
-               if (ret < 0)
-                       return ret;
-       } while (!(status & PCI_VPD_ADDR_F) && --count);
-
-       if (!(status & PCI_VPD_ADDR_F))
-               return -ETIMEDOUT;
-
-       ret = pci_read_config_dword(pdev, cap + PCI_VPD_DATA, &value);
-       if (ret < 0)
-               return ret;
-
-       *val = cpu_to_le32(value);
-
-       return 0;
-}
-
-static void rtl_init_mac_address(struct rtl8169_private *tp,
-                                void __iomem *ioaddr)
-{
-       struct pci_dev *pdev = tp->pci_dev;
-       int vpd_cap;
-       __le32 sig;
-       u8 mac[8];
-       u8 cfg1;
-
-       cfg1 = RTL_R8(Config1);
-       if (!(cfg1  & VPD)) {
-               if (netif_msg_probe(tp))
-                       dev_info(&pdev->dev, "VPD access disabled, enabling\n");
-               RTL_W8(Cfg9346, Cfg9346_Unlock);
-               RTL_W8(Config1, cfg1 | VPD);
-               RTL_W8(Cfg9346, Cfg9346_Lock);
-       }
-
-       vpd_cap = pci_find_capability(pdev, PCI_CAP_ID_VPD);
-       if (!vpd_cap)
-               return;
-
-       if (rtl_eeprom_read(pdev, vpd_cap, RTL_EEPROM_SIG_ADDR, &sig) < 0)
-               return;
-
-       if ((sig & RTL_EEPROM_SIG_MASK) != RTL_EEPROM_SIG) {
-               dev_info(&pdev->dev, "Missing EEPROM signature: %08x\n", sig);
-               return;
-       }
-
-       /*
-        * MAC address is stored in EEPROM at offset 0x0e
-        * Realtek says: "The VPD address does not have to be a DWORD-aligned
-        * address as defined in the PCI 2.2 Specifications, but the VPD data
-        * is always consecutive 4-byte data starting from the VPD address
-        * specified."
-        */
-       if (rtl_eeprom_read(pdev, vpd_cap, 0x000e, (__le32*)&mac[0]) < 0 ||
-           rtl_eeprom_read(pdev, vpd_cap, 0x0012, (__le32*)&mac[4]) < 0) {
-               if (netif_msg_probe(tp)) {
-                       dev_warn(&pdev->dev,
-                                "reading MAC address from EEPROM failed\n");
-               }
-               return;
-       }
-
-       if (netif_msg_probe(tp)) {
-               DECLARE_MAC_BUF(buf);
-
-               dev_info(&pdev->dev, "MAC address found in EEPROM: %s\n",
-                        print_mac(buf, mac));
-       }
-
-       if (is_valid_ether_addr(mac))
-               rtl_rar_set(tp, mac);
-}
-
 static int __devinit
 rtl8169_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
 {
@@ -2178,8 +2092,6 @@ rtl8169_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
 
        tp->mmio_addr = ioaddr;
 
-       rtl_init_mac_address(tp, ioaddr);
-
        /* Get MAC address */
        for (i = 0; i < MAC_ADDR_LEN; i++)
                dev->dev_addr[i] = RTL_R8(MAC0 + i);
index dfe7c8e1b18586fa9da406cd365bbfb14188ec97..b3a63edb69012bd443f4caebffdaddf12103b86a 100644 (file)
@@ -83,6 +83,9 @@ static acpi_status acpi_run_osc(acpi_handle handle,
        if (ACPI_FAILURE(status))
                return status;
 
+       if (!output.length)
+               return AE_NULL_OBJECT;
+
        out_obj = output.pointer;
        if (out_obj->type != ACPI_TYPE_BUFFER) {
                printk(KERN_DEBUG "Evaluate _OSC returns wrong type\n");
index fe3c9bf876089f1d71f7b45b92fb5110693eb599..e5f49f5385028b865aca64890a588eaa173db042 100644 (file)
@@ -1684,8 +1684,9 @@ asmlinkage long compat_sys_select(int n, compat_ulong_t __user *inp,
                        return -EFAULT;
 
                to = &end_time;
-               if (poll_select_set_timeout(to, tv.tv_sec,
-                                           tv.tv_usec * NSEC_PER_USEC))
+               if (poll_select_set_timeout(to,
+                               tv.tv_sec + (tv.tv_usec / USEC_PER_SEC),
+                               (tv.tv_usec % USEC_PER_SEC) * NSEC_PER_USEC))
                        return -EINVAL;
        }
 
index 99368bda0261321290a6afa52ad74a797f79cd54..aec5c13f634177bab34f108e9f4891e300b873a3 100644 (file)
@@ -930,8 +930,15 @@ errxit:
         * inside the main ready-list here.
         */
        for (nepi = ep->ovflist; (epi = nepi) != NULL;
-            nepi = epi->next, epi->next = EP_UNACTIVE_PTR)
-               list_add_tail(&epi->rdllink, &ep->rdllist);
+            nepi = epi->next, epi->next = EP_UNACTIVE_PTR) {
+               /*
+                * If the above loop quit with errors, the epoll item might still
+                * be linked to "txlist", and the list_splice() done below will
+                * take care of those cases.
+                */
+               if (!ep_is_linked(&epi->rdllink))
+                       list_add_tail(&epi->rdllink, &ep->rdllist);
+       }
        /*
         * We need to set back ep->ovflist to EP_UNACTIVE_PTR, so that after
         * releasing the lock, events will be queued in the normal way inside
index 4c82531ea0a8b0d13ce61b63eb7daeecbe5d1423..5853f4440af41949081cfd2bf3e2b8f1b9363c18 100644 (file)
@@ -456,17 +456,8 @@ static int ext3_dx_readdir(struct file * filp,
        if (info->extra_fname) {
                if (call_filldir(filp, dirent, filldir, info->extra_fname))
                        goto finished;
-
                info->extra_fname = NULL;
-               info->curr_node = rb_next(info->curr_node);
-               if (!info->curr_node) {
-                       if (info->next_hash == ~0) {
-                               filp->f_pos = EXT3_HTREE_EOF;
-                               goto finished;
-                       }
-                       info->curr_hash = info->next_hash;
-                       info->curr_minor_hash = 0;
-               }
+               goto next_node;
        } else if (!info->curr_node)
                info->curr_node = rb_first(&info->root);
 
@@ -498,9 +489,14 @@ static int ext3_dx_readdir(struct file * filp,
                info->curr_minor_hash = fname->minor_hash;
                if (call_filldir(filp, dirent, filldir, fname))
                        break;
-
+       next_node:
                info->curr_node = rb_next(info->curr_node);
-               if (!info->curr_node) {
+               if (info->curr_node) {
+                       fname = rb_entry(info->curr_node, struct fname,
+                                        rb_hash);
+                       info->curr_hash = fname->hash;
+                       info->curr_minor_hash = fname->minor_hash;
+               } else {
                        if (info->next_hash == ~0) {
                                filp->f_pos = EXT3_HTREE_EOF;
                                break;
index 3ca6a2b7632dcd987db185d3fbe40926628b3d78..fed5b610df5ac4485e0db7a5c796154ba89b9247 100644 (file)
@@ -459,17 +459,8 @@ static int ext4_dx_readdir(struct file *filp,
        if (info->extra_fname) {
                if (call_filldir(filp, dirent, filldir, info->extra_fname))
                        goto finished;
-
                info->extra_fname = NULL;
-               info->curr_node = rb_next(info->curr_node);
-               if (!info->curr_node) {
-                       if (info->next_hash == ~0) {
-                               filp->f_pos = EXT4_HTREE_EOF;
-                               goto finished;
-                       }
-                       info->curr_hash = info->next_hash;
-                       info->curr_minor_hash = 0;
-               }
+               goto next_node;
        } else if (!info->curr_node)
                info->curr_node = rb_first(&info->root);
 
@@ -501,9 +492,14 @@ static int ext4_dx_readdir(struct file *filp,
                info->curr_minor_hash = fname->minor_hash;
                if (call_filldir(filp, dirent, filldir, fname))
                        break;
-
+       next_node:
                info->curr_node = rb_next(info->curr_node);
-               if (!info->curr_node) {
+               if (info->curr_node) {
+                       fname = rb_entry(info->curr_node, struct fname,
+                                        rb_hash);
+                       info->curr_hash = fname->hash;
+                       info->curr_minor_hash = fname->minor_hash;
+               } else {
                        if (info->next_hash == ~0) {
                                filp->f_pos = EXT4_HTREE_EOF;
                                break;
index 448e44001286754f891249f216f7af3a01d1bfee..87df51eadcf2bd170ab0271e189cf8a580aa1adb 100644 (file)
@@ -519,8 +519,9 @@ asmlinkage long sys_select(int n, fd_set __user *inp, fd_set __user *outp,
                        return -EFAULT;
 
                to = &end_time;
-               if (poll_select_set_timeout(to, tv.tv_sec,
-                                           tv.tv_usec * NSEC_PER_USEC))
+               if (poll_select_set_timeout(to,
+                               tv.tv_sec + (tv.tv_usec / USEC_PER_SEC),
+                               (tv.tv_usec % USEC_PER_SEC) * NSEC_PER_USEC))
                        return -EINVAL;
        }
 
index f13bca2dd53b806303577cb298562a3a426b79b4..5355ca4b939e583b8483e19ab888d03a0643630f 100644 (file)
@@ -417,6 +417,11 @@ struct hid_input {
        struct input_dev *input;
 };
 
+enum hid_type {
+       HID_TYPE_OTHER = 0,
+       HID_TYPE_USBMOUSE
+};
+
 struct hid_driver;
 struct hid_ll_driver;
 
@@ -431,6 +436,7 @@ struct hid_device {                                                 /* device report descriptor */
        __u32 vendor;                                                   /* Vendor ID */
        __u32 product;                                                  /* Product ID */
        __u32 version;                                                  /* HID version */
+       enum hid_type type;                                             /* device type (mouse, kbd, ...) */
        unsigned country;                                               /* HID country */
        struct hid_report_enum report_enum[HID_REPORT_TYPES];
 
diff --git a/include/linux/i7300_idle.h b/include/linux/i7300_idle.h
new file mode 100644 (file)
index 0000000..05a80c4
--- /dev/null
@@ -0,0 +1,83 @@
+
+#ifndef I7300_IDLE_H
+#define I7300_IDLE_H
+
+#include <linux/pci.h>
+
+/*
+ * I/O AT controls (PCI bus 0 device 8 function 0)
+ * DIMM controls (PCI bus 0 device 16 function 1)
+ */
+#define IOAT_BUS 0
+#define IOAT_DEVFN PCI_DEVFN(8, 0)
+#define MEMCTL_BUS 0
+#define MEMCTL_DEVFN PCI_DEVFN(16, 1)
+
+struct fbd_ioat {
+       unsigned int vendor;
+       unsigned int ioat_dev;
+};
+
+/*
+ * The i5000 chip-set has the same hooks as the i7300
+ * but support is disabled by default because this driver
+ * has not been validated on that platform.
+ */
+#define SUPPORT_I5000 0
+
+static const struct fbd_ioat fbd_ioat_list[] = {
+       {PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_IOAT_CNB},
+#if SUPPORT_I5000
+       {PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_IOAT},
+#endif
+       {0, 0}
+};
+
+/* table of devices that work with this driver */
+static const struct pci_device_id pci_tbl[] = {
+       { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_FBD_CNB) },
+#if SUPPORT_I5000
+       { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_5000_ERR) },
+#endif
+       { } /* Terminating entry */
+};
+
+/* Check for known platforms with I/O-AT */
+static inline int i7300_idle_platform_probe(struct pci_dev **fbd_dev,
+                                               struct pci_dev **ioat_dev)
+{
+       int i;
+       struct pci_dev *memdev, *dmadev;
+
+       memdev = pci_get_bus_and_slot(MEMCTL_BUS, MEMCTL_DEVFN);
+       if (!memdev)
+               return -ENODEV;
+
+       for (i = 0; pci_tbl[i].vendor != 0; i++) {
+               if (memdev->vendor == pci_tbl[i].vendor &&
+                   memdev->device == pci_tbl[i].device) {
+                       break;
+               }
+       }
+       if (pci_tbl[i].vendor == 0)
+               return -ENODEV;
+
+       dmadev = pci_get_bus_and_slot(IOAT_BUS, IOAT_DEVFN);
+       if (!dmadev)
+               return -ENODEV;
+
+       for (i = 0; fbd_ioat_list[i].vendor != 0; i++) {
+               if (dmadev->vendor == fbd_ioat_list[i].vendor &&
+                   dmadev->device == fbd_ioat_list[i].ioat_dev) {
+                       if (fbd_dev)
+                               *fbd_dev = memdev;
+                       if (ioat_dev)
+                               *ioat_dev = dmadev;
+
+                       return 0;
+               }
+       }
+       return -ENODEV;
+}
+
+#endif
index c200b9a34affc193500897aead3eec14f98f5f5f..8fc909ef6787738b983b45243fc1786d4867fc2a 100644 (file)
@@ -115,6 +115,9 @@ struct mdk_rdev_s
                                           * in superblock.
                                           */
        struct work_struct del_work;    /* used for delayed sysfs removal */
+
+       struct sysfs_dirent *sysfs_state; /* handle for 'state'
+                                          * sysfs entry */
 };
 
 struct mddev_s
@@ -128,7 +131,6 @@ struct mddev_s
 #define MD_CHANGE_DEVS 0       /* Some device status has changed */
 #define MD_CHANGE_CLEAN 1      /* transition to or from 'clean' */
 #define MD_CHANGE_PENDING 2    /* superblock update in progress */
-#define MD_NOTIFY_ARRAY_STATE 3        /* atomic context wants to notify userspace */
 
        int                             ro;
 
@@ -239,6 +241,10 @@ struct mddev_s
        sector_t                        resync_max;     /* resync should pause
                                                         * when it gets here */
 
+       struct sysfs_dirent             *sysfs_state;   /* handle for 'array_state'
+                                                        * file in sysfs.
+                                                        */
+
        spinlock_t                      write_lock;
        wait_queue_head_t               sb_wait;        /* for waiting on superblock updates */
        atomic_t                        pending_writes; /* number of active superblock writes */
index 130d1a0eef113ef62f873d386f689f8533591d28..7e117a231af10313f1b9bd963bf404eecaf94c9e 100644 (file)
@@ -768,6 +768,7 @@ static void __init do_initcalls(void)
 static void __init do_basic_setup(void)
 {
        rcu_init_sched(); /* needed by module_init stage. */
+       init_workqueues();
        usermodehelper_init();
        driver_init();
        init_irq_proc();
@@ -851,8 +852,6 @@ static int __init kernel_init(void * unused)
 
        cad_pid = task_pid(current);
 
-       init_workqueues();
-
        smp_prepare_cpus(setup_max_cpus);
 
        do_pre_smp_initcalls();
index 046c1609606bc627059aa6cd5df687fa86f15d3b..35eebd5510c2165c6f8daa2cef1fecab9187d6d0 100644 (file)
@@ -2104,7 +2104,7 @@ static void *cgroup_tasks_start(struct seq_file *s, loff_t *pos)
        down_read(&cgrp->pids_mutex);
        if (pid) {
                int end = cgrp->pids_length;
-               int i;
+
                while (index < end) {
                        int mid = (index + end) / 2;
                        if (cgrp->tasks_pids[mid] == pid) {
index 8aff79d90ddccd3647cb884664920e45c609fe72..9bc4c00872c927a1033013a31ab19630ba9dc170 100644 (file)
@@ -160,4 +160,4 @@ static int __init stop_machine_init(void)
        stop_machine_work = alloc_percpu(struct work_struct);
        return 0;
 }
-early_initcall(stop_machine_init);
+core_initcall(stop_machine_init);
index 7d82be07fa1ddc7f907d1ad4a9471754bc722fad..646c7121dbc0a78ca0c3018f6e6025ff9bca5249 100644 (file)
@@ -16,7 +16,7 @@ config NL80211
 
 config WIRELESS_OLD_REGULATORY
        bool "Old wireless static regulatory definitions"
-       default n
+       default y
        ---help---
          This option enables the old static regulatory information
          and uses it within the new framework. This is available
@@ -40,11 +40,10 @@ config WIRELESS_OLD_REGULATORY
          ieee80211_regdom module parameter. This is being phased out and you
          should stop using them ASAP.
 
-         Say N unless you cannot install a new userspace application
-         or have one currently depending on the ieee80211_regdom module
-         parameter and cannot port it to use the new userspace interfaces.
-
-         This is scheduled for removal for 2.6.29.
+         Say Y unless you have installed a new userspace application.
+         Also say Y if have one currently depending on the ieee80211_regdom
+         module parameter and cannot port it to use the new userspace
+         interfaces.
 
 config WIRELESS_EXT
        bool "Wireless extensions"
index b91cf241a539ceaadbf603374d45b3c012a24e41..830d9eae11f99210d4f0c51ec177446e8074d6d0 100644 (file)
@@ -852,8 +852,7 @@ void conf_set_all_new_symbols(enum conf_def_mode mode)
 
        }
 
-       if (modules_sym)
-               sym_calc_value(modules_sym);
+       sym_clear_all_valid();
 
        if (mode != def_random)
                return;
index 44ee94d2ab761ba46b1f8f155009d78dbac2daad..a53e2fc8dfb539575fa2e6f2001cb79b83251b8a 100755 (executable)
@@ -1648,7 +1648,7 @@ sub dump_function($$) {
     $prototype =~ s/^noinline +//;
     $prototype =~ s/__devinit +//;
     $prototype =~ s/__init +//;
-    $prototype =~ s/^#define\s+//; #ak added
+    $prototype =~ s/^#\s*define\s+//; #ak added
     $prototype =~ s/__attribute__\s*\(\([a-z,]*\)\)//;
 
     # Yes, this truly is vile.  We are looking for:
@@ -1764,13 +1764,13 @@ sub process_state3_function($$) {
 
     $x =~ s@\/\/.*$@@gos; # strip C99-style comments to end of line
 
-    if ($x =~ m#\s*/\*\s+MACDOC\s*#io || ($x =~ /^#/ && $x !~ /^#define/)) {
+    if ($x =~ m#\s*/\*\s+MACDOC\s*#io || ($x =~ /^#/ && $x !~ /^#\s*define/)) {
        # do nothing
     }
     elsif ($x =~ /([^\{]*)/) {
        $prototype .= $1;
     }
-    if (($x =~ /\{/) || ($x =~ /\#define/) || ($x =~ /;/)) {
+    if (($x =~ /\{/) || ($x =~ /\#\s*define/) || ($x =~ /;/)) {
        $prototype =~ s@/\*.*?\*/@@gos; # strip comments.
        $prototype =~ s@[\r\n]+@ @gos; # strip newlines/cr's.
        $prototype =~ s@^\s+@@gos; # strip leading spaces