]> git.pld-linux.org Git - packages/kernel.git/blob - linux-2.4.20-iForce2.patch
- obsolete
[packages/kernel.git] / linux-2.4.20-iForce2.patch
1 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/Documentation/input/ff.txt linux-modified/Documentation/input/ff.txt
2 --- linux-vanilla/Documentation/input/ff.txt    Thu Sep 13 00:34:06 2001
3 +++ linux-modified/Documentation/input/ff.txt   Mon Jan  6 16:48:20 2003
4 @@ -1,6 +1,7 @@
5  Force feedback for Linux.
6  By Johann Deneux <deneux@ifrance.com> on 2001/04/22.
7 -
8 +You may redistribute this file. Please remember to include shape.fig and
9 +interactive.fig as well.
10  ----------------------------------------------------------------------------
11  
12  0. Introduction
13 @@ -38,13 +39,10 @@
14  
15  You then need to insert the modules into the following order:
16  % modprobe joydev
17 -% modprobe serport
18 +% modprobe serport             # Only for serial
19  % modprobe iforce
20  % modprobe evdev
21  % ./inputattach -ifor $2 &     # Only for serial
22 -For convenience, you may use the shell script named "ff" available from
23 -the cvs tree of the Linux Console Project at sourceforge. You can also
24 -retrieve it from http://www.esil.univ-mrs.fr/~jdeneux/projects/ff/.
25  If you are using USB, you don't need the inputattach step.
26  
27  Please check that you have all the /dev/input entries needed:
28 @@ -68,7 +66,7 @@
29  2.1 Does it work ?
30  ~~~~~~~~~~~~~~~~~~
31  There is an utility called fftest that will allow you to test the driver.
32 -% fftest /dev/eventXX
33 +% fftest /dev/input/eventXX
34  
35  3. Instructions to the developper
36  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
37 @@ -81,22 +79,30 @@
38  #include <linux/input.h>
39  #include <sys/ioctl.h>
40  
41 +unsigned long features[1 + FF_MAX/sizeof(unsigned long)];
42  int ioctl(int file_descriptor, int request, unsigned long *features);
43  
44 -"request" must be EVIOCGBIT(EV_FF, sizeof(unsigned long))
45 +"request" must be EVIOCGBIT(EV_FF, size of features array in bytes )
46  
47  Returns the features supported by the device. features is a bitfield with the
48  following bits:
49 -- FF_X         has an X axis (should allways be the case)
50 -- FF_Y         has an Y axis (usually not the case for wheels)
51 +- FF_X         has an X axis (usually joysticks)
52 +- FF_Y         has an Y axis (usually joysticks)
53 +- FF_WHEEL     has a wheel (usually sterring wheels)
54  - FF_CONSTANT  can render constant force effects
55 -- FF_PERIODIC  can render periodic effects (sine, ramp, square...)
56 +- FF_PERIODIC  can render periodic effects (sine, triangle, square...)
57 +- FF_RAMP       can render ramp effects
58  - FF_SPRING    can simulate the presence of a spring
59 -- FF_FRICTION  can simulate friction (aka drag, damper effect...)
60 +- FF_FRICTION  can simulate friction 
61 +- FF_DAMPER    can simulate damper effects
62  - FF_RUMBLE    rumble effects (normally the only effect supported by rumble
63                 pads)
64 -- 8 bits from FF_N_EFFECTS_0 containing the number of effects that can be
65 -               simultaneously played.
66 +- FF_INERTIA    can simulate inertia
67 +
68 +
69 +int ioctl(int fd, EVIOCGEFFECTS, int *n);
70 +
71 +Returns the number of effects the device can keep in its memory.
72  
73  3.2 Uploading effects to the device
74  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
75 @@ -112,7 +118,11 @@
76  The content of effect may be modified. In particular, its field "id" is set
77  to the unique id assigned by the driver. This data is required for performing
78  some operations (removing an effect, controlling the playback).
79 -See <linux/input.h> for a description of the ff_effect stuct.
80 +This if field must be set to -1 by the user in order to tell the driver to
81 +allocate a new effect.
82 +See <linux/input.h> for a description of the ff_effect stuct. You should also
83 +find help in a few sketches, contained in files shape.fig and interactive.fig.
84 +You need xfig to visualize these files.
85  
86  3.3 Removing an effect from the device
87  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
88 @@ -187,8 +197,31 @@
89  
90  3.7 Dynamic update of an effect
91  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
92 -This consists in changing some parameters of an effect while it's playing. The
93 -driver currently does not support that. You still have the brute-force method,
94 -which consists in erasing the effect and uploading the updated version. It
95 -actually works pretty well. You don't need to stop-and-start the effect.
96 +Proceed as if you wanted to upload a new effect, except that instead of
97 +setting the id field to -1, you set it to the wanted effect id.
98 +Normally, the effect is not stopped and restarted. However, depending on the
99 +type of device, not all paramaters can be dynamically updated. For example,
100 +the direction of an effect cannot be updated with iforce devices. In this
101 +case, the driver stops the effect, up-load it, and restart it.
102 +
103 +
104 +3.8 Information about the status of effects
105 +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
106 +Every time the status of an effect is changed, an event is sent. The values
107 +and meanings of the fields of the event are as follows:
108 +struct input_event {
109 +/* When the status of the effect changed */
110 +       struct timeval time;
111 +
112 +/* Set to EV_FF_STATUS */
113 +       unsigned short type;
114 +
115 +/* Contains the id of the effect */
116 +       unsigned short code;
117 +
118 +/* Indicates the status */
119 +       unsigned int value;
120 +};
121  
122 +FF_STATUS_STOPPED      The effect stopped playing
123 +FF_STATUS_PLAYING      The effect started to play
124 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/Documentation/input/interactive.fig linux-modified/Documentation/input/interactive.fig
125 --- linux-vanilla/Documentation/input/interactive.fig   Thu Jan  1 02:00:00 1970
126 +++ linux-modified/Documentation/input/interactive.fig  Mon Jan  6 16:48:20 2003
127 @@ -0,0 +1,42 @@
128 +#FIG 3.2
129 +Landscape
130 +Center
131 +Inches
132 +Letter  
133 +100.00
134 +Single
135 +-2
136 +1200 2
137 +2 1 0 2 0 7 50 0 -1 6.000 0 0 -1 0 0 6
138 +        1200 3600 1800 3600 2400 4800 3000 4800 4200 5700 4800 5700
139 +2 2 0 1 0 7 50 0 -1 4.000 0 0 -1 0 0 5
140 +        1200 3150 4800 3150 4800 6300 1200 6300 1200 3150
141 +2 1 0 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
142 +        1200 4800 4800 4800
143 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 4
144 +        2400 4800 2400 6525 1950 7125 1950 7800
145 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 4
146 +        3000 4800 3000 6525 3600 7125 3600 7800
147 +2 1 0 1 0 7 50 0 -1 4.000 0 0 -1 0 1 3
148 +       0 0 1.00 60.00 120.00
149 +        3825 5400 4125 5100 5400 5100
150 +2 1 0 1 0 7 50 0 -1 4.000 0 0 -1 0 1 3
151 +       0 0 1.00 60.00 120.00
152 +        2100 4200 2400 3900 5400 3900
153 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
154 +        4800 5700 5400 5700
155 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
156 +        1800 3600 5400 3600
157 +2 1 0 1 0 7 50 0 -1 4.000 0 0 -1 0 1 3
158 +       0 0 1.00 60.00 120.00
159 +        2700 4800 2700 4425 5400 4425
160 +2 1 0 1 0 7 50 0 -1 4.000 0 0 -1 1 1 2
161 +       0 0 1.00 60.00 120.00
162 +       0 0 1.00 60.00 120.00
163 +        1950 7800 3600 7800
164 +4 1 0 50 0 0 12 0.0000 4 135 810 2775 7725 Dead band\001
165 +4 0 0 50 0 0 12 0.0000 4 180 1155 5400 5700 right saturation\001
166 +4 0 0 50 0 0 12 0.0000 4 135 1065 5400 3600 left saturation\001
167 +4 0 0 50 0 0 12 0.0000 4 180 2505 5400 3900 left coeff ( positive in that case )\001
168 +4 0 0 50 0 0 12 0.0000 4 180 2640 5475 5100 right coeff ( negative in that case )\001
169 +4 0 0 50 0 0 12 0.0000 4 105 480 5400 4425 center\001
170 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/Documentation/input/joystick.txt linux-modified/Documentation/input/joystick.txt
171 --- linux-vanilla/Documentation/input/joystick.txt      Thu Sep 13 00:34:06 2001
172 +++ linux-modified/Documentation/input/joystick.txt     Mon Jan  6 16:48:20 2003
173 @@ -1,7 +1,7 @@
174                        Linux Joystick driver v2.0.0
175 -              (c) 1996-2000 Vojtech Pavlik <vojtech@suse.cz>
176 +              (c) 1996-2000 Vojtech Pavlik <vojtech@ucw.cz>
177                              Sponsored by SuSE
178 -          $Id$
179 +          $Id$
180  ----------------------------------------------------------------------------
181  
182  0. Disclaimer
183 @@ -21,8 +21,8 @@
184  Temple Place, Suite 330, Boston, MA 02111-1307 USA
185  
186    Should you need to contact me, the author, you can do so either by e-mail
187 -- mail your message to <vojtech@suse.cz>, or by paper mail: Vojtech Pavlik,
188 -Ucitelska 1576, Prague 8, 182 00 Czech Republic
189 +- mail your message to <vojtech@ucw.cz>, or by paper mail: Vojtech Pavlik,
190 +Simunkova 1594, Prague 8, 182 00 Czech Republic
191  
192    For your convenience, the GNU General Public License version 2 is included
193  in the package: See the file COPYING.
194 @@ -111,7 +111,7 @@
195         alias tty-ldisc-2 serport
196         alias char-major-13 input
197         above input joydev ns558 analog
198 -       options analog js=gameport
199 +       options analog js=gamepad
200  
201  2.5 Verifying that it works
202  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
203 @@ -503,15 +503,16 @@
204  
205  3.21 I-Force devices 
206  ~~~~~~~~~~~~~~~~~~~~
207 -  All I-Force devices are supported by the iforce.c module. This includes:
208 +  All I-Force devices are supported by the iforce.o module. This includes:
209  
210  * AVB Mag Turbo Force
211  * AVB Top Shot Pegasus
212 +* AVB Top Shot Force Feedback Racing Wheel
213  * Logitech WingMan Force
214 -* Logitech WingMan Force 3D
215  * Logitech WingMan Force Wheel 
216 -* Logitech WingMan Strike Force 3D
217  * Guillemot Race Leader Force Feedback
218 +* Guillemot Force Feedback Racing Wheel
219 +* Thrustmaster Motor Sport GT
220  
221    To use it, you need to attach the serial port to the driver using the
222  
223 @@ -524,6 +525,10 @@
224  isn't needed.
225  
226    The I-Force driver now supports force feedback via the event interface.
227 +
228 +  Please note that Logitech WingMan *3D devices are _not_ supported by this
229 +module, rather by hid. Force feedback is not supported for those devices.
230 +Logitech gamepads are also hid devices.
231  
232  3.22 Gravis Stinger gamepad 
233  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
234 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/Documentation/input/shape.fig linux-modified/Documentation/input/shape.fig
235 --- linux-vanilla/Documentation/input/shape.fig Thu Jan  1 02:00:00 1970
236 +++ linux-modified/Documentation/input/shape.fig        Mon Jan  6 16:48:20 2003
237 @@ -0,0 +1,65 @@
238 +#FIG 3.2
239 +Landscape
240 +Center
241 +Inches
242 +Letter  
243 +100.00
244 +Single
245 +-2
246 +1200 2
247 +2 1 0 2 0 7 50 0 -1 0.000 0 0 -1 0 0 6
248 +        4200 3600 4200 3075 4950 2325 7425 2325 8250 3150 8250 3600
249 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
250 +        4200 3675 4200 5400
251 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
252 +        8250 3675 8250 5400
253 +2 1 0 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
254 +        3675 3600 8700 3600
255 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
256 +        8775 3600 10200 3600
257 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
258 +        8325 3150 9075 3150
259 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
260 +        7500 2325 10200 2325
261 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
262 +        3600 3600 3000 3600
263 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
264 +        4125 3075 3000 3075
265 +2 1 0 1 0 7 50 0 -1 4.000 0 0 -1 1 1 2
266 +       0 0 1.00 60.00 120.00
267 +       0 0 1.00 60.00 120.00
268 +        4200 5400 8175 5400
269 +2 1 0 1 0 7 50 0 -1 4.000 0 0 -1 1 1 2
270 +       0 0 1.00 60.00 120.00
271 +       0 0 1.00 60.00 120.00
272 +        10125 2325 10125 3600
273 +2 1 0 1 0 7 50 0 -1 4.000 0 0 -1 1 1 2
274 +       0 0 1.00 60.00 120.00
275 +       0 0 1.00 60.00 120.00
276 +        3000 3150 3000 3600
277 +2 1 0 1 0 7 50 0 -1 4.000 0 0 -1 1 1 2
278 +       0 0 1.00 60.00 120.00
279 +       0 0 1.00 60.00 120.00
280 +        9075 3150 9075 3600
281 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
282 +        4950 2325 4950 1200
283 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2
284 +        7425 2325 7425 1200
285 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 4
286 +        4200 3075 4200 2400 3600 1800 3600 1200
287 +2 1 1 1 0 7 50 0 -1 4.000 0 0 -1 0 0 4
288 +        8250 3150 8250 2475 8775 1950 8775 1200
289 +2 1 0 1 0 7 50 0 -1 4.000 0 0 -1 1 1 2
290 +       0 0 1.00 60.00 120.00
291 +       0 0 1.00 60.00 120.00
292 +        3600 1275 4950 1275
293 +2 1 0 1 0 7 50 0 -1 4.000 0 0 -1 1 1 2
294 +       0 0 1.00 60.00 120.00
295 +       0 0 1.00 60.00 120.00
296 +        7425 1275 8700 1275
297 +4 1 0 50 0 0 12 0.0000 4 135 1140 6075 5325 Effect duration\001
298 +4 0 0 50 0 0 12 0.0000 4 180 1305 10200 3000 Effect magnitude\001
299 +4 0 0 50 0 0 12 0.0000 4 135 780 9150 3450 Fade level\001
300 +4 1 0 50 0 0 12 0.0000 4 180 1035 4275 1200 Attack length\001
301 +4 1 0 50 0 0 12 0.0000 4 180 885 8175 1200 Fade length\001
302 +4 2 0 50 0 0 12 0.0000 4 135 930 2925 3375 Attack level\001
303 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/Config.in linux-modified/drivers/char/joystick/Config.in
304 --- linux-vanilla/drivers/char/joystick/Config.in       Fri Nov 29 01:53:12 2002
305 +++ linux-modified/drivers/char/joystick/Config.in      Mon Jan  6 16:48:20 2003
306 @@ -32,8 +32,7 @@
307     dep_tristate '  InterAct digital joysticks and gamepads' CONFIG_INPUT_INTERACT $CONFIG_INPUT $CONFIG_INPUT_GAMEPORT
308     dep_tristate '  ThrustMaster DirectConnect joysticks and gamepads' CONFIG_INPUT_TMDC $CONFIG_INPUT $CONFIG_INPUT_GAMEPORT
309     dep_tristate '  Microsoft SideWinder digital joysticks and gamepads' CONFIG_INPUT_SIDEWINDER $CONFIG_INPUT $CONFIG_INPUT_GAMEPORT
310 -   dep_tristate '  I-Force USB joysticks and wheels' CONFIG_INPUT_IFORCE_USB $CONFIG_INPUT $CONFIG_USB
311 -   dep_tristate '  I-Force Serial joysticks and wheels' CONFIG_INPUT_IFORCE_232 $CONFIG_INPUT $CONFIG_INPUT_SERIO
312 +   source drivers/char/joystick/iforce/Config.in
313     dep_tristate '  Logitech WingMan Warrior joystick' CONFIG_INPUT_WARRIOR $CONFIG_INPUT $CONFIG_INPUT_SERIO
314     dep_tristate '  LogiCad3d Magellan/SpaceMouse 6dof controller' CONFIG_INPUT_MAGELLAN $CONFIG_INPUT $CONFIG_INPUT_SERIO
315     dep_tristate '  SpaceTec SpaceOrb/Avenger 6dof controller' CONFIG_INPUT_SPACEORB $CONFIG_INPUT $CONFIG_INPUT_SERIO
316 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/Makefile linux-modified/drivers/char/joystick/Makefile
317 --- linux-vanilla/drivers/char/joystick/Makefile        Fri Nov 29 01:53:12 2002
318 +++ linux-modified/drivers/char/joystick/Makefile       Mon Jan  6 16:54:09 2003
319 @@ -8,19 +8,6 @@
320  
321  export-objs    := serio.o gameport.o pcigame.o
322  
323 -# I-Force may need both USB and RS-232
324 -
325 -ifeq ($(CONFIG_INPUT_IFORCE_232),m)
326 -       ifeq ($(CONFIG_INPUT_IFORCE_USB),y)
327 -               CONFIG_INPUT_IFORCE_USB := m
328 -       endif
329 -endif
330 -ifeq ($(CONFIG_INPUT_IFORCE_USB),m)
331 -       ifeq ($(CONFIG_INPUT_IFORCE_232),y)
332 -               CONFIG_INPUT_IFORCE_232 := m
333 -       endif
334 -endif
335 -
336  # Object file lists.
337  
338  obj-y  :=
339 @@ -46,8 +33,6 @@
340  obj-$(CONFIG_INPUT_SPACEORB)   += spaceorb.o
341  obj-$(CONFIG_INPUT_SPACEBALL)  += spaceball.o
342  obj-$(CONFIG_INPUT_STINGER)    += stinger.o
343 -obj-$(CONFIG_INPUT_IFORCE_232) += iforce.o
344 -obj-$(CONFIG_INPUT_IFORCE_USB) += iforce.o
345  
346  obj-$(CONFIG_INPUT_ANALOG)     += analog.o
347  obj-$(CONFIG_INPUT_A3D)                += a3d.o
348 @@ -64,6 +49,8 @@
349  obj-$(CONFIG_INPUT_TURBOGRAFX) += turbografx.o
350  
351  obj-$(CONFIG_INPUT_AMIJOY)     += amijoy.o
352 +
353 +subdir-$(CONFIG_JOYSTICK_IFORCE)       += iforce
354  
355  # The global Rules.make.
356  
357 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/a3d.c linux-modified/drivers/char/joystick/a3d.c
358 --- linux-vanilla/drivers/char/joystick/a3d.c   Sat Aug  3 02:39:43 2002
359 +++ linux-modified/drivers/char/joystick/a3d.c  Mon Jan  6 16:48:20 2003
360 @@ -347,8 +347,8 @@
361         a3d->dev.idversion = 0x0100;
362  
363         input_register_device(&a3d->dev);
364 -       printk(KERN_INFO "input%d: %s on gameport%d.0\n",
365 -               a3d->dev.number, a3d_names[a3d->mode], gameport->number);
366 +       printk(KERN_INFO "input: %s on gameport%d.0\n",
367 +              a3d_names[a3d->mode], gameport->number);
368  
369         return;
370  fail2: gameport_close(gameport);
371 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/adi.c linux-modified/drivers/char/joystick/adi.c
372 --- linux-vanilla/drivers/char/joystick/adi.c   Thu Sep 13 00:34:06 2001
373 +++ linux-modified/drivers/char/joystick/adi.c  Mon Jan  6 16:48:20 2003
374 @@ -514,8 +514,8 @@
375                 if (port->adi[i].length > 0) {
376                         adi_init_center(port->adi + i);
377                         input_register_device(&port->adi[i].dev);
378 -                       printk(KERN_INFO "input%d: %s [%s] on gameport%d.%d\n",
379 -                               port->adi[i].dev.number, port->adi[i].name, port->adi[i].cname, gameport->number, i);
380 +                       printk(KERN_INFO "input: %s [%s] on gameport%d.%d\n",
381 +                               port->adi[i].name, port->adi[i].cname, gameport->number, i);
382                 }
383  }
384  
385 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/analog.c linux-modified/drivers/char/joystick/analog.c
386 --- linux-vanilla/drivers/char/joystick/analog.c        Fri Nov 29 01:53:12 2002
387 +++ linux-modified/drivers/char/joystick/analog.c       Mon Jan  6 16:48:20 2003
388 @@ -490,8 +490,8 @@
389  
390         input_register_device(&analog->dev);
391  
392 -       printk(KERN_INFO "input%d: %s at gameport%d.%d",
393 -               analog->dev.number, analog->name, port->gameport->number, index);
394 +       printk(KERN_INFO "input: %s at gameport%d.%d",
395 +               analog->name, port->gameport->number, index);
396  
397         if (port->cooked)
398                 printk(" [ADC port]\n");
399 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/cobra.c linux-modified/drivers/char/joystick/cobra.c
400 --- linux-vanilla/drivers/char/joystick/cobra.c Thu Sep 13 00:34:06 2001
401 +++ linux-modified/drivers/char/joystick/cobra.c        Mon Jan  6 16:48:20 2003
402 @@ -208,8 +208,8 @@
403                         cobra->dev[i].absmin[ABS_Y] = -1; cobra->dev[i].absmax[ABS_Y] = 1;
404  
405                         input_register_device(cobra->dev + i);
406 -                       printk(KERN_INFO "input%d: %s on gameport%d.%d\n",
407 -                               cobra->dev[i].number, cobra_name, gameport->number, i);
408 +                       printk(KERN_INFO "input: %s on gameport%d.%d\n",
409 +                               cobra_name, gameport->number, i);
410                 }
411  
412  
413 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/db9.c linux-modified/drivers/char/joystick/db9.c
414 --- linux-vanilla/drivers/char/joystick/db9.c   Thu Sep 13 00:34:06 2001
415 +++ linux-modified/drivers/char/joystick/db9.c  Mon Jan  6 16:48:20 2003
416 @@ -362,8 +362,8 @@
417                 db9->dev[i].absmin[ABS_Y] = -1; db9->dev[i].absmax[ABS_Y] = 1;
418  
419                 input_register_device(db9->dev + i);
420 -               printk(KERN_INFO "input%d: %s on %s\n",
421 -                       db9->dev[i].number, db9_name[db9->mode], db9->pd->port->name);
422 +               printk(KERN_INFO "input: %s on %s\n",
423 +                       db9_name[db9->mode], db9->pd->port->name);
424         }
425  
426         return db9;
427 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/gamecon.c linux-modified/drivers/char/joystick/gamecon.c
428 --- linux-vanilla/drivers/char/joystick/gamecon.c       Thu Sep 13 00:34:06 2001
429 +++ linux-modified/drivers/char/joystick/gamecon.c      Mon Jan  6 16:48:20 2003
430 @@ -608,7 +608,7 @@
431         for (i = 0; i < 5; i++) 
432                 if (gc->pads[0] & gc_status_bit[i]) {
433                         input_register_device(gc->dev + i);
434 -                       printk(KERN_INFO "input%d: %s on %s\n", gc->dev[i].number, gc->dev[i].name, gc->pd->port->name);
435 +                       printk(KERN_INFO "input: %s on %s\n", gc->dev[i].name, gc->pd->port->name);
436                 }
437  
438         return gc;
439 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/gf2k.c linux-modified/drivers/char/joystick/gf2k.c
440 --- linux-vanilla/drivers/char/joystick/gf2k.c  Thu Sep 13 00:34:06 2001
441 +++ linux-modified/drivers/char/joystick/gf2k.c Mon Jan  6 16:48:20 2003
442 @@ -323,8 +323,8 @@
443         }
444  
445         input_register_device(&gf2k->dev);
446 -       printk(KERN_INFO "input%d: %s on gameport%d.0\n",
447 -               gf2k->dev.number, gf2k_names[gf2k->id], gameport->number);
448 +       printk(KERN_INFO "input: %s on gameport%d.0\n",
449 +               gf2k_names[gf2k->id], gameport->number);
450  
451         return;
452  fail2: gameport_close(gameport);
453 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/grip.c linux-modified/drivers/char/joystick/grip.c
454 --- linux-vanilla/drivers/char/joystick/grip.c  Thu Sep 13 00:34:06 2001
455 +++ linux-modified/drivers/char/joystick/grip.c Mon Jan  6 16:48:20 2003
456 @@ -382,8 +382,8 @@
457  
458                         input_register_device(grip->dev + i);
459  
460 -                       printk(KERN_INFO "input%d: %s on gameport%d.%d\n",
461 -                               grip->dev[i].number, grip_name[grip->mode[i]], gameport->number, i);
462 +                       printk(KERN_INFO "input: %s on gameport%d.%d\n",
463 +                               grip_name[grip->mode[i]], gameport->number, i);
464                 }
465  
466         return;
467 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/iforce/Config.help linux-modified/drivers/char/joystick/iforce/Config.help
468 --- linux-vanilla/drivers/char/joystick/iforce/Config.help      Thu Jan  1 02:00:00 1970
469 +++ linux-modified/drivers/char/joystick/iforce/Config.help     Mon Jan  6 16:48:20 2003
470 @@ -0,0 +1,21 @@
471 +CONFIG_JOYSTICK_IFORCE
472 +  Say Y here if you have an I-Force joystick or steering wheel
473 +
474 +  You also must choose at least one of the two options below.
475 +
476 +  This driver is also available as a module ( = code which can be
477 +  inserted in and removed from the running kernel whenever you want).
478 +  The module will be called iforce.o. If you want to compile it as a
479 +  module, say M here and read <file:Documentation/modules.txt>.
480 +
481 +CONFIG_JOYSTICK_IFORCE_USB
482 +  Say Y here if you have an I-Force joystick or steering wheel
483 +  connected to your USB port. 
484 +
485 +CONFIG_JOYSTICK_IFORCE_232
486 +  Say Y here if you have an I-Force joystick or steering wheel
487 +  connected to your serial (COM) port.
488 +
489 +  You will need an additional utility called inputattach, see
490 +  Documentation/input/joystick.txt and ff.txt.
491 +
492 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/iforce/Config.in linux-modified/drivers/char/joystick/iforce/Config.in
493 --- linux-vanilla/drivers/char/joystick/iforce/Config.in        Thu Jan  1 02:00:00 1970
494 +++ linux-modified/drivers/char/joystick/iforce/Config.in       Mon Jan  6 16:48:20 2003
495 @@ -0,0 +1,14 @@
496 +#
497 +# I-Force driver configuration
498 +#
499 +
500 +dep_tristate 'I-Force devices' CONFIG_JOYSTICK_IFORCE $CONFIG_INPUT $CONFIG_INPUT_JOYSTICK
501 +
502 +if [ "$CONFIG_JOYSTICK_IFORCE" = "m" -o "$CONFIG_JOYSTICK_IFORCE" = "y" ]; then
503 +       if [ "$CONFIG_JOYSTICK_IFORCE" = "m" -o "$CONFIG_USB" = "y" ]; then
504 +               dep_mbool '  I-Force USB joysticks and wheels' CONFIG_JOYSTICK_IFORCE_USB $CONFIG_USB
505 +       fi
506 +       if [ "$CONFIG_JOYSTICK_IFORCE" = "m" -o "$CONFIG_INPUT_SERIO" = "y" ]; then
507 +               dep_mbool '  I-Force Serial joysticks and wheels' CONFIG_JOYSTICK_IFORCE_232 $CONFIG_INPUT_SERIO
508 +       fi
509 +fi
510 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/iforce/Makefile linux-modified/drivers/char/joystick/iforce/Makefile
511 --- linux-vanilla/drivers/char/joystick/iforce/Makefile Thu Jan  1 02:00:00 1970
512 +++ linux-modified/drivers/char/joystick/iforce/Makefile        Mon Jan  6 16:48:20 2003
513 @@ -0,0 +1,30 @@
514 +#
515 +# Makefile for the I-Force driver
516 +#
517 +# By Johann Deneux <deneux@ifrance.com>
518 +#
519 +
520 +# Goal definition
521 +list-multi     := iforce.o
522 +iforce-objs    := iforce-ff.o iforce-main.o iforce-packets.o
523 +
524 +obj-$(CONFIG_JOYSTICK_IFORCE)  += iforce.o 
525 +
526 +ifeq ($(CONFIG_JOYSTICK_IFORCE_232),y)
527 +       iforce-objs += iforce-serio.o 
528 +endif
529 +
530 +ifeq ($(CONFIG_JOYSTICK_IFORCE_USB),y)
531 +       iforce-objs += iforce-usb.o 
532 +endif
533 +
534 +EXTRA_CFLAGS = -Werror-implicit-function-declaration
535 +
536 +# The global Rules.make.
537 +
538 +include $(TOPDIR)/Rules.make
539 +
540 +# Additional rules
541 +iforce.o: $(iforce-objs)
542 +       $(LD) -r -o $@ $(iforce-objs)
543 +
544 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/iforce/iforce-ff.c linux-modified/drivers/char/joystick/iforce/iforce-ff.c
545 --- linux-vanilla/drivers/char/joystick/iforce/iforce-ff.c      Thu Jan  1 02:00:00 1970
546 +++ linux-modified/drivers/char/joystick/iforce/iforce-ff.c     Mon Jan  6 16:48:20 2003
547 @@ -0,0 +1,544 @@
548 +/*
549 + * $Id$
550 + *
551 + *  Copyright (c) 2000-2002 Vojtech Pavlik <vojtech@ucw.cz>
552 + *  Copyright (c) 2001-2002 Johann Deneux <deneux@ifrance.com>
553 + *
554 + *  USB/RS232 I-Force joysticks and wheels.
555 + */
556 +
557 +/*
558 + * This program is free software; you can redistribute it and/or modify
559 + * it under the terms of the GNU General Public License as published by
560 + * the Free Software Foundation; either version 2 of the License, or
561 + * (at your option) any later version.
562 + *
563 + * This program is distributed in the hope that it will be useful,
564 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
565 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
566 + * GNU General Public License for more details.
567 + *
568 + * You should have received a copy of the GNU General Public License
569 + * along with this program; if not, write to the Free Software
570 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
571 + *
572 + * Should you need to contact me, the author, you can do so either by
573 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
574 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
575 + */
576 +
577 +#include "iforce.h"
578 +
579 +/*
580 + * Set the magnitude of a constant force effect
581 + * Return error code
582 + *
583 + * Note: caller must ensure exclusive access to device
584 + */
585 +
586 +static int make_magnitude_modifier(struct iforce* iforce,
587 +       struct resource* mod_chunk, int no_alloc, __s16 level)
588 +{
589 +       unsigned char data[3];
590 +
591 +       if (!no_alloc) {
592 +               down(&iforce->mem_mutex);
593 +               if (allocate_resource(&(iforce->device_memory), mod_chunk, 2,
594 +                       iforce->device_memory.start, iforce->device_memory.end, 2L,
595 +                       NULL, NULL)) {
596 +                       up(&iforce->mem_mutex);
597 +                       return -ENOMEM;
598 +               }
599 +               up(&iforce->mem_mutex);
600 +       }
601 +
602 +       data[0] = LO(mod_chunk->start);
603 +       data[1] = HI(mod_chunk->start);
604 +       data[2] = HIFIX80(level);
605 +
606 +       iforce_send_packet(iforce, FF_CMD_MAGNITUDE, data);
607 +
608 +//     iforce_dump_packet("magnitude: ", FF_CMD_MAGNITUDE, data);
609 +       return 0;
610 +}
611 +
612 +/*
613 + * Upload the component of an effect dealing with the period, phase and magnitude
614 + */
615 +
616 +static int make_period_modifier(struct iforce* iforce,
617 +       struct resource* mod_chunk, int no_alloc,
618 +       __s16 magnitude, __s16 offset, u16 period, u16 phase)
619 +{
620 +       unsigned char data[7];
621 +
622 +       period = TIME_SCALE(period);
623 +
624 +       if (!no_alloc) {
625 +               down(&iforce->mem_mutex);
626 +               if (allocate_resource(&(iforce->device_memory), mod_chunk, 0x0c,
627 +                       iforce->device_memory.start, iforce->device_memory.end, 2L,
628 +                       NULL, NULL)) {
629 +                       up(&iforce->mem_mutex);
630 +                       return -ENOMEM;
631 +               }
632 +               up(&iforce->mem_mutex);
633 +       }
634 +
635 +       data[0] = LO(mod_chunk->start);
636 +       data[1] = HI(mod_chunk->start);
637 +
638 +       data[2] = HIFIX80(magnitude);
639 +       data[3] = HIFIX80(offset);
640 +       data[4] = HI(phase);
641 +
642 +       data[5] = LO(period);
643 +       data[6] = HI(period);
644 +
645 +       iforce_send_packet(iforce, FF_CMD_PERIOD, data);
646 +
647 +       return 0;
648 +}
649 +
650 +/*
651 + * Uploads the part of an effect setting the envelope of the force
652 + */
653 +
654 +static int make_envelope_modifier(struct iforce* iforce,
655 +       struct resource* mod_chunk, int no_alloc,
656 +       u16 attack_duration, __s16 initial_level,
657 +       u16 fade_duration, __s16 final_level)
658 +{
659 +       unsigned char data[8];
660 +
661 +       attack_duration = TIME_SCALE(attack_duration);
662 +       fade_duration = TIME_SCALE(fade_duration);
663 +
664 +       if (!no_alloc) {
665 +               down(&iforce->mem_mutex);
666 +               if (allocate_resource(&(iforce->device_memory), mod_chunk, 0x0e,
667 +                       iforce->device_memory.start, iforce->device_memory.end, 2L,
668 +                       NULL, NULL)) {
669 +                       up(&iforce->mem_mutex);
670 +                       return -ENOMEM;
671 +               }
672 +               up(&iforce->mem_mutex);
673 +       }
674 +
675 +       data[0] = LO(mod_chunk->start);
676 +       data[1] = HI(mod_chunk->start);
677 +
678 +       data[2] = LO(attack_duration);
679 +       data[3] = HI(attack_duration);
680 +       data[4] = HI(initial_level);
681 +
682 +       data[5] = LO(fade_duration);
683 +       data[6] = HI(fade_duration);
684 +       data[7] = HI(final_level);
685 +
686 +       iforce_send_packet(iforce, FF_CMD_ENVELOPE, data);
687 +
688 +       return 0;
689 +}
690 +
691 +/*
692 + * Component of spring, friction, inertia... effects
693 + */
694 +
695 +static int make_condition_modifier(struct iforce* iforce,
696 +       struct resource* mod_chunk, int no_alloc,
697 +       __u16 rsat, __u16 lsat, __s16 rk, __s16 lk, u16 db, __s16 center)
698 +{
699 +       unsigned char data[10];
700 +
701 +       if (!no_alloc) {
702 +               down(&iforce->mem_mutex);
703 +               if (allocate_resource(&(iforce->device_memory), mod_chunk, 8,
704 +                       iforce->device_memory.start, iforce->device_memory.end, 2L,
705 +                       NULL, NULL)) {
706 +                       up(&iforce->mem_mutex);
707 +                       return -ENOMEM;
708 +               }
709 +               up(&iforce->mem_mutex);
710 +       }
711 +
712 +       data[0] = LO(mod_chunk->start);
713 +       data[1] = HI(mod_chunk->start);
714 +
715 +       data[2] = (100*rk)>>15; /* Dangerous: the sign is extended by gcc on plateforms providing an arith shift */
716 +       data[3] = (100*lk)>>15; /* This code is incorrect on cpus lacking arith shift */
717 +
718 +       center = (500*center)>>15;
719 +       data[4] = LO(center);
720 +       data[5] = HI(center);
721 +
722 +       db = (1000*db)>>16;
723 +       data[6] = LO(db);
724 +       data[7] = HI(db);
725 +
726 +       data[8] = (100*rsat)>>16;
727 +       data[9] = (100*lsat)>>16;
728 +
729 +       iforce_send_packet(iforce, FF_CMD_CONDITION, data);
730 +//     iforce_dump_packet("condition", FF_CMD_CONDITION, data);
731 +
732 +       return 0;
733 +}
734 +
735 +static unsigned char find_button(struct iforce *iforce, signed short button)
736 +{
737 +       int i;
738 +       for (i = 1; iforce->type->btn[i] >= 0; i++)
739 +               if (iforce->type->btn[i] == button)
740 +                       return i + 1;
741 +       return 0;
742 +}
743 +
744 +/*
745 + * Analyse the changes in an effect, and tell if we need to send an condition 
746 + * parameter packet
747 + */
748 +static int need_condition_modifier(struct iforce* iforce, struct ff_effect* new)
749 +{
750 +       int id = new->id;
751 +       struct ff_effect* old = &iforce->core_effects[id].effect;
752 +       int ret=0;
753 +       int i;
754 +
755 +       if (new->type != FF_SPRING && new->type != FF_FRICTION) {
756 +               printk(KERN_WARNING "iforce.c: bad effect type in need_condition_modifier\n");
757 +               return FALSE;
758 +       }
759 +
760 +       for(i=0; i<2; i++) {
761 +               ret |= old->u.condition[i].right_saturation != new->u.condition[i].right_saturation
762 +                       || old->u.condition[i].left_saturation != new->u.condition[i].left_saturation
763 +                       || old->u.condition[i].right_coeff != new->u.condition[i].right_coeff
764 +                       || old->u.condition[i].left_coeff != new->u.condition[i].left_coeff
765 +                       || old->u.condition[i].deadband != new->u.condition[i].deadband
766 +                       || old->u.condition[i].center != new->u.condition[i].center;
767 +       }
768 +       return ret;
769 +}
770 +
771 +/*
772 + * Analyse the changes in an effect, and tell if we need to send a magnitude
773 + * parameter packet
774 + */
775 +static int need_magnitude_modifier(struct iforce* iforce, struct ff_effect* effect)
776 +{
777 +       int id = effect->id;
778 +       struct ff_effect* old = &iforce->core_effects[id].effect;
779 +
780 +       if (effect->type != FF_CONSTANT) {
781 +               printk(KERN_WARNING "iforce.c: bad effect type in need_envelope_modifier\n");
782 +               return FALSE;
783 +       }
784 +
785 +       return (old->u.constant.level != effect->u.constant.level);
786 +}
787 +
788 +/*
789 + * Analyse the changes in an effect, and tell if we need to send an envelope
790 + * parameter packet
791 + */
792 +static int need_envelope_modifier(struct iforce* iforce, struct ff_effect* effect)
793 +{
794 +       int id = effect->id;
795 +       struct ff_effect* old = &iforce->core_effects[id].effect;
796 +
797 +       switch (effect->type) {
798 +       case FF_CONSTANT:
799 +               if (old->u.constant.envelope.attack_length != effect->u.constant.envelope.attack_length
800 +               || old->u.constant.envelope.attack_level != effect->u.constant.envelope.attack_level
801 +               || old->u.constant.envelope.fade_length != effect->u.constant.envelope.fade_length
802 +               || old->u.constant.envelope.fade_level != effect->u.constant.envelope.fade_level)
803 +                       return TRUE;
804 +               break;
805 +
806 +       case FF_PERIODIC:
807 +               if (old->u.periodic.envelope.attack_length != effect->u.periodic.envelope.attack_length
808 +               || old->u.periodic.envelope.attack_level != effect->u.periodic.envelope.attack_level
809 +               || old->u.periodic.envelope.fade_length != effect->u.periodic.envelope.fade_length
810 +               || old->u.periodic.envelope.fade_level != effect->u.periodic.envelope.fade_level)
811 +                       return TRUE;
812 +               break;
813 +
814 +       default:
815 +               printk(KERN_WARNING "iforce.c: bad effect type in need_envelope_modifier\n");
816 +       }
817 +
818 +       return FALSE;
819 +}
820 +
821 +/*
822 + * Analyse the changes in an effect, and tell if we need to send a periodic
823 + * parameter effect
824 + */
825 +static int need_period_modifier(struct iforce* iforce, struct ff_effect* new)
826 +{
827 +       int id = new->id;
828 +       struct ff_effect* old = &iforce->core_effects[id].effect;
829 +
830 +       if (new->type != FF_PERIODIC) {
831 +               printk(KERN_WARNING "iforce.c: bad effect type in need_periodic_modifier\n");
832 +               return FALSE;
833 +       }
834 +
835 +       return (old->u.periodic.period != new->u.periodic.period
836 +               || old->u.periodic.magnitude != new->u.periodic.magnitude
837 +               || old->u.periodic.offset != new->u.periodic.offset
838 +               || old->u.periodic.phase != new->u.periodic.phase);
839 +}
840 +
841 +/*
842 + * Analyse the changes in an effect, and tell if we need to send an effect
843 + * packet
844 + */
845 +static int need_core(struct iforce* iforce, struct ff_effect* new)
846 +{
847 +       int id = new->id;
848 +       struct ff_effect* old = &iforce->core_effects[id].effect;
849 +
850 +       if (old->direction != new->direction
851 +               || old->trigger.button != new->trigger.button
852 +               || old->trigger.interval != new->trigger.interval
853 +               || old->replay.length != new->replay.length
854 +               || old->replay.delay != new->replay.delay)
855 +               return TRUE;
856 +
857 +       return FALSE;
858 +}
859 +/*
860 + * Send the part common to all effects to the device
861 + */
862 +static int make_core(struct iforce* iforce, u16 id, u16 mod_id1, u16 mod_id2,
863 +       u8 effect_type, u8 axes, u16 duration, u16 delay, u16 button,
864 +       u16 interval, u16 direction)
865 +{
866 +       unsigned char data[14];
867 +
868 +       duration = TIME_SCALE(duration);
869 +       delay    = TIME_SCALE(delay);
870 +       interval = TIME_SCALE(interval);
871 +
872 +       data[0]  = LO(id);
873 +       data[1]  = effect_type;
874 +       data[2]  = LO(axes) | find_button(iforce, button);
875 +
876 +       if (!duration) duration = 0xFFFF;
877 +       data[3]  = LO(duration);
878 +       data[4]  = HI(duration);
879 +
880 +       data[5]  = HI(direction);
881 +
882 +       data[6]  = LO(interval);
883 +       data[7]  = HI(interval);
884 +
885 +       data[8]  = LO(mod_id1);
886 +       data[9]  = HI(mod_id1);
887 +       data[10] = LO(mod_id2);
888 +       data[11] = HI(mod_id2);
889 +
890 +       data[12] = LO(delay);
891 +       data[13] = HI(delay);
892 +
893 +       /* Stop effect */
894 +/*     iforce_control_playback(iforce, id, 0);*/
895 +
896 +       iforce_send_packet(iforce, FF_CMD_EFFECT, data);
897 +
898 +       /* If needed, restart effect */
899 +       if (test_bit(FF_CORE_SHOULD_PLAY, iforce->core_effects[id].flags)) {
900 +               /* BUG: perhaps we should replay n times, instead of 1. But we do not know n */
901 +               iforce_control_playback(iforce, id, 1);
902 +       }
903 +
904 +       return 0;
905 +}
906 +
907 +/*
908 + * Upload a periodic effect to the device
909 + * See also iforce_upload_constant.
910 + */
911 +int iforce_upload_periodic(struct iforce* iforce, struct ff_effect* effect, int is_update)
912 +{
913 +       u8 wave_code;
914 +       int core_id = effect->id;
915 +       struct iforce_core_effect* core_effect = iforce->core_effects + core_id;
916 +       struct resource* mod1_chunk = &(iforce->core_effects[core_id].mod1_chunk);
917 +       struct resource* mod2_chunk = &(iforce->core_effects[core_id].mod2_chunk);
918 +       int param1_err = 1;
919 +       int param2_err = 1;
920 +       int core_err = 0;
921 +
922 +       if (!is_update || need_period_modifier(iforce, effect)) {
923 +               param1_err = make_period_modifier(iforce, mod1_chunk, 
924 +                       is_update,
925 +                       effect->u.periodic.magnitude, effect->u.periodic.offset,
926 +                       effect->u.periodic.period, effect->u.periodic.phase);
927 +               if (param1_err) return param1_err;
928 +               set_bit(FF_MOD1_IS_USED, core_effect->flags);
929 +       }
930 +
931 +       if (!is_update || need_envelope_modifier(iforce, effect)) {
932 +               param2_err = make_envelope_modifier(iforce, mod2_chunk,
933 +                       is_update,
934 +                       effect->u.periodic.envelope.attack_length,
935 +                       effect->u.periodic.envelope.attack_level,
936 +                       effect->u.periodic.envelope.fade_length,
937 +                       effect->u.periodic.envelope.fade_level);
938 +               if (param2_err) return param2_err;
939 +               set_bit(FF_MOD2_IS_USED, core_effect->flags);
940 +       }
941 +
942 +       switch (effect->u.periodic.waveform) {
943 +               case FF_SQUARE:         wave_code = 0x20; break;
944 +               case FF_TRIANGLE:       wave_code = 0x21; break;
945 +               case FF_SINE:           wave_code = 0x22; break;
946 +               case FF_SAW_UP:         wave_code = 0x23; break;
947 +               case FF_SAW_DOWN:       wave_code = 0x24; break;
948 +               default:                wave_code = 0x20; break;
949 +       }
950 +
951 +       if (!is_update || need_core(iforce, effect)) {
952 +               core_err = make_core(iforce, effect->id,
953 +                       mod1_chunk->start,
954 +                       mod2_chunk->start,
955 +                       wave_code,
956 +                       0x20,
957 +                       effect->replay.length,
958 +                       effect->replay.delay,
959 +                       effect->trigger.button,
960 +                       effect->trigger.interval,
961 +                       effect->direction);
962 +       }
963 +
964 +       /* If one of the parameter creation failed, we already returned an
965 +        * error code.
966 +        * If the core creation failed, we return its error code.
967 +        * Else: if one parameter at least was created, we return 0
968 +        *       else we return 1;
969 +        */
970 +       return core_err < 0 ? core_err : (param1_err && param2_err);
971 +}
972 +
973 +/*
974 + * Upload a constant force effect
975 + * Return value:
976 + *  <0 Error code
977 + *  0 Ok, effect created or updated
978 + *  1 effect did not change since last upload, and no packet was therefore sent
979 + */
980 +int iforce_upload_constant(struct iforce* iforce, struct ff_effect* effect, int is_update)
981 +{
982 +       int core_id = effect->id;
983 +       struct iforce_core_effect* core_effect = iforce->core_effects + core_id;
984 +       struct resource* mod1_chunk = &(iforce->core_effects[core_id].mod1_chunk);
985 +       struct resource* mod2_chunk = &(iforce->core_effects[core_id].mod2_chunk);
986 +       int param1_err = 1;
987 +       int param2_err = 1;
988 +       int core_err = 0;
989 +
990 +       if (!is_update || need_magnitude_modifier(iforce, effect)) {
991 +               param1_err = make_magnitude_modifier(iforce, mod1_chunk,
992 +                       is_update,
993 +                       effect->u.constant.level);
994 +               if (param1_err) return param1_err;
995 +               set_bit(FF_MOD1_IS_USED, core_effect->flags);
996 +       }
997 +
998 +       if (!is_update || need_envelope_modifier(iforce, effect)) {
999 +               param2_err = make_envelope_modifier(iforce, mod2_chunk,
1000 +                       is_update,
1001 +                       effect->u.constant.envelope.attack_length,
1002 +                       effect->u.constant.envelope.attack_level,
1003 +                       effect->u.constant.envelope.fade_length,
1004 +                       effect->u.constant.envelope.fade_level);
1005 +               if (param2_err) return param2_err;
1006 +               set_bit(FF_MOD2_IS_USED, core_effect->flags);
1007 +       }
1008 +
1009 +       if (!is_update || need_core(iforce, effect)) {
1010 +               core_err = make_core(iforce, effect->id,
1011 +                       mod1_chunk->start,
1012 +                       mod2_chunk->start,
1013 +                       0x00,
1014 +                       0x20,
1015 +                       effect->replay.length,
1016 +                       effect->replay.delay,
1017 +                       effect->trigger.button,
1018 +                       effect->trigger.interval,
1019 +                       effect->direction);
1020 +       }
1021 +
1022 +       /* If one of the parameter creation failed, we already returned an
1023 +        * error code.
1024 +        * If the core creation failed, we return its error code.
1025 +        * Else: if one parameter at least was created, we return 0
1026 +        *       else we return 1;
1027 +        */
1028 +       return core_err < 0 ? core_err : (param1_err && param2_err);
1029 +}
1030 +
1031 +/*
1032 + * Upload an condition effect. Those are for example friction, inertia, springs...
1033 + */
1034 +int iforce_upload_condition(struct iforce* iforce, struct ff_effect* effect, int is_update)
1035 +{
1036 +       int core_id = effect->id;
1037 +       struct iforce_core_effect* core_effect = iforce->core_effects + core_id;
1038 +       struct resource* mod1_chunk = &(core_effect->mod1_chunk);
1039 +       struct resource* mod2_chunk = &(core_effect->mod2_chunk);
1040 +       u8 type;
1041 +       int param_err = 1;
1042 +       int core_err = 0;
1043 +
1044 +       switch (effect->type) {
1045 +               case FF_SPRING:         type = 0x40; break;
1046 +               case FF_DAMPER:         type = 0x41; break;
1047 +               default: return -1;
1048 +       }
1049 +
1050 +       if (!is_update || need_condition_modifier(iforce, effect)) {
1051 +               param_err = make_condition_modifier(iforce, mod1_chunk,
1052 +                       is_update,
1053 +                       effect->u.condition[0].right_saturation,
1054 +                       effect->u.condition[0].left_saturation,
1055 +                       effect->u.condition[0].right_coeff,
1056 +                       effect->u.condition[0].left_coeff,
1057 +                       effect->u.condition[0].deadband,
1058 +                       effect->u.condition[0].center);
1059 +               if (param_err) return param_err;
1060 +               set_bit(FF_MOD1_IS_USED, core_effect->flags);
1061 +
1062 +               param_err = make_condition_modifier(iforce, mod2_chunk,
1063 +                       is_update,
1064 +                       effect->u.condition[1].right_saturation,
1065 +                       effect->u.condition[1].left_saturation,
1066 +                       effect->u.condition[1].right_coeff,
1067 +                       effect->u.condition[1].left_coeff,
1068 +                       effect->u.condition[1].deadband,
1069 +                       effect->u.condition[1].center);
1070 +               if (param_err) return param_err;
1071 +               set_bit(FF_MOD2_IS_USED, core_effect->flags);
1072 +
1073 +       }
1074 +
1075 +       if (!is_update || need_core(iforce, effect)) {
1076 +               core_err = make_core(iforce, effect->id,
1077 +                       mod1_chunk->start, mod2_chunk->start,
1078 +                       type, 0xc0,
1079 +                       effect->replay.length, effect->replay.delay,
1080 +                       effect->trigger.button, effect->trigger.interval,
1081 +                       effect->direction);
1082 +       }
1083 +
1084 +       /* If the parameter creation failed, we already returned an
1085 +        * error code.
1086 +        * If the core creation failed, we return its error code.
1087 +        * Else: if a parameter  was created, we return 0
1088 +        *       else we return 1;
1089 +        */
1090 +       return core_err < 0 ? core_err : param_err;
1091 +}
1092 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/iforce/iforce-main.c linux-modified/drivers/char/joystick/iforce/iforce-main.c
1093 --- linux-vanilla/drivers/char/joystick/iforce/iforce-main.c    Thu Jan  1 02:00:00 1970
1094 +++ linux-modified/drivers/char/joystick/iforce/iforce-main.c   Wed Feb 26 20:36:04 2003
1095 @@ -0,0 +1,562 @@
1096 +/*
1097 + * $Id$
1098 + *
1099 + *  Copyright (c) 2000-2002 Vojtech Pavlik <vojtech@ucw.cz>
1100 + *  Copyright (c) 2001-2002 Johann Deneux <deneux@ifrance.com>
1101 + *
1102 + *  USB/RS232 I-Force joysticks and wheels.
1103 + */
1104 +
1105 +/*
1106 + * This program is free software; you can redistribute it and/or modify
1107 + * it under the terms of the GNU General Public License as published by
1108 + * the Free Software Foundation; either version 2 of the License, or
1109 + * (at your option) any later version.
1110 + *
1111 + * This program is distributed in the hope that it will be useful,
1112 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
1113 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
1114 + * GNU General Public License for more details.
1115 + *
1116 + * You should have received a copy of the GNU General Public License
1117 + * along with this program; if not, write to the Free Software
1118 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
1119 + *
1120 + * Should you need to contact me, the author, you can do so either by
1121 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
1122 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
1123 + */
1124 +
1125 +#include "iforce.h"
1126 +
1127 +MODULE_AUTHOR("Vojtech Pavlik <vojtech@ucw.cz>, Johann Deneux <deneux@ifrance.com>");
1128 +MODULE_DESCRIPTION("USB/RS232 I-Force joysticks and wheels driver");
1129 +MODULE_LICENSE("GPL");
1130 +
1131 +#define  USB_VENDOR_ID_SAITEK 0x06a3
1132 +#define  USB_PRODUCT_ID_CYBORGFORCE 0xff12
1133 +               
1134 +
1135 +static signed short btn_joystick[] =
1136 +{ BTN_TRIGGER, BTN_TOP, BTN_THUMB, BTN_TOP2, BTN_BASE,
1137 +  BTN_BASE2, BTN_BASE3, BTN_BASE4, BTN_BASE5, BTN_A, BTN_B, BTN_C, -1 };
1138 +
1139 +static signed short btn_avb_pegasus[] =
1140 +{ BTN_TRIGGER, BTN_TOP, BTN_THUMB, BTN_TOP2, BTN_BASE,
1141 +  BTN_BASE2, BTN_BASE3, BTN_BASE4, -1 };
1142 +
1143 +static signed short btn_wheel[] =
1144 +{ BTN_TRIGGER, BTN_TOP, BTN_THUMB, BTN_TOP2, BTN_BASE,
1145 +  BTN_BASE2, BTN_BASE3, BTN_BASE4, BTN_BASE5, BTN_A, BTN_B, BTN_C, -1 };
1146 +
1147 +static signed short btn_avb_tw[] =
1148 +{ BTN_TRIGGER, BTN_THUMB, BTN_TOP, BTN_TOP2, BTN_BASE,
1149 +  BTN_BASE2, BTN_BASE3, BTN_BASE4, -1 };
1150 +
1151 +static signed short btn_avb_wheel[] =
1152 +{ BTN_GEAR_DOWN, BTN_GEAR_UP, BTN_BASE, BTN_BASE2, BTN_BASE3,
1153 +  BTN_BASE4, BTN_BASE5, BTN_BASE6, -1 };
1154 +
1155 +static signed short abs_joystick[] =
1156 +{ ABS_X, ABS_Y, ABS_THROTTLE, ABS_HAT0X, ABS_HAT0Y, -1 };
1157 +
1158 +static signed short abs_avb_pegasus[] =
1159 +{ ABS_X, ABS_Y, ABS_THROTTLE, ABS_RUDDER, ABS_HAT0X, ABS_HAT0Y,
1160 +  ABS_HAT1X, ABS_HAT1Y, -1 };
1161 +
1162 +static signed short abs_wheel[] =
1163 +{ ABS_WHEEL, ABS_GAS, ABS_BRAKE, ABS_HAT0X, ABS_HAT0Y, -1 };
1164 +
1165 +static signed short btn_saitek_joystick[] = 
1166 +{ BTN_TRIGGER, BTN_TOP2, BTN_THUMB,BTN_THUMB2, BTN_TOP,
1167 +       BTN_BASE, BTN_BASE2, BTN_BASE4, BTN_BASE3, -1 };
1168 +
1169 +static signed short abs_saitek_joystick[] = 
1170 +{ ABS_X, ABS_Y, ABS_THROTTLE, ABS_RUDDER,ABS_HAT0X, ABS_HAT0Y, -1 };
1171 +
1172 +
1173 +
1174 +static signed short ff_iforce[] =
1175 +{ FF_PERIODIC, FF_CONSTANT, FF_SPRING, FF_DAMPER,
1176 +  FF_SQUARE, FF_TRIANGLE, FF_SINE, FF_SAW_UP, FF_SAW_DOWN, FF_GAIN,
1177 +  FF_AUTOCENTER, -1 };
1178 +
1179 +static struct iforce_device iforce_device[] = {
1180 +       { 0x044f, 0xa01c, "Thrustmaster Motor Sport GT",                btn_wheel, abs_wheel, ff_iforce },
1181 +       { 0x046d, 0xc281, "Logitech WingMan Force",                     btn_joystick, abs_joystick, ff_iforce },
1182 +       { 0x046d, 0xc291, "Logitech WingMan Formula Force",             btn_wheel, abs_wheel, ff_iforce },
1183 +       { 0x05ef, 0x020a, "AVB Top Shot Pegasus",                       btn_avb_pegasus, abs_avb_pegasus, ff_iforce },
1184 +       { 0x05ef, 0x8884, "AVB Mag Turbo Force",                        btn_avb_wheel, abs_wheel, ff_iforce },
1185 +       { 0x05ef, 0x8888, "AVB Top Shot Force Feedback Racing Wheel",   btn_avb_tw, abs_wheel, ff_iforce }, //?
1186 +       { 0x061c, 0xc084, "ACT LABS Force RS",                          btn_wheel, abs_wheel, ff_iforce }, //?
1187 +       { 0x06f8, 0x0001, "Guillemot Race Leader Force Feedback",       btn_wheel, abs_wheel, ff_iforce }, //?
1188 +       { 0x06f8, 0x0004, "Guillemot Force Feedback Racing Wheel",      btn_wheel, abs_wheel, ff_iforce }, //?
1189 +       { 0x06a3, 0xff12, "Saitek Cyborgforce",                         btn_saitek_joystick, abs_saitek_joystick, ff_iforce },
1190 +       { 0x0000, 0x0000, "Unknown I-Force Device [%04x:%04x]",         btn_joystick, abs_joystick, ff_iforce }
1191 +};
1192 +
1193 +
1194 +
1195 +static int iforce_input_event(struct input_dev *dev, unsigned int type, unsigned int code, int value)
1196 +{
1197 +       struct iforce* iforce = (struct iforce*)(dev->private);
1198 +       unsigned char data[3];
1199 +
1200 +       if (type != EV_FF)
1201 +               return -1;
1202 +
1203 +       switch (code) {
1204 +
1205 +               case FF_GAIN:
1206 +
1207 +                       data[0] = value >> 9;
1208 +                       iforce_send_packet(iforce, FF_CMD_GAIN, data);
1209 +
1210 +                       return 0;
1211 +
1212 +               case FF_AUTOCENTER:
1213 +
1214 +                       data[0] = 0x03;
1215 +                       data[1] = value >> 9;
1216 +                       iforce_send_packet(iforce, FF_CMD_AUTOCENTER, data);
1217 +
1218 +                       data[0] = 0x04;
1219 +                       data[1] = 0x01;
1220 +                       iforce_send_packet(iforce, FF_CMD_AUTOCENTER, data);
1221 +
1222 +                       return 0;
1223 +
1224 +               default: /* Play or stop an effect */
1225 +
1226 +                       if (value > 0) {
1227 +                               set_bit(FF_CORE_SHOULD_PLAY, iforce->core_effects[code].flags);
1228 +                       }
1229 +                       else {
1230 +                               clear_bit(FF_CORE_SHOULD_PLAY, iforce->core_effects[code].flags);
1231 +                       }
1232 +
1233 +                       iforce_control_playback(iforce, code, value);
1234 +                       return 0;
1235 +       }
1236 +
1237 +       return -1;
1238 +}
1239 +
1240 +/*
1241 + * Function called when an ioctl is performed on the event dev entry.
1242 + * It uploads an effect to the device
1243 + */
1244 +static int iforce_upload_effect(struct input_dev *dev, struct ff_effect *effect)
1245 +{
1246 +       struct iforce* iforce = (struct iforce*)(dev->private);
1247 +       int id;
1248 +       int ret;
1249 +       int is_update;
1250 +
1251 +/* Check this effect type is supported by this device */
1252 +       if (!test_bit(effect->type, iforce->dev.ffbit))
1253 +               return -EINVAL;
1254 +
1255 +/*
1256 + * If we want to create a new effect, get a free id
1257 + */
1258 +       if (effect->id == -1) {
1259 +
1260 +               for (id=0; id < FF_EFFECTS_MAX; ++id)
1261 +                       if (!test_and_set_bit(FF_CORE_IS_USED, iforce->core_effects[id].flags)) break;
1262 +
1263 +               if ( id == FF_EFFECTS_MAX || id >= iforce->dev.ff_effects_max)
1264 +                       return -ENOMEM;
1265 +
1266 +               effect->id = id;
1267 +               iforce->core_effects[id].owner = current->pid;
1268 +               iforce->core_effects[id].flags[0] = (1<<FF_CORE_IS_USED);       /* Only IS_USED bit must be set */
1269 +
1270 +               is_update = FALSE;
1271 +       }
1272 +       else {
1273 +               /* We want to update an effect */
1274 +               /* Parameter type cannot be updated */
1275 +               if (effect->type != iforce->core_effects[effect->id].effect.type)
1276 +                       return -EINVAL;
1277 +
1278 +               /* Check the effect is not already being updated */
1279 +               if (test_bit(FF_CORE_UPDATE, iforce->core_effects[effect->id].flags)) {
1280 +                       return -EAGAIN;
1281 +               }
1282 +
1283 +               is_update = TRUE;
1284 +       }
1285 +
1286 +/*
1287 + * Upload the effect
1288 + */
1289 +       switch (effect->type) {
1290 +
1291 +               case FF_PERIODIC:
1292 +                       ret = iforce_upload_periodic(iforce, effect, is_update);
1293 +                       break;
1294 +
1295 +               case FF_CONSTANT:
1296 +                       ret = iforce_upload_constant(iforce, effect, is_update);
1297 +                       break;
1298 +
1299 +               case FF_SPRING:
1300 +               case FF_DAMPER:
1301 +                       ret = iforce_upload_condition(iforce, effect, is_update);
1302 +                       break;
1303 +
1304 +               default:
1305 +                       return -EINVAL;
1306 +       }
1307 +       if (ret == 0) {
1308 +               /* A packet was sent, forbid new updates until we are notified
1309 +                * that the packet was updated
1310 +                */
1311 +               set_bit(FF_CORE_UPDATE, iforce->core_effects[effect->id].flags);
1312 +       }
1313 +       iforce->core_effects[effect->id].effect = *effect;
1314 +       return ret;
1315 +}
1316 +
1317 +/*
1318 + * Erases an effect: it frees the effect id and mark as unused the memory
1319 + * allocated for the parameters
1320 + */
1321 +static int iforce_erase_effect(struct input_dev *dev, int effect_id)
1322 +{
1323 +       struct iforce* iforce = (struct iforce*)(dev->private);
1324 +       int err = 0;
1325 +       struct iforce_core_effect* core_effect;
1326 +
1327 +       if (effect_id < 0 || effect_id >= FF_EFFECTS_MAX)
1328 +               return -EINVAL;
1329 +
1330 +       core_effect = iforce->core_effects + effect_id;
1331 +
1332 +       if (test_bit(FF_MOD1_IS_USED, core_effect->flags))
1333 +               err = release_resource(&(iforce->core_effects[effect_id].mod1_chunk));
1334 +
1335 +       if (!err && test_bit(FF_MOD2_IS_USED, core_effect->flags))
1336 +               err = release_resource(&(iforce->core_effects[effect_id].mod2_chunk));
1337 +
1338 +       /*TODO: remember to change that if more FF_MOD* bits are added */
1339 +       core_effect->flags[0] = 0;
1340 +
1341 +       return err;
1342 +}
1343 +
1344 +static int iforce_open(struct input_dev *dev)
1345 +{
1346 +       struct iforce *iforce = dev->private;
1347 +
1348 +       switch (iforce->bus) {
1349 +#ifdef CONFIG_JOYSTICK_IFORCE_USB
1350 +               case IFORCE_USB:
1351 +                       iforce->irq->dev = iforce->usbdev;
1352 +                       if (usb_submit_urb(iforce->irq))
1353 +                               return -EIO;
1354 +                       break;
1355 +#endif
1356 +       }
1357 +
1358 +       /* Enable force feedback */
1359 +       iforce_send_packet(iforce, FF_CMD_ENABLE, "\004");
1360 +
1361 +       return 0;
1362 +}
1363 +
1364 +static int iforce_flush(struct input_dev *dev, struct file *file)
1365 +{
1366 +       struct iforce *iforce = dev->private;
1367 +       int i;
1368 +
1369 +       /* Erase all effects this process owns */
1370 +       for (i=0; i<dev->ff_effects_max; ++i) {
1371 +
1372 +               if (test_bit(FF_CORE_IS_USED, iforce->core_effects[i].flags) &&
1373 +                       current->pid == iforce->core_effects[i].owner) {
1374 +                       
1375 +                       /* Stop effect */
1376 +                       input_report_ff(dev, i, 0);
1377 +
1378 +                       /* Free ressources assigned to effect */
1379 +                       if (iforce_erase_effect(dev, i)) {
1380 +                               printk(KERN_WARNING "iforce_flush: erase effect %d failed\n", i);
1381 +                       }
1382 +               }
1383 +
1384 +       }
1385 +       return 0;
1386 +}
1387 +
1388 +static void iforce_release(struct input_dev *dev)
1389 +{
1390 +       struct iforce *iforce = dev->private;
1391 +       int i;
1392 +
1393 +       /* Check: no effect should be present in memory */
1394 +       for (i=0; i<dev->ff_effects_max; ++i) {
1395 +               if (test_bit(FF_CORE_IS_USED, iforce->core_effects[i].flags))
1396 +                       break;
1397 +       }
1398 +       if (i<dev->ff_effects_max) {
1399 +               printk(KERN_WARNING "iforce_release: Device still owns effects\n");
1400 +       }
1401 +
1402 +       /* Disable force feedback playback */
1403 +       iforce_send_packet(iforce, FF_CMD_ENABLE, "\001");
1404 +
1405 +       switch (iforce->bus) {
1406 +#ifdef CONFIG_JOYSTICK_IFORCE_USB
1407 +               case IFORCE_USB:
1408 +                       usb_unlink_urb(iforce->irq);
1409 +
1410 +                       /* The device was unplugged before the file
1411 +                        * was released */
1412 +                       if (iforce->usbdev == NULL) {
1413 +                               iforce_delete_device(iforce);
1414 +                               kfree(iforce);
1415 +                       }
1416 +               break;
1417 +#endif
1418 +       }
1419 +}
1420 +
1421 +void iforce_delete_device(struct iforce *iforce)
1422 +{
1423 +       switch (iforce->bus) {
1424 +#ifdef CONFIG_JOYSTICK_IFORCE_USB
1425 +       case IFORCE_USB:
1426 +               iforce_usb_delete(iforce);
1427 +               break;
1428 +#endif
1429 +#ifdef CONFIG_JOYSTICK_IFORCE_232
1430 +       case IFORCE_232:
1431 +               //TODO: Wait for the last packets to be sent
1432 +               break;
1433 +#endif
1434 +       }
1435 +}
1436 +
1437 +int iforce_init_device(struct iforce *iforce)
1438 +{
1439 +       unsigned char c[] = "CEOV";
1440 +       int i;
1441 +
1442 +       init_waitqueue_head(&iforce->wait);
1443 +       spin_lock_init(&iforce->xmit_lock);
1444 +       init_MUTEX(&iforce->mem_mutex);
1445 +       iforce->xmit.buf = iforce->xmit_data;
1446 +
1447 +       iforce->dev.ff_effects_max = 10;
1448 +
1449 +/*
1450 + * Input device fields.
1451 + */
1452 +
1453 +       iforce->dev.idbus = BUS_USB;
1454 +       iforce->dev.private = iforce;
1455 +       iforce->dev.name = "Unknown I-Force device";
1456 +       iforce->dev.open = iforce_open;
1457 +       iforce->dev.close = iforce_release;
1458 +       iforce->dev.flush = iforce_flush;
1459 +       iforce->dev.event = iforce_input_event;
1460 +       iforce->dev.upload_effect = iforce_upload_effect;
1461 +       iforce->dev.erase_effect = iforce_erase_effect;
1462 +
1463 +/*
1464 + * On-device memory allocation.
1465 + */
1466 +
1467 +       iforce->device_memory.name = "I-Force device effect memory";
1468 +       iforce->device_memory.start = 0;
1469 +       iforce->device_memory.end = 200;
1470 +       iforce->device_memory.flags = IORESOURCE_MEM;
1471 +       iforce->device_memory.parent = NULL;
1472 +       iforce->device_memory.child = NULL;
1473 +       iforce->device_memory.sibling = NULL;
1474 +
1475 +/*
1476 + * Wait until device ready - until it sends its first response.
1477 + */
1478 +
1479 +       for (i = 0; i < 20; i++)
1480 +               if (!iforce_get_id_packet(iforce, "O"))
1481 +                       break;
1482 +
1483 +       if (i == 20) { /* 5 seconds */
1484 +               printk(KERN_ERR "iforce-main.c: Timeout waiting for response from device.\n");
1485 +               return -1;
1486 +       }
1487 +
1488 +/*
1489 + * Get device info.
1490 + */
1491 +
1492 +       if (!iforce_get_id_packet(iforce, "M"))
1493 +               iforce->dev.idvendor = (iforce->edata[2] << 8) | iforce->edata[1];
1494 +       else
1495 +               printk(KERN_WARNING "iforce-main.c: Device does not respond to id packet M\n");
1496 +
1497 +       if (!iforce_get_id_packet(iforce, "P"))
1498 +               iforce->dev.idproduct = (iforce->edata[2] << 8) | iforce->edata[1];
1499 +       else
1500 +               printk(KERN_WARNING "iforce-main.c: Device does not respond to id packet P\n");
1501 +
1502 +       if (!iforce_get_id_packet(iforce, "B"))
1503 +               iforce->device_memory.end = (iforce->edata[2] << 8) | iforce->edata[1];
1504 +       else
1505 +               printk(KERN_WARNING "iforce-main.c: Device does not respond to id packet B\n");
1506 +
1507 +       if (!iforce_get_id_packet(iforce, "N"))
1508 +               iforce->dev.ff_effects_max = iforce->edata[1];
1509 +       else
1510 +               printk(KERN_WARNING "iforce-main.c: Device does not respond to id packet N\n");
1511 +
1512 +       /* Check if the device can store more effects than the driver can really handle */
1513 +       if (iforce->dev.ff_effects_max > FF_EFFECTS_MAX) {
1514 +               printk(KERN_WARNING "input??: Device can handle %d effects, but N_EFFECTS_MAX is set to %d in iforce.h\n",
1515 +                       iforce->dev.ff_effects_max, FF_EFFECTS_MAX);
1516 +               iforce->dev.ff_effects_max = FF_EFFECTS_MAX;
1517 +       }
1518 +
1519 +/*
1520 + * Display additional info.
1521 + */
1522 +
1523 +       for (i = 0; c[i]; i++)
1524 +               if (!iforce_get_id_packet(iforce, c + i))
1525 +                       iforce_dump_packet("info", iforce->ecmd, iforce->edata);
1526 +
1527 +/*
1528 + * Disable spring, enable force feedback.
1529 + * FIXME: We should use iforce_set_autocenter() et al here.
1530 + */
1531 +
1532 +       iforce_send_packet(iforce, FF_CMD_AUTOCENTER, "\004\000");
1533 +
1534 +/*
1535 + * Find appropriate device entry
1536 + */
1537 +
1538 +       for (i = 0; iforce_device[i].idvendor; i++)
1539 +               if (iforce_device[i].idvendor == iforce->dev.idvendor &&
1540 +                   iforce_device[i].idproduct == iforce->dev.idproduct)
1541 +                       break;
1542 +
1543 +       iforce->type = iforce_device + i;
1544 +       iforce->dev.name = iforce->type->name;
1545 +
1546 +/*
1547 + * Set input device bitfields and ranges.
1548 + */
1549 +
1550 +       iforce->dev.evbit[0] = BIT(EV_KEY) | BIT(EV_ABS) | BIT(EV_FF) | BIT(EV_FF_STATUS);
1551 +
1552 +       for (i = 0; iforce->type->btn[i] >= 0; i++) {
1553 +               signed short t = iforce->type->btn[i];
1554 +               set_bit(t, iforce->dev.keybit);
1555 +       }
1556 +       set_bit(BTN_DEAD, iforce->dev.keybit);
1557 +
1558 +       for (i = 0; iforce->type->abs[i] >= 0; i++) {
1559 +
1560 +               signed short t = iforce->type->abs[i];
1561 +               set_bit(t, iforce->dev.absbit);
1562 +
1563 +               switch (t) {
1564 +
1565 +                       case ABS_X:
1566 +                       case ABS_Y:
1567 +                       case ABS_WHEEL:
1568 +                         if (iforce->dev.idvendor == USB_VENDOR_ID_SAITEK && iforce->dev.idproduct == USB_PRODUCT_ID_CYBORGFORCE)
1569 +                           {
1570 +                             iforce->dev.absmax[t] =  0x1000;
1571 +                             iforce->dev.absmin[t] = 0;
1572 +                           }
1573 +                         else {
1574 +                           iforce->dev.absmax[t] =  1920;
1575 +                           iforce->dev.absmin[t] = -1920;
1576 +                         }
1577 +                         iforce->dev.absflat[t] = 128;
1578 +                         iforce->dev.absfuzz[t] = 16;
1579 +                         set_bit(t, iforce->dev.ffbit);
1580 +                         break;
1581 +
1582 +                       case ABS_THROTTLE:
1583 +                       case ABS_GAS:
1584 +                       case ABS_BRAKE:
1585 +
1586 +                               iforce->dev.absmax[t] = 255;
1587 +                               iforce->dev.absmin[t] = 0;
1588 +                               break;
1589 +
1590 +                       case ABS_RUDDER:
1591 +                         if (iforce->dev.idvendor == USB_VENDOR_ID_SAITEK && iforce->dev.idproduct == USB_PRODUCT_ID_CYBORGFORCE)
1592 +                           {
1593 +                               iforce->dev.absmax[t] = 255;
1594 +                               iforce->dev.absmin[t] = 0;
1595 +                               iforce->dev.absflat[t] = 10;
1596 +                               iforce->dev.absfuzz[t] = 4;
1597 +
1598 +                           }
1599 +                         else
1600 +                           {
1601 +                             iforce->dev.absmax[t] = 127;
1602 +                             iforce->dev.absmin[t] = -128;
1603 +                               
1604 +                           }
1605 +                         break;
1606 +
1607 +                       case ABS_HAT0X:
1608 +                       case ABS_HAT0Y:
1609 +                       case ABS_HAT1X:
1610 +                       case ABS_HAT1Y:
1611 +                               iforce->dev.absmax[t] =  1;
1612 +                               iforce->dev.absmin[t] = -1;
1613 +                               break;
1614 +               }
1615 +       }
1616 +
1617 +       for (i = 0; iforce->type->ff[i] >= 0; i++)
1618 +               set_bit(iforce->type->ff[i], iforce->dev.ffbit);
1619 +
1620 +/*
1621 + * Register input device.
1622 + */
1623 +
1624 +       input_register_device(&iforce->dev);
1625 +
1626 +       printk(KERN_DEBUG "iforce->dev.open = %p\n", iforce->dev.open);
1627 +
1628 +       printk(KERN_INFO "input: %s [%d effects, %ld bytes memory]\n",
1629 +               iforce->dev.name, iforce->dev.ff_effects_max,
1630 +               iforce->device_memory.end);
1631 +
1632 +       return 0;
1633 +}
1634 +
1635 +static int __init iforce_init(void)
1636 +{
1637 +#ifdef CONFIG_JOYSTICK_IFORCE_USB
1638 +       usb_register(&iforce_usb_driver);
1639 +#endif
1640 +#ifdef CONFIG_JOYSTICK_IFORCE_232
1641 +       serio_register_device(&iforce_serio_dev);
1642 +#endif
1643 +       return 0;
1644 +}
1645 +
1646 +static void __exit iforce_exit(void)
1647 +{
1648 +#ifdef CONFIG_JOYSTICK_IFORCE_USB
1649 +       usb_deregister(&iforce_usb_driver);
1650 +#endif
1651 +#ifdef CONFIG_JOYSTICK_IFORCE_232
1652 +       serio_unregister_device(&iforce_serio_dev);
1653 +#endif
1654 +}
1655 +
1656 +module_init(iforce_init);
1657 +module_exit(iforce_exit);
1658 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/iforce/iforce-packets.c linux-modified/drivers/char/joystick/iforce/iforce-packets.c
1659 --- linux-vanilla/drivers/char/joystick/iforce/iforce-packets.c Thu Jan  1 02:00:00 1970
1660 +++ linux-modified/drivers/char/joystick/iforce/iforce-packets.c        Mon Feb 17 21:28:41 2003
1661 @@ -0,0 +1,320 @@
1662 +/*
1663 + * $Id$
1664 + *
1665 + *  Copyright (c) 2000-2002 Vojtech Pavlik <vojtech@ucw.cz>
1666 + *  Copyright (c) 2001-2002 Johann Deneux <deneux@ifrance.com>
1667 + *
1668 + *  USB/RS232 I-Force joysticks and wheels.
1669 + */
1670 +
1671 +/*
1672 + * This program is free software; you can redistribute it and/or modify
1673 + * it under the terms of the GNU General Public License as published by
1674 + * the Free Software Foundation; either version 2 of the License, or
1675 + * (at your option) any later version.
1676 + *
1677 + * This program is distributed in the hope that it will be useful,
1678 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
1679 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
1680 + * GNU General Public License for more details.
1681 + *
1682 + * You should have received a copy of the GNU General Public License
1683 + * along with this program; if not, write to the Free Software
1684 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
1685 + *
1686 + * Should you need to contact me, the author, you can do so either by
1687 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
1688 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
1689 + */
1690 +
1691 +#include "iforce.h"
1692 +
1693 +static struct {
1694 +       __s32 x;
1695 +       __s32 y;
1696 +} iforce_hat_to_axis[16] = {{ 0,-1}, { 1,-1}, { 1, 0}, { 1, 1}, { 0, 1}, {-1, 1}, {-1, 0}, {-1,-1}};
1697 +
1698 +
1699 +void iforce_dump_packet(char *msg, u16 cmd, unsigned char *data)
1700 +{
1701 +       int i;
1702 +
1703 +       printk(KERN_DEBUG "iforce.c: %s ( cmd = %04x, data = ", msg, cmd);
1704 +       for (i = 0; i < LO(cmd); i++)
1705 +               printk("%02x ", data[i]);
1706 +       printk(")\n");
1707 +}
1708 +
1709 +/*
1710 + * Send a packet of bytes to the device
1711 + */
1712 +int iforce_send_packet(struct iforce *iforce, u16 cmd, unsigned char* data)
1713 +{
1714 +       /* Copy data to buffer */
1715 +       int n = LO(cmd);
1716 +       int c;
1717 +       int empty;
1718 +       int head, tail;
1719 +       unsigned long flags;
1720 +                       
1721 +/*
1722 + * Update head and tail of xmit buffer
1723 + */
1724 +       spin_lock_irqsave(&iforce->xmit_lock, flags);
1725 +
1726 +       head = iforce->xmit.head;
1727 +       tail = iforce->xmit.tail;
1728 +
1729 +       if (CIRC_SPACE(head, tail, XMIT_SIZE) < n+2) {
1730 +               printk(KERN_WARNING "iforce.c: not enough space in xmit buffer to send new packet\n");
1731 +               spin_unlock_irqrestore(&iforce->xmit_lock, flags);
1732 +               return -1;
1733 +       }
1734 +
1735 +       empty = head == tail;
1736 +       XMIT_INC(iforce->xmit.head, n+2);
1737 +
1738 +/*
1739 + * Store packet in xmit buffer
1740 + */
1741 +       iforce->xmit.buf[head] = HI(cmd);
1742 +       XMIT_INC(head, 1);
1743 +       iforce->xmit.buf[head] = LO(cmd);
1744 +       XMIT_INC(head, 1);
1745 +
1746 +       c = CIRC_SPACE_TO_END(head, tail, XMIT_SIZE);
1747 +       if (n < c) c=n;
1748 +
1749 +       memcpy(&iforce->xmit.buf[head],
1750 +              data,
1751 +              c);
1752 +       if (n != c) {
1753 +               memcpy(&iforce->xmit.buf[0],
1754 +                      data + c,
1755 +                      n - c);
1756 +       }
1757 +       XMIT_INC(head, n);
1758 +
1759 +       spin_unlock_irqrestore(&iforce->xmit_lock, flags);
1760 +/*
1761 + * If necessary, start the transmission
1762 + */
1763 +       switch (iforce->bus) {
1764 +
1765 +#ifdef CONFIG_JOYSTICK_IFORCE_232
1766 +               case IFORCE_232:
1767 +               if (empty)
1768 +                       iforce_serial_xmit(iforce);
1769 +               break;
1770 +#endif
1771 +#ifdef CONFIG_JOYSTICK_IFORCE_USB
1772 +               case IFORCE_USB: 
1773 +
1774 +               if (iforce->usbdev && empty &&
1775 +                       !test_and_set_bit(IFORCE_XMIT_RUNNING, iforce->xmit_flags)) {
1776 +
1777 +                       iforce_usb_xmit(iforce);
1778 +               }
1779 +               break;
1780 +#endif
1781 +       }
1782 +       return 0;
1783 +}
1784 +
1785 +/* Start or stop an effect */
1786 +int iforce_control_playback(struct iforce* iforce, u16 id, unsigned int value)
1787 +{
1788 +       unsigned char data[3];
1789 +
1790 +//printk(KERN_DEBUG "iforce-packets.c: control_playback %d %d\n", id, value);
1791 +
1792 +       data[0] = LO(id);
1793 +       data[1] = (value > 0) ? ((value > 1) ? 0x41 : 0x01) : 0;
1794 +       data[2] = LO(value);
1795 +       return iforce_send_packet(iforce, FF_CMD_PLAY, data);
1796 +}
1797 +
1798 +/* Mark an effect that was being updated as ready. That means it can be updated
1799 + * again */
1800 +static int mark_core_as_ready(struct iforce *iforce, unsigned short addr)
1801 +{
1802 +       int i;
1803 +       for (i=0; i<iforce->dev.ff_effects_max; ++i) {
1804 +               if (test_bit(FF_CORE_IS_USED, iforce->core_effects[i].flags) &&
1805 +                   (iforce->core_effects[i].mod1_chunk.start == addr ||
1806 +                    iforce->core_effects[i].mod2_chunk.start == addr)) {
1807 +                       clear_bit(FF_CORE_UPDATE, iforce->core_effects[i].flags);
1808 +                       return 0;
1809 +               }
1810 +       }
1811 +       printk(KERN_WARNING "iforce-packets.c: unused effect %04x updated !!!\n", addr);
1812 +       return -1;
1813 +}
1814 +
1815 +void iforce_process_packet(struct iforce *iforce, u16 cmd, unsigned char *data)
1816 +{
1817 +       struct input_dev *dev = &iforce->dev;
1818 +       int i;
1819 +       static int being_used = 0;
1820 +
1821 +       if (being_used)
1822 +               printk(KERN_WARNING "iforce-packets.c: re-entrant call to iforce_process %d\n", being_used);
1823 +       being_used++;
1824 +
1825 +#ifdef CONFIG_JOYSTICK_IFORCE_232
1826 +       if (HI(iforce->expect_packet) == HI(cmd)) {
1827 +               iforce->expect_packet = 0;
1828 +               iforce->ecmd = cmd;
1829 +               memcpy(iforce->edata, data, IFORCE_MAX_LENGTH);
1830 +               if (waitqueue_active(&iforce->wait))
1831 +                       wake_up(&iforce->wait);
1832 +       }
1833 +#endif
1834 +
1835 +       if (!iforce->type) {
1836 +               being_used--;
1837 +               return;
1838 +       }
1839 +
1840 +       switch (HI(cmd)) {
1841 +
1842 +       case 0x01:      /* joystick position data */
1843 +       case 0x03:      /* wheel position data */
1844 +       case 0x06:      /*saitek cyborgforve data */
1845 +                       if (HI(cmd) == 6) {
1846 +                               input_report_abs(dev, ABS_X, (__s16) (((__s16)data[1] << 8) | data[0]));
1847 +                               input_report_abs(dev, ABS_Y, (__s16) (((__s16)data[3] << 8) | data[2]));
1848 +                               input_report_abs(dev, ABS_THROTTLE, 255 - data[4]);
1849 +                               input_report_abs(dev, ABS_RUDDER, 255 - data[7]); 
1850 +                       }
1851 +                       else if (HI(cmd) == 1) {
1852 +                               input_report_abs(dev, ABS_X, (__s16) (((__s16)data[1] << 8) | data[0]));
1853 +                               input_report_abs(dev, ABS_Y, (__s16) (((__s16)data[3] << 8) | data[2]));
1854 +                               input_report_abs(dev, ABS_THROTTLE, 255 - data[4]);
1855 +                               if (LO(cmd) >= 8 && test_bit(ABS_RUDDER ,dev->absbit))
1856 +                                       input_report_abs(dev, ABS_RUDDER, (__s8)data[7]);
1857 +                       } else {
1858 +                               input_report_abs(dev, ABS_WHEEL, (__s16) (((__s16)data[1] << 8) | data[0]));
1859 +                               input_report_abs(dev, ABS_GAS,   255 - data[2]);
1860 +                               input_report_abs(dev, ABS_BRAKE, 255 - data[3]);
1861 +                       }
1862 +
1863 +                       input_report_abs(dev, ABS_HAT0X, iforce_hat_to_axis[data[6] >> 4].x);
1864 +                       input_report_abs(dev, ABS_HAT0Y, iforce_hat_to_axis[data[6] >> 4].y);
1865 +
1866 +                       for (i = 0; iforce->type->btn[i] >= 0; i++)
1867 +                               input_report_key(dev, iforce->type->btn[i], data[(i >> 3) + 5] & (1 << (i & 7)));
1868 +
1869 +                       /* If there are untouched bits left, interpret them as the second hat */
1870 +                       if (i <= 8) {
1871 +                               int btns = data[6];
1872 +                               if (test_bit(ABS_HAT1X, dev->absbit)) {
1873 +                                       if (btns & 8) input_report_abs(dev, ABS_HAT1X, -1);
1874 +                                       else if (btns & 2) input_report_abs(dev, ABS_HAT1X, 1);
1875 +                                       else input_report_abs(dev, ABS_HAT1X, 0);
1876 +                               }
1877 +                               if (test_bit(ABS_HAT1Y, dev->absbit)) {
1878 +                                       if (btns & 1) input_report_abs(dev, ABS_HAT1Y, -1);
1879 +                                       else if (btns & 4) input_report_abs(dev, ABS_HAT1Y, 1);
1880 +                                       else input_report_abs(dev, ABS_HAT1Y, 0);
1881 +                               }
1882 +                       }
1883 +
1884 +                       break;
1885 +
1886 +               case 0x02:      /* status report */
1887 +                       input_report_key(dev, BTN_DEAD, data[0] & 0x02);
1888 +
1889 +                       /* Check if an effect was just started or stopped */
1890 +                       i = data[1] & 0x7f;
1891 +                       if (data[1] & 0x80) {
1892 +                               if (!test_and_set_bit(FF_CORE_IS_PLAYED, iforce->core_effects[i].flags)) {
1893 +                               /* Report play event */
1894 +                               input_report_ff_status(dev, i, FF_STATUS_PLAYING);
1895 +                               }
1896 +                       }
1897 +                       else if (test_and_clear_bit(FF_CORE_IS_PLAYED, iforce->core_effects[i].flags)) {
1898 +                               /* Report stop event */
1899 +                               input_report_ff_status(dev, i, FF_STATUS_STOPPED);
1900 +                       }
1901 +                       if (LO(cmd) > 3) {
1902 +                               int j;
1903 +                               for (j=3; j<LO(cmd); j+=2) {
1904 +                                       mark_core_as_ready(iforce, data[j] | (data[j+1]<<8));
1905 +                               }
1906 +                       }
1907 +                       break;
1908 +       }
1909 +       being_used--;
1910 +}
1911 +
1912 +int iforce_get_id_packet(struct iforce *iforce, char *packet)
1913 +{
1914 +       DECLARE_WAITQUEUE(wait, current);
1915 +       int timeout = HZ; /* 1 second */
1916 +
1917 +       switch (iforce->bus) {
1918 +
1919 +       case IFORCE_USB:
1920 +
1921 +#ifdef CONFIG_JOYSTICK_IFORCE_USB
1922 +               iforce->dr.bRequest = packet[0];
1923 +               iforce->ctrl->dev = iforce->usbdev;
1924 +
1925 +               set_current_state(TASK_INTERRUPTIBLE);
1926 +               add_wait_queue(&iforce->wait, &wait);
1927 +
1928 +               if (usb_submit_urb(iforce->ctrl)) {
1929 +                       set_current_state(TASK_RUNNING);
1930 +                       remove_wait_queue(&iforce->wait, &wait);
1931 +                       return -1;
1932 +               }
1933 +
1934 +               while (timeout && iforce->ctrl->status == -EINPROGRESS)
1935 +                       timeout = schedule_timeout(timeout);
1936 +
1937 +               set_current_state(TASK_RUNNING);
1938 +               remove_wait_queue(&iforce->wait, &wait);
1939 +
1940 +               if (!timeout) {
1941 +                       usb_unlink_urb(iforce->ctrl);
1942 +                       return -1;
1943 +               }
1944 +#else
1945 +               printk(KERN_ERR "iforce_get_id_packet: iforce->bus = USB!\n");
1946 +#endif
1947 +               break;
1948 +
1949 +       case IFORCE_232:
1950 +
1951 +#ifdef CONFIG_JOYSTICK_IFORCE_232
1952 +               iforce->expect_packet = FF_CMD_QUERY;
1953 +               iforce_send_packet(iforce, FF_CMD_QUERY, packet);
1954 +
1955 +               set_current_state(TASK_INTERRUPTIBLE);
1956 +               add_wait_queue(&iforce->wait, &wait);
1957 +
1958 +               while (timeout && iforce->expect_packet)
1959 +                       timeout = schedule_timeout(timeout);
1960 +
1961 +               set_current_state(TASK_RUNNING);
1962 +               remove_wait_queue(&iforce->wait, &wait);
1963 +
1964 +               if (!timeout) {
1965 +                       iforce->expect_packet = 0;
1966 +                       return -1;
1967 +               }
1968 +#else
1969 +               printk(KERN_ERR "iforce_get_id_packet: iforce->bus = SERIO!\n");
1970 +#endif
1971 +               break;
1972 +
1973 +       default:
1974 +               printk(KERN_ERR "iforce_get_id_packet: iforce->bus = %d\n",
1975 +                      iforce->bus);
1976 +               break;
1977 +       }
1978 +
1979 +       return -(iforce->edata[0] != packet[0]);
1980 +}
1981 +
1982 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/iforce/iforce-serio.c linux-modified/drivers/char/joystick/iforce/iforce-serio.c
1983 --- linux-vanilla/drivers/char/joystick/iforce/iforce-serio.c   Thu Jan  1 02:00:00 1970
1984 +++ linux-modified/drivers/char/joystick/iforce/iforce-serio.c  Mon Jan  6 16:48:20 2003
1985 @@ -0,0 +1,166 @@
1986 +/*
1987 + * $Id$
1988 + *
1989 + *  Copyright (c) 2000-2001 Vojtech Pavlik <vojtech@ucw.cz>
1990 + *  Copyright (c) 2001 Johann Deneux <deneux@ifrance.com>
1991 + *
1992 + *  USB/RS232 I-Force joysticks and wheels.
1993 + */
1994 +
1995 +/*
1996 + * This program is free software; you can redistribute it and/or modify
1997 + * it under the terms of the GNU General Public License as published by
1998 + * the Free Software Foundation; either version 2 of the License, or
1999 + * (at your option) any later version.
2000 + *
2001 + * This program is distributed in the hope that it will be useful,
2002 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
2003 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
2004 + * GNU General Public License for more details.
2005 + *
2006 + * You should have received a copy of the GNU General Public License
2007 + * along with this program; if not, write to the Free Software
2008 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
2009 + *
2010 + * Should you need to contact me, the author, you can do so either by
2011 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
2012 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
2013 + */
2014 +
2015 +#include "iforce.h"
2016 +
2017 +void iforce_serial_xmit(struct iforce *iforce)
2018 +{
2019 +       unsigned char cs;
2020 +       int i;
2021 +       unsigned long flags;
2022 +
2023 +       if (test_and_set_bit(IFORCE_XMIT_RUNNING, iforce->xmit_flags)) {
2024 +               set_bit(IFORCE_XMIT_AGAIN, iforce->xmit_flags);
2025 +               return;
2026 +       }
2027 +
2028 +       spin_lock_irqsave(&iforce->xmit_lock, flags);
2029 +
2030 +again:
2031 +       if (iforce->xmit.head == iforce->xmit.tail) {
2032 +               clear_bit(IFORCE_XMIT_RUNNING, iforce->xmit_flags);
2033 +               spin_unlock_irqrestore(&iforce->xmit_lock, flags);
2034 +               return;
2035 +       }
2036 +
2037 +       cs = 0x2b;
2038 +
2039 +       serio_write(iforce->serio, 0x2b);
2040 +
2041 +       serio_write(iforce->serio, iforce->xmit.buf[iforce->xmit.tail]);
2042 +       cs ^= iforce->xmit.buf[iforce->xmit.tail];
2043 +       XMIT_INC(iforce->xmit.tail, 1);
2044 +
2045 +       for (i=iforce->xmit.buf[iforce->xmit.tail]; i >= 0; --i) {
2046 +               serio_write(iforce->serio, iforce->xmit.buf[iforce->xmit.tail]);
2047 +               cs ^= iforce->xmit.buf[iforce->xmit.tail];
2048 +               XMIT_INC(iforce->xmit.tail, 1);
2049 +       }
2050 +       
2051 +       serio_write(iforce->serio, cs);
2052 +
2053 +       if (test_and_clear_bit(IFORCE_XMIT_AGAIN, iforce->xmit_flags))
2054 +               goto again;
2055 +
2056 +       clear_bit(IFORCE_XMIT_RUNNING, iforce->xmit_flags);
2057 +
2058 +       spin_unlock_irqrestore(&iforce->xmit_lock, flags);
2059 +}
2060 +
2061 +static void iforce_serio_write_wakeup(struct serio *serio)
2062 +{
2063 +       iforce_serial_xmit((struct iforce *)serio->private);
2064 +}
2065 +
2066 +static void iforce_serio_irq(struct serio *serio, unsigned char data, unsigned int flags)
2067 +{
2068 +       struct iforce* iforce = serio->private;
2069 +
2070 +       if (!iforce->pkt) {
2071 +               if (data != 0x2b) {
2072 +                       return;
2073 +               }
2074 +               iforce->pkt = 1;
2075 +               return;
2076 +       }
2077 +
2078 +       if (!iforce->id) {
2079 +               if (data > 3 && data != 0xff) {
2080 +                       iforce->pkt = 0;
2081 +                       return;
2082 +               }
2083 +               iforce->id = data;
2084 +               return;
2085 +       }
2086 +
2087 +       if (!iforce->len) {
2088 +               if (data > IFORCE_MAX_LENGTH) {
2089 +                       iforce->pkt = 0;
2090 +                       iforce->id = 0;
2091 +                       return;
2092 +               }
2093 +               iforce->len = data;
2094 +               return;
2095 +       }
2096 +
2097 +       if (iforce->idx < iforce->len) {
2098 +               iforce->csum += iforce->data[iforce->idx++] = data;
2099 +               return;
2100 +       }
2101 +
2102 +       if (iforce->idx == iforce->len) {
2103 +               iforce_process_packet(iforce, (iforce->id << 8) | iforce->idx, iforce->data);
2104 +               iforce->pkt = 0;
2105 +               iforce->id  = 0;
2106 +               iforce->len = 0;
2107 +               iforce->idx = 0;
2108 +               iforce->csum = 0;
2109 +       }
2110 +}
2111 +
2112 +static void iforce_serio_connect(struct serio *serio, struct serio_dev *dev)
2113 +{
2114 +       struct iforce *iforce;
2115 +       if (serio->type != (SERIO_RS232 | SERIO_IFORCE))
2116 +               return;
2117 +
2118 +       if (!(iforce = kmalloc(sizeof(struct iforce), GFP_KERNEL))) return;
2119 +       memset(iforce, 0, sizeof(struct iforce));
2120 +
2121 +       iforce->bus = IFORCE_232;
2122 +       iforce->serio = serio;
2123 +       serio->private = iforce;
2124 +
2125 +       if (serio_open(serio, dev)) {
2126 +               kfree(iforce);
2127 +               return;
2128 +       }
2129 +
2130 +       if (iforce_init_device(iforce)) {
2131 +               serio_close(serio);
2132 +               kfree(iforce);
2133 +               return;
2134 +       }
2135 +}
2136 +
2137 +static void iforce_serio_disconnect(struct serio *serio)
2138 +{
2139 +       struct iforce* iforce = serio->private;
2140 +
2141 +       input_unregister_device(&iforce->dev);
2142 +       serio_close(serio);
2143 +       kfree(iforce);
2144 +}
2145 +
2146 +struct serio_dev iforce_serio_dev = {
2147 +       write_wakeup:   iforce_serio_write_wakeup,
2148 +       interrupt:      iforce_serio_irq,
2149 +       connect:        iforce_serio_connect,
2150 +       disconnect:     iforce_serio_disconnect,
2151 +};
2152 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/iforce/iforce-usb.c linux-modified/drivers/char/joystick/iforce/iforce-usb.c
2153 --- linux-vanilla/drivers/char/joystick/iforce/iforce-usb.c     Thu Jan  1 02:00:00 1970
2154 +++ linux-modified/drivers/char/joystick/iforce/iforce-usb.c    Mon Feb 17 21:28:41 2003
2155 @@ -0,0 +1,211 @@
2156 + /*
2157 + * $Id$
2158 + *
2159 + *  Copyright (c) 2000-2002 Vojtech Pavlik <vojtech@ucw.cz>
2160 + *  Copyright (c) 2001-2002 Johann Deneux <deneux@ifrance.com>
2161 + *
2162 + *  USB/RS232 I-Force joysticks and wheels.
2163 + */
2164 +
2165 +/*
2166 + * This program is free software; you can redistribute it and/or modify
2167 + * it under the terms of the GNU General Public License as published by
2168 + * the Free Software Foundation; either version 2 of the License, or
2169 + * (at your option) any later version.
2170 + *
2171 + * This program is distributed in the hope that it will be useful,
2172 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
2173 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
2174 + * GNU General Public License for more details.
2175 + *
2176 + * You should have received a copy of the GNU General Public License
2177 + * along with this program; if not, write to the Free Software
2178 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
2179 + *
2180 + * Should you need to contact me, the author, you can do so either by
2181 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
2182 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
2183 + */
2184 +
2185 +#include "iforce.h"
2186 +
2187 +void iforce_usb_xmit(struct iforce *iforce)
2188 +{
2189 +       int n, c;
2190 +       unsigned long flags;
2191 +
2192 +       spin_lock_irqsave(&iforce->xmit_lock, flags);
2193 +
2194 +       if (iforce->xmit.head == iforce->xmit.tail) {
2195 +               clear_bit(IFORCE_XMIT_RUNNING, iforce->xmit_flags);
2196 +               spin_unlock_irqrestore(&iforce->xmit_lock, flags);
2197 +               return;
2198 +       }
2199 +
2200 +       ((char *)iforce->out->transfer_buffer)[0] = iforce->xmit.buf[iforce->xmit.tail];
2201 +       XMIT_INC(iforce->xmit.tail, 1);
2202 +       n = iforce->xmit.buf[iforce->xmit.tail];
2203 +       XMIT_INC(iforce->xmit.tail, 1);
2204 +
2205 +       iforce->out->transfer_buffer_length = n + 1;
2206 +       iforce->out->dev = iforce->usbdev;
2207 +
2208 +       /* Copy rest of data then */
2209 +       c = CIRC_CNT_TO_END(iforce->xmit.head, iforce->xmit.tail, XMIT_SIZE);
2210 +       if (n < c) c=n;
2211 +
2212 +       memcpy(iforce->out->transfer_buffer + 1,
2213 +              &iforce->xmit.buf[iforce->xmit.tail],
2214 +              c);
2215 +       if (n != c) {
2216 +               memcpy(iforce->out->transfer_buffer + 1 + c,
2217 +                      &iforce->xmit.buf[0],
2218 +                      n-c);
2219 +       }
2220 +       XMIT_INC(iforce->xmit.tail, n);
2221 +
2222 +       spin_unlock_irqrestore(&iforce->xmit_lock, flags);
2223 +
2224 +       if ( (n=usb_submit_urb(iforce->out)) ) {
2225 +               printk(KERN_WARNING "iforce.c: iforce_usb_xmit: usb_submit_urb failed %d\n", n);
2226 +       }
2227 +}
2228 +
2229 +static void iforce_usb_irq(struct urb *urb)
2230 +{
2231 +       struct iforce *iforce = urb->context;
2232 +       if (urb->status) return;
2233 +       iforce_process_packet(iforce,
2234 +               (iforce->data[0] << 8) | (urb->actual_length - 1), iforce->data + 1);
2235 +}
2236 +
2237 +static void iforce_usb_out(struct urb *urb)
2238 +{
2239 +       struct iforce *iforce = urb->context;
2240 +
2241 +       if (urb->status) {
2242 +               printk(KERN_DEBUG "iforce_usb_out: urb->status %d, exiting", urb->status);
2243 +               return;
2244 +       }
2245 +
2246 +       iforce_usb_xmit(iforce);
2247 +
2248 +       if (waitqueue_active(&iforce->wait))
2249 +               wake_up(&iforce->wait);
2250 +}
2251 +
2252 +static void iforce_usb_ctrl(struct urb *urb)
2253 +{
2254 +       struct iforce *iforce = urb->context;
2255 +       if (urb->status) return;
2256 +       iforce->ecmd = 0xff00 | urb->actual_length;
2257 +       if (waitqueue_active(&iforce->wait))
2258 +               wake_up(&iforce->wait);
2259 +}
2260 +
2261 +static void *iforce_usb_probe(struct usb_device *dev, unsigned int ifnum,
2262 +                               const struct usb_device_id *id)
2263 +{
2264 +       struct usb_endpoint_descriptor *epirq, *epout;
2265 +       struct iforce *iforce;
2266 +
2267 +       epirq = dev->config[0].interface[ifnum].altsetting[0].endpoint + 0;
2268 +       epout = dev->config[0].interface[ifnum].altsetting[0].endpoint + 1;
2269 +
2270 +       if (!(iforce = kmalloc(sizeof(struct iforce) + 32, GFP_KERNEL)))
2271 +               goto fail;
2272 +
2273 +       memset(iforce, 0, sizeof(struct iforce));
2274 +
2275 +       if (!(iforce->irq = usb_alloc_urb(0))) {
2276 +               goto fail;
2277 +       }
2278 +
2279 +       if (!(iforce->out = usb_alloc_urb(0))) {
2280 +               goto fail;
2281 +       }
2282 +
2283 +       if (!(iforce->ctrl = usb_alloc_urb(0))) {
2284 +               goto fail;
2285 +       }
2286 +
2287 +       iforce->bus = IFORCE_USB;
2288 +       iforce->usbdev = dev;
2289 +
2290 +       iforce->dr.bRequestType = USB_TYPE_VENDOR | USB_DIR_IN | USB_RECIP_INTERFACE;
2291 +       iforce->dr.wIndex = 0;
2292 +       iforce->dr.wLength = 16;
2293 +
2294 +       usb_fill_int_urb(iforce->irq, dev, usb_rcvintpipe(dev, epirq->bEndpointAddress),
2295 +                       iforce->data, 16, iforce_usb_irq, iforce, epirq->bInterval);
2296 +
2297 +       usb_fill_bulk_urb(iforce->out, dev, usb_sndbulkpipe(dev, epout->bEndpointAddress),
2298 +                       iforce + 1, 32, iforce_usb_out, iforce);
2299 +
2300 +       usb_fill_control_urb(iforce->ctrl, dev, usb_rcvctrlpipe(dev, 0),
2301 +                       (void*) &iforce->dr, iforce->edata, 16, iforce_usb_ctrl, iforce);
2302 +
2303 +       if (iforce_init_device(iforce)) goto fail;
2304 +
2305 +       return iforce;
2306 +
2307 +fail:
2308 +       if (iforce) {
2309 +               if (iforce->irq) usb_free_urb(iforce->irq);
2310 +               if (iforce->out) usb_free_urb(iforce->out);
2311 +               if (iforce->ctrl) usb_free_urb(iforce->ctrl);
2312 +               kfree(iforce);
2313 +       }
2314 +
2315 +       return NULL;
2316 +}
2317 +
2318 +/* Called by iforce_delete() */
2319 +void iforce_usb_delete(struct iforce* iforce)
2320 +{
2321 +       usb_unlink_urb(iforce->irq);
2322 +       usb_unlink_urb(iforce->out);
2323 +       usb_unlink_urb(iforce->ctrl);
2324 +
2325 +       usb_free_urb(iforce->irq);
2326 +       usb_free_urb(iforce->out);
2327 +       usb_free_urb(iforce->ctrl);
2328 +}
2329 +
2330 +static void iforce_usb_disconnect(struct usb_device *dev, void *ptr)
2331 +{
2332 +       struct iforce *iforce = ptr;
2333 +       int open = iforce->dev.handle->open;
2334 +
2335 +       iforce->usbdev = NULL;
2336 +       input_unregister_device(&iforce->dev);
2337 +
2338 +       if (!open) {
2339 +               iforce_delete_device(iforce);
2340 +               kfree(iforce);
2341 +       }
2342 +}
2343 +
2344 +static struct usb_device_id iforce_usb_ids [] = {
2345 +       { USB_DEVICE(0x044f, 0xa01c) },         /* Thrustmaster Motor Sport GT */
2346 +       { USB_DEVICE(0x046d, 0xc281) },         /* Logitech WingMan Force */
2347 +       { USB_DEVICE(0x046d, 0xc291) },         /* Logitech WingMan Formula Force */
2348 +       { USB_DEVICE(0x05ef, 0x020a) },         /* AVB Top Shot Pegasus */
2349 +       { USB_DEVICE(0x05ef, 0x8884) },         /* AVB Mag Turbo Force */
2350 +       { USB_DEVICE(0x05ef, 0x8888) },         /* AVB Top Shot FFB Racing Wheel */
2351 +       { USB_DEVICE(0x061c, 0xc084) },         /* ACT LABS Force RS */
2352 +       { USB_DEVICE(0x06f8, 0x0001) },         /* Guillemot Race Leader Force Feedback */
2353 +       { USB_DEVICE(0x06f8, 0x0004) },         /* Guillemot Force Feedback Racing Wheel */
2354 +       { USB_DEVICE(0x06a3, 0xff12) },         /* Saitek Cyborgforce 3d */
2355 +       { }                                     /* Terminating entry */
2356 +};
2357 +
2358 +MODULE_DEVICE_TABLE (usb, iforce_usb_ids);
2359 +
2360 +struct usb_driver iforce_usb_driver = {
2361 +//     owner:          THIS_MODULE,
2362 +       name:           "iforce",
2363 +       probe:          iforce_usb_probe,
2364 +       disconnect:     iforce_usb_disconnect,
2365 +       id_table:       iforce_usb_ids,
2366 +};
2367 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/iforce/iforce.h linux-modified/drivers/char/joystick/iforce/iforce.h
2368 --- linux-vanilla/drivers/char/joystick/iforce/iforce.h Thu Jan  1 02:00:00 1970
2369 +++ linux-modified/drivers/char/joystick/iforce/iforce.h        Sun Mar  9 16:58:46 2003
2370 @@ -0,0 +1,184 @@
2371 +/*
2372 + * $Id$
2373 + *
2374 + *  Copyright (c) 2000-2002 Vojtech Pavlik <vojtech@ucw.cz>
2375 + *  Copyright (c) 2001-2002 Johann Deneux <deneux@ifrance.com>
2376 + *
2377 + *  USB/RS232 I-Force joysticks and wheels.
2378 + */
2379 +
2380 +/*
2381 + * This program is free software; you can redistribute it and/or modify
2382 + * it under the terms of the GNU General Public License as published by
2383 + * the Free Software Foundation; either version 2 of the License, or
2384 + * (at your option) any later version.
2385 + *
2386 + * This program is distributed in the hope that it will be useful,
2387 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
2388 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
2389 + * GNU General Public License for more details.
2390 + *
2391 + * You should have received a copy of the GNU General Public License
2392 + * along with this program; if not, write to the Free Software
2393 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
2394 + *
2395 + * Should you need to contact me, the author, you can do so either by
2396 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
2397 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
2398 + */
2399 +
2400 +#include <linux/kernel.h>
2401 +#include <linux/slab.h>
2402 +#include <linux/input.h>
2403 +#include <linux/module.h>
2404 +#include <linux/init.h>
2405 +#include <linux/spinlock.h>
2406 +#include <linux/usb.h>
2407 +#include <linux/serio.h>
2408 +#include <linux/config.h>
2409 +#include <linux/circ_buf.h>
2410 +#include <asm/semaphore.h>
2411 +
2412 +/* FF: This module provides arbitrary resource management routines.
2413 + * I use it to manage the device's memory.
2414 + * Despite the name of this module, I am *not* going to access the ioports.
2415 + */
2416 +#include <linux/ioport.h>
2417 +
2418 +#define IFORCE_MAX_LENGTH      16
2419 +
2420 +#define IFORCE_232     1
2421 +#define IFORCE_USB     2
2422 +
2423 +#define FALSE 0
2424 +#define TRUE 1
2425 +
2426 +#define FF_EFFECTS_MAX 32
2427 +
2428 +/* Each force feedback effect is made of one core effect, which can be
2429 + * associated to at most to effect modifiers
2430 + */
2431 +#define FF_MOD1_IS_USED                0
2432 +#define FF_MOD2_IS_USED                1
2433 +#define FF_CORE_IS_USED                2
2434 +#define FF_CORE_IS_PLAYED      3       /* Effect is currently being played */
2435 +#define FF_CORE_SHOULD_PLAY    4       /* User wants the effect to be played */
2436 +#define FF_CORE_UPDATE         5       /* Effect is being updated */
2437 +#define FF_MODCORE_MAX         5
2438 +
2439 +struct iforce_core_effect {
2440 +       /* Information about where modifiers are stored in the device's memory */
2441 +       struct resource mod1_chunk;
2442 +       struct resource mod2_chunk;
2443 +       unsigned long flags[NBITS(FF_MODCORE_MAX)];
2444 +       pid_t owner;
2445 +       /* Used to keep track of parameters of an effect. They are needed
2446 +        * to know what parts of an effect changed in an update operation.
2447 +        * We try to send only parameter packets if possible, as sending
2448 +        * effect parameter requires the effect to be stoped and restarted
2449 +        */
2450 +       struct ff_effect effect;
2451 +};
2452 +
2453 +#define FF_CMD_EFFECT          0x010e
2454 +#define FF_CMD_ENVELOPE                0x0208
2455 +#define FF_CMD_MAGNITUDE       0x0303
2456 +#define FF_CMD_PERIOD          0x0407
2457 +#define FF_CMD_CONDITION       0x050a
2458 +
2459 +#define FF_CMD_AUTOCENTER      0x4002
2460 +#define FF_CMD_PLAY            0x4103
2461 +#define FF_CMD_ENABLE          0x4201
2462 +#define FF_CMD_GAIN            0x4301
2463 +
2464 +#define FF_CMD_QUERY           0xff01
2465 +
2466 +/* Buffer for async write */
2467 +#define XMIT_SIZE              256
2468 +#define XMIT_INC(var, n)       (var)+=n; (var)&= XMIT_SIZE -1
2469 +/* iforce::xmit_flags */
2470 +#define IFORCE_XMIT_RUNNING    0
2471 +#define IFORCE_XMIT_AGAIN      1
2472 +
2473 +struct iforce_device {
2474 +       u16 idvendor;
2475 +       u16 idproduct;
2476 +       char *name;
2477 +       signed short *btn;
2478 +       signed short *abs;
2479 +       signed short *ff;
2480 +};
2481 +
2482 +struct iforce {
2483 +       struct input_dev dev;           /* Input device interface */
2484 +       struct iforce_device *type;
2485 +       int bus;
2486 +
2487 +       unsigned char data[IFORCE_MAX_LENGTH];
2488 +       unsigned char edata[IFORCE_MAX_LENGTH];
2489 +       u16 ecmd;
2490 +       u16 expect_packet;
2491 +
2492 +#ifdef CONFIG_JOYSTICK_IFORCE_232
2493 +       struct serio *serio;            /* RS232 transfer */
2494 +       int idx, pkt, len, id;
2495 +       unsigned char csum;
2496 +#endif
2497 +#ifdef CONFIG_JOYSTICK_IFORCE_USB
2498 +       struct usb_device *usbdev;      /* USB transfer */
2499 +       struct urb *irq, *out, *ctrl;
2500 +       struct usb_ctrlrequest dr;
2501 +#endif
2502 +       spinlock_t xmit_lock;
2503 +       /* Buffer used for asynchronous sending of bytes to the device */
2504 +       struct circ_buf xmit;
2505 +       unsigned char xmit_data[XMIT_SIZE];
2506 +       long xmit_flags[1];
2507 +       
2508 +                                       /* Force Feedback */
2509 +       wait_queue_head_t wait;
2510 +       struct resource device_memory;
2511 +       struct iforce_core_effect core_effects[FF_EFFECTS_MAX];
2512 +       struct semaphore mem_mutex;
2513 +};
2514 +
2515 +/* Get hi and low bytes of a 16-bits int */
2516 +#define HI(a)  ((unsigned char)((a) >> 8))
2517 +#define LO(a)  ((unsigned char)((a) & 0xff))
2518 +
2519 +/* For many parameters, it seems that 0x80 is a special value that should
2520 + * be avoided. Instead, we replace this value by 0x7f
2521 + */
2522 +#define HIFIX80(a) ((unsigned char)(((a)<0? (a)+255 : (a))>>8))
2523 +
2524 +/* Encode a time value */
2525 +#define TIME_SCALE(a)  (a)
2526 +
2527 +
2528 +/* Public functions */
2529 +/* iforce-serio.c */
2530 +void iforce_serial_xmit(struct iforce *iforce);
2531 +
2532 +/* iforce-usb.c */
2533 +void iforce_usb_xmit(struct iforce *iforce);
2534 +void iforce_usb_delete(struct iforce *iforce);
2535 +
2536 +/* iforce-main.c */
2537 +int iforce_init_device(struct iforce *iforce);
2538 +void iforce_delete_device(struct iforce *iforce);
2539 +
2540 +/* iforce-packets.c */
2541 +int iforce_control_playback(struct iforce*, u16 id, unsigned int);
2542 +void iforce_process_packet(struct iforce *iforce, u16 cmd, unsigned char *data);
2543 +int iforce_send_packet(struct iforce *iforce, u16 cmd, unsigned char* data);
2544 +void iforce_dump_packet(char *msg, u16 cmd, unsigned char *data) ;
2545 +int iforce_get_id_packet(struct iforce *iforce, char *packet);
2546 +
2547 +/* iforce-ff.c */
2548 +int iforce_upload_periodic(struct iforce*, struct ff_effect*, int is_update);
2549 +int iforce_upload_constant(struct iforce*, struct ff_effect*, int is_update);
2550 +int iforce_upload_condition(struct iforce*, struct ff_effect*, int is_update);
2551 +
2552 +/* Public variables */
2553 +extern struct serio_dev iforce_serio_dev;
2554 +extern struct usb_driver iforce_usb_driver;
2555 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/iforce.c linux-modified/drivers/char/joystick/iforce.c
2556 --- linux-vanilla/drivers/char/joystick/iforce.c        Mon Feb  3 20:32:38 2003
2557 +++ linux-modified/drivers/char/joystick/iforce.c       Thu Jan  1 02:00:00 1970
2558 @@ -1,1199 +0,0 @@
2559 -/*
2560 - * $Id$
2561 - *
2562 - *  Copyright (c) 2000-2001 Vojtech Pavlik <vojtech@suse.cz>
2563 - *  Copyright (c) 2001 Johann Deneux <deneux@ifrance.com>
2564 - *
2565 - *  USB/RS232 I-Force joysticks and wheels.
2566 - *
2567 - *  Sponsored by SuSE
2568 - */
2569 -
2570 -/*
2571 - * This program is free software; you can redistribute it and/or modify
2572 - * it under the terms of the GNU General Public License as published by
2573 - * the Free Software Foundation; either version 2 of the License, or
2574 - * (at your option) any later version.
2575 - *
2576 - * This program is distributed in the hope that it will be useful,
2577 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
2578 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
2579 - * GNU General Public License for more details.
2580 - *
2581 - * You should have received a copy of the GNU General Public License
2582 - * along with this program; if not, write to the Free Software
2583 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
2584 - *
2585 - * Should you need to contact me, the author, you can do so either by
2586 - * e-mail - mail your message to <vojtech@suse.cz>, or by paper mail:
2587 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
2588 - */
2589 -
2590 -#include <linux/kernel.h>
2591 -#include <linux/slab.h>
2592 -#include <linux/input.h>
2593 -#include <linux/module.h>
2594 -#include <linux/init.h>
2595 -#include <linux/spinlock.h>
2596 -#include <linux/usb.h>
2597 -#include <linux/serio.h>
2598 -#include <linux/config.h>
2599 -
2600 -/* FF: This module provides arbitrary resource management routines.
2601 - * I use it to manage the device's memory.
2602 - * Despite the name of this module, I am *not* going to access the ioports.
2603 - */
2604 -#include <linux/ioport.h>
2605 -
2606 -MODULE_AUTHOR("Vojtech Pavlik <vojtech@suse.cz>, Johann Deneux <deneux@ifrance.com>");
2607 -MODULE_DESCRIPTION("USB/RS232 I-Force joysticks and wheels driver");
2608 -MODULE_LICENSE("GPL");
2609 -
2610 -#define IFORCE_MAX_LENGTH      16
2611 -
2612 -#if defined(CONFIG_INPUT_IFORCE_232) || defined(CONFIG_INPUT_IFORCE_232_MODULE)
2613 -#define IFORCE_232     1
2614 -#endif
2615 -#if defined(CONFIG_INPUT_IFORCE_USB) || defined(CONFIG_INPUT_IFORCE_USB_MODULE)
2616 -#define IFORCE_USB     2
2617 -#endif
2618 -
2619 -#define FF_EFFECTS_MAX 32
2620 -
2621 -/* Each force feedback effect is made of one core effect, which can be
2622 - * associated to at most to effect modifiers
2623 - */
2624 -#define FF_MOD1_IS_USED                0
2625 -#define FF_MOD2_IS_USED                1
2626 -#define FF_CORE_IS_USED                2
2627 -#define FF_CORE_IS_PLAYED      3
2628 -#define FF_MODCORE_MAX         3
2629 -
2630 -struct iforce_core_effect {
2631 -       /* Information about where modifiers are stored in the device's memory */
2632 -       struct resource mod1_chunk;
2633 -       struct resource mod2_chunk;
2634 -       unsigned long flags[NBITS(FF_MODCORE_MAX)];
2635 -};
2636 -
2637 -#define FF_CMD_EFFECT          0x010e
2638 -#define FF_CMD_SHAPE           0x0208
2639 -#define FF_CMD_MAGNITUDE       0x0303
2640 -#define FF_CMD_PERIOD          0x0407
2641 -#define FF_CMD_INTERACT                0x050a
2642 -
2643 -#define FF_CMD_AUTOCENTER      0x4002
2644 -#define FF_CMD_PLAY            0x4103
2645 -#define FF_CMD_ENABLE          0x4201
2646 -#define FF_CMD_GAIN            0x4301
2647 -
2648 -#define FF_CMD_QUERY           0xff01
2649 -
2650 -static signed short btn_joystick[] = { BTN_TRIGGER, BTN_TOP, BTN_THUMB, BTN_TOP2, BTN_BASE,
2651 -       BTN_BASE2, BTN_BASE3, BTN_BASE4, BTN_BASE5, BTN_A, BTN_B, BTN_C, BTN_DEAD, -1 };
2652 -static signed short btn_wheel[] =    { BTN_TRIGGER, BTN_TOP, BTN_THUMB, BTN_TOP2, BTN_BASE,
2653 -       BTN_BASE2, BTN_BASE3, BTN_BASE4, BTN_BASE5, BTN_A, BTN_B, BTN_C, -1 };
2654 -static signed short abs_joystick[] = { ABS_X, ABS_Y, ABS_THROTTLE, ABS_HAT0X, ABS_HAT0Y, -1 };
2655 -static signed short abs_wheel[] =    { ABS_WHEEL, ABS_GAS, ABS_BRAKE, ABS_HAT0X, ABS_HAT0Y, -1 };
2656 -static signed short ff_iforce[] =    { FF_PERIODIC, FF_CONSTANT, FF_SPRING, FF_FRICTION,
2657 -       FF_SQUARE, FF_TRIANGLE, FF_SINE, FF_SAW_UP, FF_SAW_DOWN, FF_GAIN, FF_AUTOCENTER, -1 };
2658 -
2659 -static struct iforce_device {
2660 -       u16 idvendor;
2661 -       u16 idproduct;
2662 -       char *name;
2663 -       signed short *btn;
2664 -       signed short *abs;
2665 -       signed short *ff;
2666 -} iforce_device[] = {
2667 -       { 0x046d, 0xc281, "Logitech WingMan Force",                     btn_joystick, abs_joystick, ff_iforce },
2668 -       { 0x046d, 0xc291, "Logitech WingMan Formula Force",             btn_wheel, abs_wheel, ff_iforce },
2669 -       { 0x05ef, 0x020a, "AVB Top Shot Pegasus",                       btn_joystick, abs_joystick, ff_iforce },
2670 -       { 0x05ef, 0x8884, "AVB Mag Turbo Force",                        btn_wheel, abs_wheel, ff_iforce },
2671 -       { 0x06f8, 0x0001, "Guillemot Race Leader Force Feedback",       btn_wheel, abs_wheel, ff_iforce },
2672 -       { 0x0000, 0x0000, "Unknown I-Force Device [%04x:%04x]",         btn_joystick, abs_joystick, ff_iforce }
2673 -};
2674 -
2675 -struct iforce {
2676 -       struct input_dev dev;           /* Input device interface */
2677 -       struct iforce_device *type;
2678 -       char name[64];
2679 -       int open;
2680 -       int bus;
2681 -
2682 -       unsigned char data[IFORCE_MAX_LENGTH];
2683 -       unsigned char edata[IFORCE_MAX_LENGTH];
2684 -       u16 ecmd;
2685 -       u16 expect_packet;
2686 -
2687 -#ifdef IFORCE_232
2688 -       struct serio *serio;            /* RS232 transfer */
2689 -       int idx, pkt, len, id;
2690 -       unsigned char csum;
2691 -#endif
2692 -#ifdef IFORCE_USB
2693 -       struct usb_device *usbdev;      /* USB transfer */
2694 -       struct urb irq, out, ctrl;
2695 -       struct usb_ctrlrequest dr;
2696 -#endif
2697 -                                       /* Force Feedback */
2698 -       wait_queue_head_t wait;
2699 -       struct resource device_memory;
2700 -       struct iforce_core_effect core_effects[FF_EFFECTS_MAX];
2701 -};
2702 -
2703 -static struct {
2704 -       __s32 x;
2705 -       __s32 y;
2706 -} iforce_hat_to_axis[16] = {{ 0,-1}, { 1,-1}, { 1, 0}, { 1, 1}, { 0, 1}, {-1, 1}, {-1, 0}, {-1,-1}};
2707 -
2708 -/* Get hi and low bytes of a 16-bits int */
2709 -#define HI(a)  ((unsigned char)((a) >> 8))
2710 -#define LO(a)  ((unsigned char)((a) & 0xff))
2711 -
2712 -/* Encode a time value */
2713 -#define TIME_SCALE(a)  ((a) == 0xffff ? 0xffff : (a) * 1000 / 256)
2714 -
2715 -static void dump_packet(char *msg, u16 cmd, unsigned char *data)
2716 -{
2717 -       int i;
2718 -
2719 -       printk(KERN_DEBUG "iforce.c: %s ( cmd = %04x, data = ", msg, cmd);
2720 -       for (i = 0; i < LO(cmd); i++)
2721 -               printk("%02x ", data[i]);
2722 -       printk(")\n");
2723 -}
2724 -
2725 -/*
2726 - * Send a packet of bytes to the device
2727 - */
2728 -static void send_packet(struct iforce *iforce, u16 cmd, unsigned char* data)
2729 -{
2730 -       switch (iforce->bus) {
2731 -
2732 -#ifdef IFORCE_232
2733 -               case IFORCE_232: {
2734 -
2735 -                       int i;
2736 -                       unsigned char csum = 0x2b ^ HI(cmd) ^ LO(cmd);
2737 -
2738 -                       serio_write(iforce->serio, 0x2b);
2739 -                       serio_write(iforce->serio, HI(cmd));
2740 -                       serio_write(iforce->serio, LO(cmd));
2741 -
2742 -                       for (i = 0; i < LO(cmd); i++) {
2743 -                               serio_write(iforce->serio, data[i]);
2744 -                               csum = csum ^ data[i];
2745 -                       }
2746 -
2747 -                       serio_write(iforce->serio, csum);
2748 -                       return;
2749 -               }
2750 -#endif
2751 -#ifdef IFORCE_USB
2752 -               case IFORCE_USB: {
2753 -
2754 -                       DECLARE_WAITQUEUE(wait, current);
2755 -                       int timeout = HZ; /* 1 second */
2756 -
2757 -                       memcpy(iforce->out.transfer_buffer + 1, data, LO(cmd));
2758 -                       ((char*)iforce->out.transfer_buffer)[0] = HI(cmd);
2759 -                       iforce->out.transfer_buffer_length = LO(cmd) + 2;
2760 -                       iforce->out.dev = iforce->usbdev;
2761 -
2762 -                       set_current_state(TASK_INTERRUPTIBLE);
2763 -                       add_wait_queue(&iforce->wait, &wait);
2764 -
2765 -                       if (usb_submit_urb(&iforce->out)) {
2766 -                               set_current_state(TASK_RUNNING);
2767 -                               remove_wait_queue(&iforce->wait, &wait);
2768 -                               return;
2769 -                       }
2770 -
2771 -                       while (timeout && iforce->out.status == -EINPROGRESS)
2772 -                               timeout = schedule_timeout(timeout);
2773 -
2774 -                       set_current_state(TASK_RUNNING);
2775 -                       remove_wait_queue(&iforce->wait, &wait);
2776 -
2777 -                       if (!timeout)
2778 -                               usb_unlink_urb(&iforce->out);
2779 -
2780 -                       return;
2781 -               }
2782 -#endif
2783 -       }
2784 -}
2785 -
2786 -static void iforce_process_packet(struct iforce *iforce, u16 cmd, unsigned char *data)
2787 -{
2788 -       struct input_dev *dev = &iforce->dev;
2789 -       int i;
2790 -
2791 -#ifdef IFORCE_232
2792 -       if (HI(iforce->expect_packet) == HI(cmd)) {
2793 -               iforce->expect_packet = 0;
2794 -               iforce->ecmd = cmd;
2795 -               memcpy(iforce->edata, data, IFORCE_MAX_LENGTH);
2796 -               if (waitqueue_active(&iforce->wait))
2797 -                       wake_up(&iforce->wait);
2798 -       }
2799 -#endif
2800 -
2801 -       if (!iforce->type)
2802 -               return;
2803 -
2804 -       switch (HI(cmd)) {
2805 -
2806 -               case 0x01:      /* joystick position data */
2807 -               case 0x03:      /* wheel position data */
2808 -
2809 -                       if (HI(cmd) == 1) {
2810 -                               input_report_abs(dev, ABS_X, (__s16) (((__s16)data[1] << 8) | data[0]));
2811 -                               input_report_abs(dev, ABS_Y, (__s16) (((__s16)data[3] << 8) | data[2]));
2812 -                               input_report_abs(dev, ABS_THROTTLE, 255 - data[4]);
2813 -                       } else {
2814 -                               input_report_abs(dev, ABS_WHEEL, (__s16) (((__s16)data[1] << 8) | data[0]));
2815 -                               input_report_abs(dev, ABS_GAS,   255 - data[2]);
2816 -                               input_report_abs(dev, ABS_BRAKE, 255 - data[3]);
2817 -                       }
2818 -
2819 -                       input_report_abs(dev, ABS_HAT0X, iforce_hat_to_axis[data[6] >> 4].x);
2820 -                       input_report_abs(dev, ABS_HAT0Y, iforce_hat_to_axis[data[6] >> 4].y);
2821 -
2822 -                       for (i = 0; iforce->type->btn[i] >= 0; i++)
2823 -                               input_report_key(dev, iforce->type->btn[i], data[(i >> 3) + 5] & (1 << (i & 7)));
2824 -
2825 -                       break;
2826 -
2827 -               case 0x02:      /* status report */
2828 -
2829 -                       input_report_key(dev, BTN_DEAD, data[0] & 0x02);
2830 -                       break;
2831 -       }
2832 -}
2833 -
2834 -static int get_id_packet(struct iforce *iforce, char *packet)
2835 -{
2836 -       DECLARE_WAITQUEUE(wait, current);
2837 -       int timeout = HZ; /* 1 second */
2838 -
2839 -       switch (iforce->bus) {
2840 -
2841 -#ifdef IFORCE_USB
2842 -               case IFORCE_USB:
2843 -
2844 -                       iforce->dr.bRequest = packet[0];
2845 -                       iforce->ctrl.dev = iforce->usbdev;
2846 -
2847 -                       set_current_state(TASK_INTERRUPTIBLE);
2848 -                       add_wait_queue(&iforce->wait, &wait);
2849 -
2850 -                       if (usb_submit_urb(&iforce->ctrl)) {
2851 -                               set_current_state(TASK_RUNNING);
2852 -                               remove_wait_queue(&iforce->wait, &wait);
2853 -                               return -1;
2854 -                       }
2855 -
2856 -                       while (timeout && iforce->ctrl.status == -EINPROGRESS)
2857 -                               timeout = schedule_timeout(timeout);
2858 -
2859 -                       set_current_state(TASK_RUNNING);
2860 -                       remove_wait_queue(&iforce->wait, &wait);
2861 -
2862 -                       if (!timeout) {
2863 -                               usb_unlink_urb(&iforce->ctrl);
2864 -                               return -1;
2865 -                       }
2866 -
2867 -                       break;
2868 -#endif
2869 -#ifdef IFORCE_232
2870 -               case IFORCE_232:
2871 -
2872 -                       iforce->expect_packet = FF_CMD_QUERY;
2873 -                       send_packet(iforce, FF_CMD_QUERY, packet);
2874 -
2875 -                       set_current_state(TASK_INTERRUPTIBLE);
2876 -                       add_wait_queue(&iforce->wait, &wait);
2877 -
2878 -                       while (timeout && iforce->expect_packet)
2879 -                               timeout = schedule_timeout(timeout);
2880 -
2881 -                       set_current_state(TASK_RUNNING);
2882 -                       remove_wait_queue(&iforce->wait, &wait);
2883 -
2884 -                       if (!timeout) {
2885 -                               iforce->expect_packet = 0;
2886 -                               return -1;
2887 -                       }
2888 -
2889 -                       break;
2890 -#endif
2891 -       }
2892 -
2893 -       return -(iforce->edata[0] != packet[0]);
2894 -}
2895 -
2896 -static int iforce_open(struct input_dev *dev)
2897 -{
2898 -       struct iforce *iforce = dev->private;
2899 -
2900 -       switch (iforce->bus) {
2901 -#ifdef IFORCE_USB
2902 -               case IFORCE_USB:
2903 -                       if (iforce->open++)
2904 -                               break;
2905 -                       iforce->irq.dev = iforce->usbdev;
2906 -                       if (usb_submit_urb(&iforce->irq))
2907 -                                       return -EIO;
2908 -                       break;
2909 -#endif
2910 -       }
2911 -       return 0;
2912 -}
2913 -
2914 -static void iforce_close(struct input_dev *dev)
2915 -{
2916 -       struct iforce *iforce = dev->private;
2917 -
2918 -       switch (iforce->bus) {
2919 -#ifdef IFORCE_USB
2920 -               case IFORCE_USB:
2921 -                       if (!--iforce->open)
2922 -                               usb_unlink_urb(&iforce->irq);
2923 -                       break;
2924 -#endif
2925 -       }
2926 -}
2927 -
2928 -/*
2929 - * Start or stop playing an effect
2930 - */
2931 -
2932 -static int iforce_input_event(struct input_dev *dev, unsigned int type, unsigned int code, int value)
2933 -{
2934 -       struct iforce* iforce = (struct iforce*)(dev->private);
2935 -       unsigned char data[3];
2936 -
2937 -       printk(KERN_DEBUG "iforce.c: input_event(type = %d, code = %d, value = %d)\n", type, code, value);
2938 -
2939 -       if (type != EV_FF)
2940 -               return -1;
2941 -
2942 -       switch (code) {
2943 -
2944 -               case FF_GAIN:
2945 -
2946 -                       data[0] = value >> 9;
2947 -                       send_packet(iforce, FF_CMD_GAIN, data);
2948 -
2949 -                       return 0;
2950 -
2951 -               case FF_AUTOCENTER:
2952 -
2953 -                       data[0] = 0x03;
2954 -                       data[1] = value >> 9;
2955 -                       send_packet(iforce, FF_CMD_AUTOCENTER, data);
2956 -
2957 -                       data[0] = 0x04;
2958 -                       data[1] = 0x01;
2959 -                       send_packet(iforce, FF_CMD_AUTOCENTER, data);
2960 -
2961 -                       return 0;
2962 -
2963 -               default: /* Play an effect */
2964 -
2965 -                       if (code >= iforce->dev.ff_effects_max)
2966 -                               return -1;
2967 -
2968 -                       data[0] = LO(code);
2969 -                       data[1] = (value > 0) ? ((value > 1) ? 0x41 : 0x01) : 0;
2970 -                       data[2] = LO(value);
2971 -                       send_packet(iforce, FF_CMD_PLAY, data);
2972 -
2973 -                       return 0;
2974 -       }
2975 -
2976 -       return -1;
2977 -}
2978 -
2979 -/*
2980 - * Set the magnitude of a constant force effect
2981 - * Return error code
2982 - *
2983 - * Note: caller must ensure exclusive access to device
2984 - */
2985 -
2986 -static int make_magnitude_modifier(struct iforce* iforce,
2987 -       struct resource* mod_chunk, __s16 level)
2988 -{
2989 -       unsigned char data[3];
2990 -
2991 -       if (allocate_resource(&(iforce->device_memory), mod_chunk, 2,
2992 -               iforce->device_memory.start, iforce->device_memory.end, 2L,
2993 -               NULL, NULL)) {
2994 -               return -ENOMEM;
2995 -       }
2996 -
2997 -       data[0] = LO(mod_chunk->start);
2998 -       data[1] = HI(mod_chunk->start);
2999 -       data[2] = HI(level);
3000 -
3001 -       send_packet(iforce, FF_CMD_MAGNITUDE, data);
3002 -
3003 -       return 0;
3004 -}
3005 -
3006 -/*
3007 - * Upload the component of an effect dealing with the period, phase and magnitude
3008 - */
3009 -
3010 -static int make_period_modifier(struct iforce* iforce, struct resource* mod_chunk,
3011 -       __s16 magnitude, __s16 offset, u16 period, u16 phase)
3012 -{
3013 -       unsigned char data[7];
3014 -
3015 -       period = TIME_SCALE(period);
3016 -
3017 -       if (allocate_resource(&(iforce->device_memory), mod_chunk, 0x0c,
3018 -               iforce->device_memory.start, iforce->device_memory.end, 2L,
3019 -               NULL, NULL)) {
3020 -               return -ENOMEM;
3021 -       }
3022 -
3023 -       data[0] = LO(mod_chunk->start);
3024 -       data[1] = HI(mod_chunk->start);
3025 -
3026 -       data[2] = HI(magnitude);
3027 -       data[3] = HI(offset);
3028 -       data[4] = HI(phase);
3029 -
3030 -       data[5] = LO(period);
3031 -       data[6] = HI(period);
3032 -
3033 -       send_packet(iforce, FF_CMD_PERIOD, data);
3034 -
3035 -       return 0;
3036 -}
3037 -
3038 -/*
3039 - * Uploads the part of an effect setting the shape of the force
3040 - */
3041 -
3042 -static int make_shape_modifier(struct iforce* iforce, struct resource* mod_chunk,
3043 -       u16 attack_duration, __s16 initial_level,
3044 -       u16 fade_duration, __s16 final_level)
3045 -{
3046 -       unsigned char data[8];
3047 -
3048 -       attack_duration = TIME_SCALE(attack_duration);
3049 -       fade_duration = TIME_SCALE(fade_duration);
3050 -
3051 -       if (allocate_resource(&(iforce->device_memory), mod_chunk, 0x0e,
3052 -               iforce->device_memory.start, iforce->device_memory.end, 2L,
3053 -               NULL, NULL)) {
3054 -               return -ENOMEM;
3055 -       }
3056 -
3057 -       data[0] = LO(mod_chunk->start);
3058 -       data[1] = HI(mod_chunk->start);
3059 -
3060 -       data[2] = LO(attack_duration);
3061 -       data[3] = HI(attack_duration);
3062 -       data[4] = HI(initial_level);
3063 -
3064 -       data[5] = LO(fade_duration);
3065 -       data[6] = HI(fade_duration);
3066 -       data[7] = HI(final_level);
3067 -
3068 -       send_packet(iforce, FF_CMD_SHAPE, data);
3069 -
3070 -       return 0;
3071 -}
3072 -
3073 -/*
3074 - * Component of spring, friction, inertia... effects
3075 - */
3076 -
3077 -static int make_interactive_modifier(struct iforce* iforce,
3078 -       struct resource* mod_chunk,
3079 -       __s16 rsat, __s16 lsat, __s16 rk, __s16 lk, u16 db, __s16 center)
3080 -{
3081 -       unsigned char data[10];
3082 -
3083 -       if (allocate_resource(&(iforce->device_memory), mod_chunk, 8,
3084 -               iforce->device_memory.start, iforce->device_memory.end, 2L,
3085 -               NULL, NULL)) {
3086 -               return -ENOMEM;
3087 -       }
3088 -
3089 -       data[0] = LO(mod_chunk->start);
3090 -       data[1] = HI(mod_chunk->start);
3091 -
3092 -       data[2] = HI(rk);
3093 -       data[3] = HI(lk);
3094 -
3095 -       data[4] = LO(center);
3096 -       data[5] = HI(center);
3097 -
3098 -       data[6] = LO(db);
3099 -       data[7] = HI(db);
3100 -
3101 -       data[8] = HI(rsat);
3102 -       data[9] = HI(lsat);
3103 -
3104 -       send_packet(iforce, FF_CMD_INTERACT, data);
3105 -
3106 -       return 0;
3107 -}
3108 -
3109 -static unsigned char find_button(struct iforce *iforce, signed short button)
3110 -{
3111 -       int i;
3112 -       for (i = 1; iforce->type->btn[i] >= 0; i++)
3113 -               if (iforce->type->btn[i] == button)
3114 -                       return i + 1;
3115 -       return 0;
3116 -}
3117 -
3118 -/*
3119 - * Send the part common to all effects to the device
3120 - */
3121 -
3122 -static int make_core(struct iforce* iforce, u16 id, u16 mod_id1, u16 mod_id2,
3123 -       u8 effect_type, u8 axes, u16 duration, u16 delay, u16 button,
3124 -       u16 interval, u16 direction)
3125 -{
3126 -       unsigned char data[14];
3127 -
3128 -       duration = TIME_SCALE(duration);
3129 -       delay    = TIME_SCALE(delay);
3130 -       interval = TIME_SCALE(interval);
3131 -
3132 -       data[0]  = LO(id);
3133 -       data[1]  = effect_type;
3134 -       data[2]  = LO(axes) | find_button(iforce, button);
3135 -
3136 -       data[3]  = LO(duration);
3137 -       data[4]  = HI(duration);
3138 -
3139 -       data[5]  = HI(direction);
3140 -
3141 -       data[6]  = LO(interval);
3142 -       data[7]  = HI(interval);
3143 -
3144 -       data[8]  = LO(mod_id1);
3145 -       data[9]  = HI(mod_id1);
3146 -       data[10] = LO(mod_id2);
3147 -       data[11] = HI(mod_id2);
3148 -
3149 -       data[12] = LO(delay);
3150 -       data[13] = HI(delay);
3151 -
3152 -       send_packet(iforce, FF_CMD_EFFECT, data);
3153 -
3154 -       return 0;
3155 -}
3156 -
3157 -/*
3158 - * Upload a periodic effect to the device
3159 - */
3160 -
3161 -static int iforce_upload_periodic(struct iforce* iforce, struct ff_effect* effect)
3162 -{
3163 -       u8 wave_code;
3164 -       int core_id = effect->id;
3165 -       struct iforce_core_effect* core_effect = iforce->core_effects + core_id;
3166 -       struct resource* mod1_chunk = &(iforce->core_effects[core_id].mod1_chunk);
3167 -       struct resource* mod2_chunk = &(iforce->core_effects[core_id].mod2_chunk);
3168 -       int err = 0;
3169 -
3170 -       err = make_period_modifier(iforce, mod1_chunk,
3171 -               effect->u.periodic.magnitude, effect->u.periodic.offset,
3172 -               effect->u.periodic.period, effect->u.periodic.phase);
3173 -       if (err) return err;
3174 -       set_bit(FF_MOD1_IS_USED, core_effect->flags);
3175 -
3176 -       err = make_shape_modifier(iforce, mod2_chunk,
3177 -               effect->u.periodic.shape.attack_length,
3178 -               effect->u.periodic.shape.attack_level,
3179 -               effect->u.periodic.shape.fade_length,
3180 -               effect->u.periodic.shape.fade_level);
3181 -       if (err) return err;
3182 -       set_bit(FF_MOD2_IS_USED, core_effect->flags);
3183 -
3184 -       switch (effect->u.periodic.waveform) {
3185 -               case FF_SQUARE:         wave_code = 0x20; break;
3186 -               case FF_TRIANGLE:       wave_code = 0x21; break;
3187 -               case FF_SINE:           wave_code = 0x22; break;
3188 -               case FF_SAW_UP:         wave_code = 0x23; break;
3189 -               case FF_SAW_DOWN:       wave_code = 0x24; break;
3190 -               default:                wave_code = 0x20; break;
3191 -       }
3192 -
3193 -       err = make_core(iforce, effect->id,
3194 -               mod1_chunk->start,
3195 -               mod2_chunk->start,
3196 -               wave_code,
3197 -               0x20,
3198 -               effect->replay.length,
3199 -               effect->replay.delay,
3200 -               effect->trigger.button,
3201 -               effect->trigger.interval,
3202 -               effect->u.periodic.direction);
3203 -
3204 -       return err;
3205 -}
3206 -
3207 -/*
3208 - * Upload a constant force effect
3209 - */
3210 -static int iforce_upload_constant(struct iforce* iforce, struct ff_effect* effect)
3211 -{
3212 -       int core_id = effect->id;
3213 -       struct iforce_core_effect* core_effect = iforce->core_effects + core_id;
3214 -       struct resource* mod1_chunk = &(iforce->core_effects[core_id].mod1_chunk);
3215 -       struct resource* mod2_chunk = &(iforce->core_effects[core_id].mod2_chunk);
3216 -       int err = 0;
3217 -
3218 -       printk(KERN_DEBUG "iforce.c: make constant effect\n");
3219 -
3220 -       err = make_magnitude_modifier(iforce, mod1_chunk, effect->u.constant.level);
3221 -       if (err) return err;
3222 -       set_bit(FF_MOD1_IS_USED, core_effect->flags);
3223 -
3224 -       err = make_shape_modifier(iforce, mod2_chunk,
3225 -               effect->u.constant.shape.attack_length,
3226 -               effect->u.constant.shape.attack_level,
3227 -               effect->u.constant.shape.fade_length,
3228 -               effect->u.constant.shape.fade_level);
3229 -       if (err) return err;
3230 -       set_bit(FF_MOD2_IS_USED, core_effect->flags);
3231 -
3232 -       err = make_core(iforce, effect->id,
3233 -               mod1_chunk->start,
3234 -               mod2_chunk->start,
3235 -               0x00,
3236 -               0x20,
3237 -               effect->replay.length,
3238 -               effect->replay.delay,
3239 -               effect->trigger.button,
3240 -               effect->trigger.interval,
3241 -               effect->u.constant.direction);
3242 -
3243 -       return err;
3244 -}
3245 -
3246 -/*
3247 - * Upload an interactive effect. Those are for example friction, inertia, springs...
3248 - */
3249 -static int iforce_upload_interactive(struct iforce* iforce, struct ff_effect* effect)
3250 -{
3251 -       int core_id = effect->id;
3252 -       struct iforce_core_effect* core_effect = iforce->core_effects + core_id;
3253 -       struct resource* mod_chunk = &(core_effect->mod1_chunk);
3254 -       u8 type, axes;
3255 -       u16 mod1, mod2, direction;
3256 -       int err = 0;
3257 -
3258 -       printk(KERN_DEBUG "iforce.c: make interactive effect\n");
3259 -
3260 -       switch (effect->type) {
3261 -               case FF_SPRING:         type = 0x40; break;
3262 -               case FF_FRICTION:       type = 0x41; break;
3263 -               default: return -1;
3264 -       }
3265 -
3266 -       err = make_interactive_modifier(iforce, mod_chunk,
3267 -               effect->u.interactive.right_saturation,
3268 -               effect->u.interactive.left_saturation,
3269 -               effect->u.interactive.right_coeff,
3270 -               effect->u.interactive.left_coeff,
3271 -               effect->u.interactive.deadband,
3272 -               effect->u.interactive.center);
3273 -       if (err) return err;
3274 -       set_bit(FF_MOD1_IS_USED, core_effect->flags);
3275 -
3276 -       switch ((test_bit(ABS_X, &effect->u.interactive.axis) ||
3277 -               test_bit(ABS_WHEEL, &effect->u.interactive.axis)) |
3278 -               (!!test_bit(ABS_Y, &effect->u.interactive.axis) << 1)) {
3279 -
3280 -               case 0: /* Only one axis, choose orientation */
3281 -                       mod1 = mod_chunk->start;
3282 -                       mod2 = 0xffff;
3283 -                       direction = effect->u.interactive.direction;
3284 -                       axes = 0x20;
3285 -                       break;
3286 -
3287 -               case 1: /* Only X axis */
3288 -                       mod1 = mod_chunk->start;
3289 -                       mod2 = 0xffff;
3290 -                       direction = 0x5a00;
3291 -                       axes = 0x40;
3292 -                       break;
3293 -
3294 -               case 2: /* Only Y axis */
3295 -                       mod1 = 0xffff;
3296 -                       mod2 = mod_chunk->start;
3297 -                       direction = 0xb400;
3298 -                       axes = 0x80;
3299 -                       break;
3300 -
3301 -               case 3: /* Both X and Y axes */
3302 -                       /* TODO: same setting for both axes is not mandatory */
3303 -                       mod1 = mod_chunk->start;
3304 -                       mod2 = mod_chunk->start;
3305 -                       direction = 0x6000;
3306 -                       axes = 0xc0;
3307 -                       break;
3308 -
3309 -               default:
3310 -                       return -1;
3311 -       }
3312 -
3313 -       err = make_core(iforce, effect->id,
3314 -               mod1, mod2,
3315 -               type, axes,
3316 -               effect->replay.length, effect->replay.delay,
3317 -               effect->trigger.button, effect->trigger.interval,
3318 -               direction);
3319 -
3320 -       return err;
3321 -}
3322 -
3323 -/*
3324 - * Function called when an ioctl is performed on the event dev entry.
3325 - * It uploads an effect to the device
3326 - */
3327 -static int iforce_upload_effect(struct input_dev *dev, struct ff_effect *effect)
3328 -{
3329 -       struct iforce* iforce = (struct iforce*)(dev->private);
3330 -       int id;
3331 -
3332 -       printk(KERN_DEBUG "iforce.c: upload effect\n");
3333 -
3334 -/*
3335 - * Get a free id
3336 - */
3337 -
3338 -       for (id=0; id < FF_EFFECTS_MAX; ++id)
3339 -               if (!test_bit(FF_CORE_IS_USED, iforce->core_effects[id].flags)) break;
3340 -
3341 -       if ( id == FF_EFFECTS_MAX || id >= iforce->dev.ff_effects_max)
3342 -               return -ENOMEM;
3343 -
3344 -       effect->id = id;
3345 -       set_bit(FF_CORE_IS_USED, iforce->core_effects[id].flags);
3346 -
3347 -/*
3348 - * Upload the effect
3349 - */
3350 -
3351 -       switch (effect->type) {
3352 -
3353 -               case FF_PERIODIC:
3354 -                       return iforce_upload_periodic(iforce, effect);
3355 -
3356 -               case FF_CONSTANT:
3357 -                       return iforce_upload_constant(iforce, effect);
3358 -
3359 -               case FF_SPRING:
3360 -               case FF_FRICTION:
3361 -                       return iforce_upload_interactive(iforce, effect);
3362 -
3363 -               default:
3364 -                       return -1;
3365 -       }
3366 -}
3367 -
3368 -/*
3369 - * Erases an effect: it frees the effect id and mark as unused the memory
3370 - * allocated for the parameters
3371 - */
3372 -static int iforce_erase_effect(struct input_dev *dev, int effect_id)
3373 -{
3374 -       struct iforce* iforce = (struct iforce*)(dev->private);
3375 -       int err = 0;
3376 -       struct iforce_core_effect* core_effect;
3377 -
3378 -       printk(KERN_DEBUG "iforce.c: erase effect %d\n", effect_id);
3379 -
3380 -       if (effect_id < 0 || effect_id >= FF_EFFECTS_MAX)
3381 -               return -EINVAL;
3382 -
3383 -       core_effect = iforce->core_effects + effect_id;
3384 -
3385 -       if (test_bit(FF_MOD1_IS_USED, core_effect->flags))
3386 -               err = release_resource(&(iforce->core_effects[effect_id].mod1_chunk));
3387 -
3388 -       if (!err && test_bit(FF_MOD2_IS_USED, core_effect->flags))
3389 -               err = release_resource(&(iforce->core_effects[effect_id].mod2_chunk));
3390 -
3391 -       /*TODO: remember to change that if more FF_MOD* bits are added */
3392 -       core_effect->flags[0] = 0;
3393 -
3394 -       return err;
3395 -}
3396 -static int iforce_init_device(struct iforce *iforce)
3397 -{
3398 -       unsigned char c[] = "CEOV";
3399 -       int i;
3400 -
3401 -       init_waitqueue_head(&iforce->wait);
3402 -       iforce->dev.ff_effects_max = 10;
3403 -
3404 -/*
3405 - * Input device fields.
3406 - */
3407 -
3408 -       iforce->dev.idbus = BUS_USB;
3409 -       iforce->dev.private = iforce;
3410 -       iforce->dev.name = iforce->name;
3411 -       iforce->dev.open = iforce_open;
3412 -       iforce->dev.close = iforce_close;
3413 -       iforce->dev.event = iforce_input_event;
3414 -       iforce->dev.upload_effect = iforce_upload_effect;
3415 -       iforce->dev.erase_effect = iforce_erase_effect;
3416 -
3417 -/*
3418 - * On-device memory allocation.
3419 - */
3420 -
3421 -       iforce->device_memory.name = "I-Force device effect memory";
3422 -       iforce->device_memory.start = 0;
3423 -       iforce->device_memory.end = 200;
3424 -       iforce->device_memory.flags = IORESOURCE_MEM;
3425 -       iforce->device_memory.parent = NULL;
3426 -       iforce->device_memory.child = NULL;
3427 -       iforce->device_memory.sibling = NULL;
3428 -
3429 -/*
3430 - * Wait until device ready - until it sends its first response.
3431 - */
3432 -
3433 -       for (i = 0; i < 20; i++)
3434 -               if (!get_id_packet(iforce, "O"))
3435 -                       break;
3436 -
3437 -       if (i == 20) { /* 5 seconds */
3438 -               printk(KERN_ERR "iforce.c: Timeout waiting for response from device.\n");
3439 -               iforce_close(&iforce->dev);
3440 -               return -1;
3441 -       }
3442 -
3443 -/*
3444 - * Get device info.
3445 - */
3446 -
3447 -       if (!get_id_packet(iforce, "M"))
3448 -               iforce->dev.idvendor = (iforce->edata[2] << 8) | iforce->edata[1];
3449 -       if (!get_id_packet(iforce, "P"))
3450 -               iforce->dev.idproduct = (iforce->edata[2] << 8) | iforce->edata[1];
3451 -       if (!get_id_packet(iforce, "B"))
3452 -               iforce->device_memory.end = (iforce->edata[2] << 8) | iforce->edata[1];
3453 -       if (!get_id_packet(iforce, "N"))
3454 -               iforce->dev.ff_effects_max = iforce->edata[1];
3455 -
3456 -/*
3457 - * Display additional info.
3458 - */
3459 -
3460 -       for (i = 0; c[i]; i++)
3461 -               if (!get_id_packet(iforce, c + i))
3462 -                       dump_packet("info", iforce->ecmd, iforce->edata);
3463 -
3464 -/*
3465 - * Disable spring, enable force feedback.
3466 - * FIXME: We should use iforce_set_autocenter() et al here.
3467 - */
3468 -
3469 -       send_packet(iforce, FF_CMD_AUTOCENTER, "\004\000");
3470 -       send_packet(iforce, FF_CMD_ENABLE, "\004");
3471 -
3472 -/*
3473 - * Find appropriate device entry
3474 - */
3475 -
3476 -       for (i = 0; iforce_device[i].idvendor; i++)
3477 -               if (iforce_device[i].idvendor == iforce->dev.idvendor &&
3478 -                   iforce_device[i].idproduct == iforce->dev.idproduct)
3479 -                       break;
3480 -
3481 -       iforce->type = iforce_device + i;
3482 -
3483 -       sprintf(iforce->name, iforce->type->name,
3484 -               iforce->dev.idproduct, iforce->dev.idvendor);
3485 -
3486 -/*
3487 - * Set input device bitfields and ranges.
3488 - */
3489 -
3490 -       iforce->dev.evbit[0] = BIT(EV_KEY) | BIT(EV_ABS) | BIT(EV_FF);
3491 -
3492 -       for (i = 0; iforce->type->btn[i] >= 0; i++) {
3493 -               signed short t = iforce->type->btn[i];
3494 -               set_bit(t, iforce->dev.keybit);
3495 -               if (t != BTN_DEAD)
3496 -                       set_bit(FF_BTN(t), iforce->dev.ffbit);
3497 -       }
3498 -
3499 -       for (i = 0; iforce->type->abs[i] >= 0; i++) {
3500 -
3501 -               signed short t = iforce->type->abs[i];
3502 -               set_bit(t, iforce->dev.absbit);
3503 -
3504 -               switch (t) {
3505 -
3506 -                       case ABS_X:
3507 -                       case ABS_Y:
3508 -                       case ABS_WHEEL:
3509 -
3510 -                               iforce->dev.absmax[t] =  1920;
3511 -                               iforce->dev.absmin[t] = -1920;
3512 -                               iforce->dev.absflat[t] = 128;
3513 -                               iforce->dev.absfuzz[t] = 16;
3514 -
3515 -                               set_bit(FF_ABS(t), iforce->dev.ffbit);
3516 -                               break;
3517 -
3518 -                       case ABS_THROTTLE:
3519 -                       case ABS_GAS:
3520 -                       case ABS_BRAKE:
3521 -
3522 -                               iforce->dev.absmax[t] = 255;
3523 -                               iforce->dev.absmin[t] = 0;
3524 -                               break;
3525 -
3526 -                       case ABS_HAT0X:
3527 -                       case ABS_HAT0Y:
3528 -                               iforce->dev.absmax[t] =  1;
3529 -                               iforce->dev.absmin[t] = -1;
3530 -                               break;
3531 -               }
3532 -       }
3533 -
3534 -       for (i = 0; iforce->type->ff[i] >= 0; i++)
3535 -               set_bit(iforce->type->ff[i], iforce->dev.ffbit);
3536 -
3537 -/*
3538 - * Register input device.
3539 - */
3540 -
3541 -       input_register_device(&iforce->dev);
3542 -
3543 -       return 0;
3544 -}
3545 -
3546 -#ifdef IFORCE_USB
3547 -
3548 -static void iforce_usb_irq(struct urb *urb)
3549 -{
3550 -       struct iforce *iforce = urb->context;
3551 -       if (urb->status) return;
3552 -       iforce_process_packet(iforce,
3553 -               (iforce->data[0] << 8) | (urb->actual_length - 1), iforce->data + 1);
3554 -}
3555 -
3556 -static void iforce_usb_out(struct urb *urb)
3557 -{
3558 -       struct iforce *iforce = urb->context;
3559 -       if (urb->status) return;
3560 -       if (waitqueue_active(&iforce->wait))
3561 -               wake_up(&iforce->wait);
3562 -}
3563 -
3564 -static void iforce_usb_ctrl(struct urb *urb)
3565 -{
3566 -       struct iforce *iforce = urb->context;
3567 -       if (urb->status) return;
3568 -       iforce->ecmd = 0xff00 | urb->actual_length;
3569 -       if (waitqueue_active(&iforce->wait))
3570 -               wake_up(&iforce->wait);
3571 -}
3572 -
3573 -static void *iforce_usb_probe(struct usb_device *dev, unsigned int ifnum,
3574 -                               const struct usb_device_id *id)
3575 -{
3576 -       struct usb_endpoint_descriptor *epirq, *epout;
3577 -       struct iforce *iforce;
3578 -
3579 -       epirq = dev->config[0].interface[ifnum].altsetting[0].endpoint + 0;
3580 -       epout = dev->config[0].interface[ifnum].altsetting[0].endpoint + 1;
3581 -
3582 -       if (!(iforce = kmalloc(sizeof(struct iforce) + 32, GFP_KERNEL))) return NULL;
3583 -       memset(iforce, 0, sizeof(struct iforce));
3584 -
3585 -       iforce->bus = IFORCE_USB;
3586 -       iforce->usbdev = dev;
3587 -
3588 -       iforce->dr.bRequestType = USB_TYPE_VENDOR | USB_DIR_IN | USB_RECIP_INTERFACE;
3589 -       iforce->dr.wIndex = 0;
3590 -       iforce->dr.wLength = 16;
3591 -
3592 -       FILL_INT_URB(&iforce->irq, dev, usb_rcvintpipe(dev, epirq->bEndpointAddress),
3593 -                       iforce->data, 16, iforce_usb_irq, iforce, epirq->bInterval);
3594 -
3595 -       FILL_BULK_URB(&iforce->out, dev, usb_sndbulkpipe(dev, epout->bEndpointAddress),
3596 -                       iforce + 1, 32, iforce_usb_out, iforce);
3597 -
3598 -       FILL_CONTROL_URB(&iforce->ctrl, dev, usb_rcvctrlpipe(dev, 0),
3599 -                       (void*) &iforce->dr, iforce->edata, 16, iforce_usb_ctrl, iforce);
3600 -
3601 -       if (iforce_init_device(iforce)) {
3602 -               kfree(iforce);
3603 -               return NULL;
3604 -       }
3605 -
3606 -       printk(KERN_INFO "input%d: %s [%d effects, %ld bytes memory] on usb%d:%d.%d\n",
3607 -               iforce->dev.number, iforce->dev.name, iforce->dev.ff_effects_max,
3608 -               iforce->device_memory.end, dev->bus->busnum, dev->devnum, ifnum);
3609 -
3610 -       return iforce;
3611 -}
3612 -
3613 -static void iforce_usb_disconnect(struct usb_device *dev, void *ptr)
3614 -{
3615 -       struct iforce *iforce = ptr;
3616 -       usb_unlink_urb(&iforce->irq);
3617 -       input_unregister_device(&iforce->dev);
3618 -       kfree(iforce);
3619 -}
3620 -
3621 -static struct usb_device_id iforce_usb_ids [] = {
3622 -       { USB_DEVICE(0x046d, 0xc281) },         /* Logitech WingMan Force */
3623 -       { USB_DEVICE(0x046d, 0xc291) },         /* Logitech WingMan Formula Force */
3624 -       { USB_DEVICE(0x05ef, 0x020a) },         /* AVB Top Shot Pegasus */
3625 -       { USB_DEVICE(0x05ef, 0x8884) },         /* AVB Mag Turbo Force */
3626 -       { USB_DEVICE(0x06f8, 0x0001) },         /* Guillemot Race Leader Force Feedback */
3627 -       { }                                     /* Terminating entry */
3628 -};
3629 -
3630 -MODULE_DEVICE_TABLE (usb, iforce_usb_ids);
3631 -
3632 -static struct usb_driver iforce_usb_driver = {
3633 -       name:           "iforce",
3634 -       probe:          iforce_usb_probe,
3635 -       disconnect:     iforce_usb_disconnect,
3636 -       id_table:       iforce_usb_ids,
3637 -};
3638 -
3639 -#endif
3640 -
3641 -#ifdef IFORCE_232
3642 -
3643 -static void iforce_serio_irq(struct serio *serio, unsigned char data, unsigned int flags)
3644 -{
3645 -       struct iforce* iforce = serio->private;
3646 -
3647 -       if (!iforce->pkt) {
3648 -               if (data != 0x2b) {
3649 -                       return;
3650 -               }
3651 -               iforce->pkt = 1;
3652 -               return;
3653 -       }
3654 -
3655 -       if (!iforce->id) {
3656 -               if (data > 3 && data != 0xff) {
3657 -                       iforce->pkt = 0;
3658 -                       return;
3659 -               }
3660 -               iforce->id = data;
3661 -               return;
3662 -       }
3663 -
3664 -       if (!iforce->len) {
3665 -               if (data > IFORCE_MAX_LENGTH) {
3666 -                       iforce->pkt = 0;
3667 -                       iforce->id = 0;
3668 -                       return;
3669 -               }
3670 -               iforce->len = data;
3671 -               return;
3672 -       }
3673 -
3674 -       if (iforce->idx < iforce->len) {
3675 -               iforce->csum += iforce->data[iforce->idx++] = data;
3676 -               return;
3677 -       }
3678 -
3679 -       if (iforce->idx == iforce->len) {
3680 -               iforce_process_packet(iforce, (iforce->id << 8) | iforce->idx, iforce->data);
3681 -               iforce->pkt = 0;
3682 -               iforce->id  = 0;
3683 -               iforce->len = 0;
3684 -               iforce->idx = 0;
3685 -               iforce->csum = 0;
3686 -       }
3687 -}
3688 -
3689 -static void iforce_serio_connect(struct serio *serio, struct serio_dev *dev)
3690 -{
3691 -       struct iforce *iforce;
3692 -       if (serio->type != (SERIO_RS232 | SERIO_IFORCE))
3693 -               return;
3694 -
3695 -       if (!(iforce = kmalloc(sizeof(struct iforce), GFP_KERNEL))) return;
3696 -       memset(iforce, 0, sizeof(struct iforce));
3697 -
3698 -       iforce->bus = IFORCE_232;
3699 -       iforce->serio = serio;
3700 -       serio->private = iforce;
3701 -
3702 -       if (serio_open(serio, dev)) {
3703 -               kfree(iforce);
3704 -               return;
3705 -       }
3706 -
3707 -       if (iforce_init_device(iforce)) {
3708 -               serio_close(serio);
3709 -               kfree(iforce);
3710 -               return;
3711 -       }
3712 -
3713 -       printk(KERN_INFO "input%d: %s [%d effects, %ld bytes memory] on serio%d\n",
3714 -               iforce->dev.number, iforce->dev.name, iforce->dev.ff_effects_max,
3715 -               iforce->device_memory.end, serio->number);
3716 -}
3717 -
3718 -static void iforce_serio_disconnect(struct serio *serio)
3719 -{
3720 -       struct iforce* iforce = serio->private;
3721 -
3722 -       input_unregister_device(&iforce->dev);
3723 -       serio_close(serio);
3724 -       kfree(iforce);
3725 -}
3726 -
3727 -static struct serio_dev iforce_serio_dev = {
3728 -       interrupt:      iforce_serio_irq,
3729 -       connect:        iforce_serio_connect,
3730 -       disconnect:     iforce_serio_disconnect,
3731 -};
3732 -
3733 -#endif
3734 -
3735 -static int __init iforce_init(void)
3736 -{
3737 -#ifdef IFORCE_USB
3738 -       usb_register(&iforce_usb_driver);
3739 -#endif
3740 -#ifdef IFORCE_232
3741 -       serio_register_device(&iforce_serio_dev);
3742 -#endif
3743 -       return 0;
3744 -}
3745 -
3746 -static void __exit iforce_exit(void)
3747 -{
3748 -#ifdef IFORCE_USB
3749 -       usb_deregister(&iforce_usb_driver);
3750 -#endif
3751 -#ifdef IFORCE_232
3752 -       serio_unregister_device(&iforce_serio_dev);
3753 -#endif
3754 -}
3755 -
3756 -module_init(iforce_init);
3757 -module_exit(iforce_exit);
3758 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/interact.c linux-modified/drivers/char/joystick/interact.c
3759 --- linux-vanilla/drivers/char/joystick/interact.c      Thu Sep 13 00:34:06 2001
3760 +++ linux-modified/drivers/char/joystick/interact.c     Mon Jan  6 16:48:20 2003
3761 @@ -270,8 +270,8 @@
3762                 set_bit(t, interact->dev.keybit);
3763  
3764         input_register_device(&interact->dev);
3765 -       printk(KERN_INFO "input%d: %s on gameport%d.0\n",
3766 -               interact->dev.number, interact_type[interact->type].name, gameport->number);
3767 +       printk(KERN_INFO "input: %s on gameport%d.0\n",
3768 +               interact_type[interact->type].name, gameport->number);
3769  
3770         return;
3771  fail2: gameport_close(gameport);
3772 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/magellan.c linux-modified/drivers/char/joystick/magellan.c
3773 --- linux-vanilla/drivers/char/joystick/magellan.c      Thu Sep 13 00:34:06 2001
3774 +++ linux-modified/drivers/char/joystick/magellan.c     Mon Jan  6 16:48:20 2003
3775 @@ -178,7 +178,7 @@
3776  
3777         input_register_device(&magellan->dev);
3778  
3779 -       printk(KERN_INFO "input%d: %s on serio%d\n", magellan->dev.number, magellan_name, serio->number);
3780 +       printk(KERN_INFO "input: %s on serio %s\n", magellan_name, serio->name);
3781  }
3782  
3783  /*
3784 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/serio.c linux-modified/drivers/char/joystick/serio.c
3785 --- linux-vanilla/drivers/char/joystick/serio.c Thu Sep 13 00:34:06 2001
3786 +++ linux-modified/drivers/char/joystick/serio.c        Mon Jan  6 16:48:20 2003
3787 @@ -1,9 +1,7 @@
3788  /*
3789 - * $Id$
3790 + * $Id$
3791   *
3792 - *  Copyright (c) 1999-2000 Vojtech Pavlik
3793 - *
3794 - *  Sponsored by SuSE
3795 + *  Copyright (c) 1999-2001 Vojtech Pavlik
3796   */
3797  
3798  /*
3799 @@ -27,14 +25,16 @@
3800   * 
3801   * Should you need to contact me, the author, you can do so either by
3802   * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
3803 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
3804 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
3805   */
3806  
3807  #include <linux/stddef.h>
3808  #include <linux/module.h>
3809  #include <linux/serio.h>
3810 +#include <linux/errno.h>
3811  
3812  MODULE_AUTHOR("Vojtech Pavlik <vojtech@ucw.cz>");
3813 +MODULE_DESCRIPTION("Serio abstraction core");
3814  MODULE_LICENSE("GPL");
3815  
3816  EXPORT_SYMBOL(serio_register_port);
3817 @@ -47,7 +47,6 @@
3818  
3819  static struct serio *serio_list;
3820  static struct serio_dev *serio_dev;
3821 -static int serio_number;
3822  
3823  static void serio_find_dev(struct serio *serio)
3824  {
3825 @@ -69,7 +68,6 @@
3826  
3827  void serio_register_port(struct serio *serio)
3828  {
3829 -       serio->number = serio_number++;
3830         serio->next = serio_list;       
3831         serio_list = serio;
3832         serio_find_dev(serio);
3833 @@ -84,8 +82,6 @@
3834  
3835         if (serio->dev && serio->dev->disconnect)
3836                 serio->dev->disconnect(serio);
3837 -
3838 -       serio_number--;
3839  }
3840  
3841  void serio_register_device(struct serio_dev *dev)
3842 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/serport.c linux-modified/drivers/char/joystick/serport.c
3843 --- linux-vanilla/drivers/char/joystick/serport.c       Thu Sep 13 00:34:06 2001
3844 +++ linux-modified/drivers/char/joystick/serport.c      Mon Jan  6 16:48:20 2003
3845 @@ -1,9 +1,7 @@
3846  /*
3847 - * $Id$
3848 + * $Id$
3849   *
3850   *  Copyright (c) 1999-2001 Vojtech Pavlik
3851 - *
3852 - *  Sponsored by SuSE
3853   */
3854  
3855  /*
3856 @@ -28,7 +26,7 @@
3857   * 
3858   *  Should you need to contact me, the author, you can do so either by
3859   * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
3860 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
3861 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
3862   */
3863  
3864  #include <asm/uaccess.h>
3865 @@ -39,12 +37,19 @@
3866  #include <linux/serio.h>
3867  #include <linux/tty.h>
3868  
3869 +MODULE_AUTHOR("Vojtech Pavlik <vojtech@ucw.cz>");
3870 +MODULE_DESCRIPTION("Input device TTY line discipline");
3871 +MODULE_LICENSE("GPL");
3872 +
3873  struct serport {
3874         struct tty_struct *tty;
3875         wait_queue_head_t wait;
3876         struct serio serio;
3877 +       char phys[32];
3878  };
3879  
3880 +char serport_name[] = "Serial port";
3881 +
3882  /*
3883   * Callback functions from the serio code.
3884   */
3885 @@ -75,6 +80,8 @@
3886  static int serport_ldisc_open(struct tty_struct *tty)
3887  {
3888         struct serport *serport;
3889 +       char ttyname[64];
3890 +       int i;
3891  
3892         MOD_INC_USE_COUNT;
3893  
3894 @@ -85,9 +92,19 @@
3895  
3896         memset(serport, 0, sizeof(struct serport));
3897  
3898 +       set_bit(TTY_DO_WRITE_WAKEUP, &tty->flags);
3899         serport->tty = tty;
3900         tty->disc_data = serport;
3901  
3902 +       strcpy(ttyname, tty->driver.name);
3903 +       for (i = 0; ttyname[i] != 0 && ttyname[i] != '/'; i++);
3904 +       ttyname[i] = 0;
3905 +
3906 +       sprintf(serport->phys, "%s%d/serio0", ttyname, MINOR(tty->device) - tty->driver.minor_start);
3907 +
3908 +       serport->serio.name = serport_name;
3909 +       serport->serio.phys = serport->phys;
3910 +
3911         serport->serio.type = SERIO_RS232;
3912         serport->serio.write = serport_serio_write;
3913         serport->serio.open = serport_serio_open;
3914 @@ -156,14 +173,14 @@
3915  
3916         serio_register_port(&serport->serio);
3917  
3918 -       printk(KERN_INFO "serio%d: Serial port %s\n", serport->serio.number, name);
3919 +       printk(KERN_INFO "serio: Serial port %s\n", name);
3920  
3921         add_wait_queue(&serport->wait, &wait);
3922 -       current->state = TASK_INTERRUPTIBLE;
3923 +       set_current_state(TASK_INTERRUPTIBLE);
3924  
3925         while(serport->serio.type && !signal_pending(current)) schedule();
3926  
3927 -       current->state = TASK_RUNNING;
3928 +       set_current_state(TASK_RUNNING);
3929         remove_wait_queue(&serport->wait, &wait);
3930  
3931         serio_unregister_port(&serport->serio);
3932 @@ -187,6 +204,14 @@
3933         return -EINVAL;
3934  }
3935  
3936 +static void serport_ldisc_write_wakeup(struct tty_struct * tty)
3937 +{
3938 +       struct serport *sp = (struct serport *) tty->disc_data;
3939 +
3940 +       serio_dev_write_wakeup(&sp->serio);
3941 +
3942 +}
3943 +
3944  /*
3945   * The line discipline structure.
3946   */
3947 @@ -199,6 +224,7 @@
3948         ioctl:          serport_ldisc_ioctl,
3949         receive_buf:    serport_ldisc_receive,
3950         receive_room:   serport_ldisc_room,
3951 +       write_wakeup:   serport_ldisc_write_wakeup
3952  };
3953  
3954  /*
3955 @@ -222,5 +248,3 @@
3956  
3957  module_init(serport_init);
3958  module_exit(serport_exit);
3959 -
3960 -MODULE_LICENSE("GPL");
3961 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/sidewinder.c linux-modified/drivers/char/joystick/sidewinder.c
3962 --- linux-vanilla/drivers/char/joystick/sidewinder.c    Thu Sep 13 00:34:06 2001
3963 +++ linux-modified/drivers/char/joystick/sidewinder.c   Mon Jan  6 16:48:20 2003
3964 @@ -719,8 +719,8 @@
3965                         set_bit(code, sw->dev[i].keybit);
3966  
3967                 input_register_device(sw->dev + i);
3968 -               printk(KERN_INFO "input%d: %s%s on gameport%d.%d [%d-bit id %d data %d]\n",
3969 -                       sw->dev[i].number, sw->name, comment, gameport->number, i, m, l, k);
3970 +               printk(KERN_INFO "input: %s%s on gameport%d.%d [%d-bit id %d data %d]\n",
3971 +                       sw->name, comment, gameport->number, i, m, l, k);
3972         }
3973  
3974         return;
3975 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/spaceball.c linux-modified/drivers/char/joystick/spaceball.c
3976 --- linux-vanilla/drivers/char/joystick/spaceball.c     Thu Sep 13 00:34:06 2001
3977 +++ linux-modified/drivers/char/joystick/spaceball.c    Mon Jan  6 16:48:20 2003
3978 @@ -81,8 +81,8 @@
3979                 case '@':                                       /* Reset packet */
3980                         spaceball->data[spaceball->idx - 1] = 0;
3981                         for (i = 1; i < spaceball->idx && spaceball->data[i] == ' '; i++);
3982 -                       printk(KERN_INFO "input%d: %s [%s] on serio%d\n",
3983 -                               spaceball->dev.number, spaceball_name, spaceball->data + i, spaceball->serio->number);
3984 +                       printk(KERN_INFO "input: %s [%s] on serio %s\n",
3985 +                               spaceball_name, spaceball->data + i, spaceball->serio->name);
3986                         break;
3987  
3988                 case 'D':                                       /* Ball data */
3989 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/spaceorb.c linux-modified/drivers/char/joystick/spaceorb.c
3990 --- linux-vanilla/drivers/char/joystick/spaceorb.c      Thu Sep 13 00:34:06 2001
3991 +++ linux-modified/drivers/char/joystick/spaceorb.c     Mon Jan  6 16:48:20 2003
3992 @@ -88,8 +88,8 @@
3993                 case 'R':                               /* Reset packet */
3994                         spaceorb->data[spaceorb->idx - 1] = 0;
3995                         for (i = 1; i < spaceorb->idx && spaceorb->data[i] == ' '; i++);
3996 -                       printk(KERN_INFO "input%d: %s [%s] on serio%d\n",
3997 -                                spaceorb->dev.number, spaceorb_name, spaceorb->data + i, spaceorb->serio->number);
3998 +                       printk(KERN_INFO "input: %s [%s] on serio %s\n",
3999 +                                spaceorb_name, spaceorb->data + i, spaceorb->serio->name);
4000                         break;
4001  
4002                 case 'D':                               /* Ball + button data */
4003 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/stinger.c linux-modified/drivers/char/joystick/stinger.c
4004 --- linux-vanilla/drivers/char/joystick/stinger.c       Thu Sep 13 00:34:06 2001
4005 +++ linux-modified/drivers/char/joystick/stinger.c      Mon Jan  6 16:48:20 2003
4006 @@ -168,7 +168,7 @@
4007  
4008         input_register_device(&stinger->dev);
4009  
4010 -       printk(KERN_INFO "input%d: %s on serio%d\n", stinger->dev.number, stinger_name, serio->number);
4011 +       printk(KERN_INFO "input: %s on serio %s\n", stinger_name, serio->name);
4012  }
4013  
4014  /*
4015 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/tmdc.c linux-modified/drivers/char/joystick/tmdc.c
4016 --- linux-vanilla/drivers/char/joystick/tmdc.c  Thu Sep 13 00:34:06 2001
4017 +++ linux-modified/drivers/char/joystick/tmdc.c Mon Jan  6 16:48:20 2003
4018 @@ -336,8 +336,8 @@
4019                         }
4020  
4021                         input_register_device(tmdc->dev + j);
4022 -                       printk(KERN_INFO "input%d: %s on gameport%d.%d\n",
4023 -                               tmdc->dev[j].number, tmdc->name[j], gameport->number, j);
4024 +                       printk(KERN_INFO "input: %s on gameport%d.%d\n",
4025 +                               tmdc->name[j], gameport->number, j);
4026                 }
4027  
4028         return;
4029 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/turbografx.c linux-modified/drivers/char/joystick/turbografx.c
4030 --- linux-vanilla/drivers/char/joystick/turbografx.c    Thu Sep 13 00:34:06 2001
4031 +++ linux-modified/drivers/char/joystick/turbografx.c   Mon Jan  6 16:48:20 2003
4032 @@ -190,8 +190,8 @@
4033                         tgfx->dev[i].absmin[ABS_Y] = -1; tgfx->dev[i].absmax[ABS_Y] = 1;
4034  
4035                         input_register_device(tgfx->dev + i);
4036 -                       printk(KERN_INFO "input%d: %d-button Multisystem joystick on %s\n",
4037 -                               tgfx->dev[i].number, config[i+1], tgfx->pd->port->name);
4038 +                       printk(KERN_INFO "input: %d-button Multisystem joystick on %s\n",
4039 +                               config[i+1], tgfx->pd->port->name);
4040                 }
4041  
4042          if (!tgfx->sticks) {
4043 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/char/joystick/warrior.c linux-modified/drivers/char/joystick/warrior.c
4044 --- linux-vanilla/drivers/char/joystick/warrior.c       Thu Sep 13 00:34:06 2001
4045 +++ linux-modified/drivers/char/joystick/warrior.c      Mon Jan  6 16:48:20 2003
4046 @@ -180,7 +180,7 @@
4047  
4048         input_register_device(&warrior->dev);
4049  
4050 -       printk(KERN_INFO "input%d: Logitech WingMan Warrior on serio%d\n", warrior->dev.number, serio->number);
4051 +       printk(KERN_INFO "input: Logitech WingMan Warrior on serio %s\n", serio->name);
4052  }
4053  
4054  /*
4055 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/input/evdev.c linux-modified/drivers/input/evdev.c
4056 --- linux-vanilla/drivers/input/evdev.c Mon Feb 25 21:37:58 2002
4057 +++ linux-modified/drivers/input/evdev.c        Mon Jan  6 16:48:20 2003
4058 @@ -1,11 +1,9 @@
4059  /*
4060 - * $Id$
4061 + * $Id$
4062   *
4063   *  Copyright (c) 1999-2001 Vojtech Pavlik
4064   *
4065   *  Event char devices, giving access to raw input device events.
4066 - *
4067 - *  Sponsored by SuSE
4068   */
4069  
4070  /*
4071 @@ -24,8 +22,8 @@
4072   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
4073   *
4074   * Should you need to contact me, the author, you can do so either by
4075 - * e-mail - mail your message to <vojtech@suse.cz>, or by paper mail:
4076 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
4077 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
4078 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
4079   */
4080  
4081  #define EVDEV_MINOR_BASE       64
4082 @@ -43,6 +41,7 @@
4083         int exist;
4084         int open;
4085         int minor;
4086 +       char name[16];
4087         struct input_handle handle;
4088         wait_queue_head_t wait;
4089         devfs_handle_t devfs;
4090 @@ -89,12 +88,20 @@
4091         return retval < 0 ? retval : 0;
4092  }
4093  
4094 +static int evdev_flush(struct file * file)
4095 +{
4096 +       struct evdev_list *list = (struct evdev_list*)file->private_data;
4097 +       
4098 +       if (!list->evdev->exist) return -ENODEV;
4099 +
4100 +       return input_flush_device(&list->evdev->handle, file);
4101 +}
4102 +
4103  static int evdev_release(struct inode * inode, struct file * file)
4104  {
4105         struct evdev_list *list = file->private_data;
4106         struct evdev_list **listptr;
4107  
4108 -       lock_kernel();
4109         listptr = &list->evdev->list;
4110         evdev_fasync(-1, file, 0);
4111  
4112 @@ -113,8 +120,7 @@
4113         }
4114  
4115         kfree(list);
4116 -       unlock_kernel();
4117 -
4118 +       
4119         return 0;
4120  }
4121  
4122 @@ -122,10 +128,16 @@
4123  {
4124         struct evdev_list *list;
4125         int i = MINOR(inode->i_rdev) - EVDEV_MINOR_BASE;
4126 +       int accept_err;
4127  
4128         if (i >= EVDEV_MINORS || !evdev_table[i])
4129                 return -ENODEV;
4130  
4131 +       /* Ask the driver if he wishes to accept the open() */
4132 +       if ((accept_err = input_accept_process(&(evdev_table[i]->handle), file))) {
4133 +               return accept_err;
4134 +       }
4135 +
4136         if (!(list = kmalloc(sizeof(struct evdev_list), GFP_KERNEL)))
4137                 return -ENOMEM;
4138         memset(list, 0, sizeof(struct evdev_list));
4139 @@ -149,6 +161,8 @@
4140         struct input_event event;
4141         int retval = 0;
4142  
4143 +       if (!list->evdev->exist) return -ENODEV;
4144 +
4145         while (retval < count) {
4146  
4147                 if (copy_from_user(&event, buffer + retval, sizeof(struct input_event)))
4148 @@ -169,7 +183,7 @@
4149         if (list->head == list->tail) {
4150  
4151                 add_wait_queue(&list->evdev->wait, &wait);
4152 -               current->state = TASK_INTERRUPTIBLE;
4153 +               set_current_state(TASK_INTERRUPTIBLE);
4154  
4155                 while (list->head == list->tail) {
4156  
4157 @@ -189,7 +203,7 @@
4158                         schedule();
4159                 }
4160  
4161 -               current->state = TASK_RUNNING;
4162 +               set_current_state(TASK_RUNNING);
4163                 remove_wait_queue(&list->evdev->wait, &wait);
4164         }
4165  
4166 @@ -221,7 +235,9 @@
4167         struct evdev_list *list = file->private_data;
4168         struct evdev *evdev = list->evdev;
4169         struct input_dev *dev = evdev->handle.dev;
4170 -       int retval;
4171 +       int retval, t, u;
4172 +
4173 +       if (!evdev->exist) return -ENODEV;
4174  
4175         switch (cmd) {
4176  
4177 @@ -234,6 +250,40 @@
4178                         if ((retval = put_user(dev->idproduct, ((short *) arg) + 2))) return retval;
4179                         if ((retval = put_user(dev->idversion, ((short *) arg) + 3))) return retval;
4180                         return 0;
4181 +               
4182 +               case EVIOCGREP:
4183 +                       if ((retval = put_user(dev->rep[0], ((int *) arg) + 0))) return retval;
4184 +                       if ((retval = put_user(dev->rep[1], ((int *) arg) + 1))) return retval;
4185 +                       return 0;
4186 +
4187 +               case EVIOCSREP:
4188 +                       if ((retval = get_user(dev->rep[0], ((int *) arg) + 0))) return retval;
4189 +                       if ((retval = get_user(dev->rep[1], ((int *) arg) + 1))) return retval;
4190 +                       return 0;
4191 +
4192 +               case EVIOCGKEYCODE:
4193 +                       if ((retval = get_user(t, ((int *) arg) + 0))) return retval;
4194 +                       if (t < 0 || t > dev->keycodemax) return -EINVAL;
4195 +                       switch (dev->keycodesize) {
4196 +                               case 1: u = *(u8*)(dev->keycode + t); break;
4197 +                               case 2: u = *(u16*)(dev->keycode + t * 2); break;
4198 +                               case 4: u = *(u32*)(dev->keycode + t * 4); break;
4199 +                               default: return -EINVAL;
4200 +                       }
4201 +                       if ((retval = put_user(u, ((int *) arg) + 1))) return retval;
4202 +                       return 0;
4203 +
4204 +               case EVIOCSKEYCODE:
4205 +                       if ((retval = get_user(t, ((int *) arg) + 0))) return retval;
4206 +                       if (t < 0 || t > dev->keycodemax) return -EINVAL;
4207 +                       if ((retval = get_user(u, ((int *) arg) + 1))) return retval;
4208 +                       switch (dev->keycodesize) {
4209 +                               case 1: *(u8*)(dev->keycode + t) = u; break;
4210 +                               case 2: *(u16*)(dev->keycode + t * 2) = u; break;
4211 +                               case 4: *(u32*)(dev->keycode + t * 4) = u; break;
4212 +                               default: return -EINVAL;
4213 +                       }
4214 +                       return 0;
4215  
4216                 case EVIOCSFF:
4217                         if (dev->upload_effect) {
4218 @@ -282,22 +332,55 @@
4219                                         default: return -EINVAL;
4220                                 }
4221                                 len = NBITS(len) * sizeof(long);
4222 -                               if (len > _IOC_SIZE(cmd)) {
4223 -                                       printk(KERN_WARNING "evdev.c: Truncating bitfield length from %d to %d\n",
4224 -                                               len, _IOC_SIZE(cmd));
4225 -                                       len = _IOC_SIZE(cmd);
4226 -                               }
4227 +                               if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd);
4228                                 return copy_to_user((char *) arg, bits, len) ? -EFAULT : len;
4229                         }
4230  
4231 +                       if (_IOC_NR(cmd) == _IOC_NR(EVIOCGKEY(0))) {
4232 +                               int len;
4233 +                               len = NBITS(KEY_MAX) * sizeof(long);
4234 +                               if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd);
4235 +                               return copy_to_user((char *) arg, dev->key, len) ? -EFAULT : len;
4236 +                       }
4237 +
4238 +                       if (_IOC_NR(cmd) == _IOC_NR(EVIOCGLED(0))) {
4239 +                               int len;
4240 +                               len = NBITS(LED_MAX) * sizeof(long);
4241 +                               if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd);
4242 +                               return copy_to_user((char *) arg, dev->led, len) ? -EFAULT : len;
4243 +                       }
4244 +
4245 +                       if (_IOC_NR(cmd) == _IOC_NR(EVIOCGSND(0))) {
4246 +                               int len;
4247 +                               len = NBITS(SND_MAX) * sizeof(long);
4248 +                               if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd);
4249 +                               return copy_to_user((char *) arg, dev->snd, len) ? -EFAULT : len;
4250 +                       }
4251 +
4252                         if (_IOC_NR(cmd) == _IOC_NR(EVIOCGNAME(0))) {
4253                                 int len;
4254 -                               if (!dev->name) return 0;
4255 +                               if (!dev->name) return -ENOENT;
4256                                 len = strlen(dev->name) + 1;
4257                                 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd);
4258                                 return copy_to_user((char *) arg, dev->name, len) ? -EFAULT : len;
4259                         }
4260  
4261 +                       if (_IOC_NR(cmd) == _IOC_NR(EVIOCGPHYS(0))) {
4262 +                               int len;
4263 +                               if (!dev->phys) return -ENOENT;
4264 +                               len = strlen(dev->phys) + 1;
4265 +                               if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd);
4266 +                               return copy_to_user((char *) arg, dev->phys, len) ? -EFAULT : len;
4267 +                       }
4268 +
4269 +                       if (_IOC_NR(cmd) == _IOC_NR(EVIOCGUNIQ(0))) {
4270 +                               int len;
4271 +                               if (!dev->uniq) return -ENOENT;
4272 +                               len = strlen(dev->uniq) + 1;
4273 +                               if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd);
4274 +                               return copy_to_user((char *) arg, dev->uniq, len) ? -EFAULT : len;
4275 +                       }
4276 +
4277                         if ((_IOC_NR(cmd) & ~ABS_MAX) == _IOC_NR(EVIOCGABS(0))) {
4278  
4279                                 int t = _IOC_NR(cmd) & ABS_MAX;
4280 @@ -323,9 +406,10 @@
4281         release:        evdev_release,
4282         ioctl:          evdev_ioctl,
4283         fasync:         evdev_fasync,
4284 +       flush:          evdev_flush
4285  };
4286  
4287 -static struct input_handle *evdev_connect(struct input_handler *handler, struct input_dev *dev)
4288 +static struct input_handle *evdev_connect(struct input_handler *handler, struct input_dev *dev, struct input_device_id *id)
4289  {
4290         struct evdev *evdev;
4291         int minor;
4292 @@ -344,16 +428,17 @@
4293  
4294         evdev->minor = minor;
4295         evdev_table[minor] = evdev;
4296 +       
4297 +       sprintf(evdev->name, "event%d", minor);
4298  
4299         evdev->handle.dev = dev;
4300 +       evdev->handle.name = evdev->name;
4301         evdev->handle.handler = handler;
4302         evdev->handle.private = evdev;
4303  
4304 -       evdev->exist = 1;
4305 -
4306         evdev->devfs = input_register_minor("event%d", minor, EVDEV_MINOR_BASE);
4307  
4308 -//     printk(KERN_INFO "event%d: Event device for input%d\n", minor, dev->number);
4309 +       evdev->exist = 1;
4310  
4311         return &evdev->handle;
4312  }
4313 @@ -374,12 +459,21 @@
4314         }
4315  }
4316  
4317 +static struct input_device_id evdev_ids[] = {
4318 +       { driver_info: 1 },     /* Matches all devices */
4319 +       { },                    /* Terminating zero entry */
4320 +};
4321 +
4322 +MODULE_DEVICE_TABLE(input, evdev_ids);
4323 +
4324  static struct input_handler evdev_handler = {
4325         event:          evdev_event,
4326         connect:        evdev_connect,
4327         disconnect:     evdev_disconnect,
4328         fops:           &evdev_fops,
4329         minor:          EVDEV_MINOR_BASE,
4330 +       name:           "evdev",
4331 +       id_table:       evdev_ids,
4332  };
4333  
4334  static int __init evdev_init(void)
4335 @@ -396,7 +490,6 @@
4336  module_init(evdev_init);
4337  module_exit(evdev_exit);
4338  
4339 -MODULE_AUTHOR("Vojtech Pavlik <vojtech@suse.cz>");
4340 -MODULE_DESCRIPTION("Event character device driver");
4341 +MODULE_AUTHOR("Vojtech Pavlik <vojtech@ucw.cz>");
4342 +MODULE_DESCRIPTION("Input driver event char devices");
4343  MODULE_LICENSE("GPL");
4344 -
4345 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/input/input.c linux-modified/drivers/input/input.c
4346 --- linux-vanilla/drivers/input/input.c Mon Jan  6 15:58:02 2003
4347 +++ linux-modified/drivers/input/input.c        Mon Jan  6 16:48:20 2003
4348 @@ -1,11 +1,9 @@
4349  /*
4350 - * $Id$
4351 + * $Id$
4352   *
4353   *  Copyright (c) 1999-2001 Vojtech Pavlik
4354   *
4355 - *  The input layer module itself
4356 - *
4357 - *  Sponsored by SuSE
4358 + *  The input core
4359   */
4360  
4361  /*
4362 @@ -24,8 +22,8 @@
4363   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
4364   * 
4365   * Should you need to contact me, the author, you can do so either by
4366 - * e-mail - mail your message to <vojtech@suse.cz>, or by paper mail:
4367 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
4368 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
4369 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
4370   */
4371  
4372  #include <linux/init.h>
4373 @@ -34,12 +32,16 @@
4374  #include <linux/input.h>
4375  #include <linux/module.h>
4376  #include <linux/random.h>
4377 +#include <linux/pm.h>
4378 +#include <linux/proc_fs.h>
4379 +#include <linux/kmod.h>
4380 +#include <linux/interrupt.h>
4381 +#include <linux/poll.h>
4382  
4383 -MODULE_AUTHOR("Vojtech Pavlik <vojtech@suse.cz>");
4384 -MODULE_DESCRIPTION("Input layer module");
4385 +MODULE_AUTHOR("Vojtech Pavlik <vojtech@ucw.cz>");
4386 +MODULE_DESCRIPTION("Input core");
4387  MODULE_LICENSE("GPL");
4388  
4389 -
4390  EXPORT_SYMBOL(input_register_device);
4391  EXPORT_SYMBOL(input_unregister_device);
4392  EXPORT_SYMBOL(input_register_handler);
4393 @@ -48,6 +50,8 @@
4394  EXPORT_SYMBOL(input_unregister_minor);
4395  EXPORT_SYMBOL(input_open_device);
4396  EXPORT_SYMBOL(input_close_device);
4397 +EXPORT_SYMBOL(input_accept_process);
4398 +EXPORT_SYMBOL(input_flush_device);
4399  EXPORT_SYMBOL(input_event);
4400  
4401  #define INPUT_MAJOR    13
4402 @@ -57,20 +61,32 @@
4403  static struct input_handler *input_handler;
4404  static struct input_handler *input_table[8];
4405  static devfs_handle_t input_devfs_handle;
4406 -static int input_number;
4407 -static long input_devices[NBITS(INPUT_DEVICES)];
4408 +
4409 +#ifdef CONFIG_PROC_FS
4410 +static struct proc_dir_entry *proc_bus_input_dir;
4411 +DECLARE_WAIT_QUEUE_HEAD(input_devices_poll_wait);
4412 +static int input_devices_state;
4413 +#endif
4414  
4415  void input_event(struct input_dev *dev, unsigned int type, unsigned int code, int value)
4416  {
4417         struct input_handle *handle = dev->handle;
4418  
4419  /*
4420 + * Wake up the device if it is sleeping.
4421 + */
4422 +       if (dev->pm_dev)
4423 +               pm_access(dev->pm_dev);
4424 +
4425 +/*
4426   * Filter non-events, and bad input values out.
4427   */
4428  
4429         if (type > EV_MAX || !test_bit(type, dev->evbit))
4430                 return;
4431  
4432 +       add_mouse_randomness((type << 4) ^ code ^ (code >> 4) ^ value);
4433 +
4434         switch (type) {
4435  
4436                 case EV_KEY:
4437 @@ -187,16 +203,36 @@
4438         mod_timer(&dev->timer, jiffies + dev->rep[REP_PERIOD]);
4439  }
4440  
4441 +int input_accept_process(struct input_handle *handle, struct file *file)
4442 +{
4443 +       if (handle->dev->accept)
4444 +               return handle->dev->accept(handle->dev, file);
4445 +
4446 +       return 0;
4447 +}
4448 +
4449  int input_open_device(struct input_handle *handle)
4450  {
4451 +       if (handle->dev->pm_dev)
4452 +               pm_access(handle->dev->pm_dev);
4453         handle->open++;
4454         if (handle->dev->open)
4455                 return handle->dev->open(handle->dev);
4456         return 0;
4457  }
4458  
4459 +int input_flush_device(struct input_handle* handle, struct file* file)
4460 +{
4461 +       if (handle->dev->flush)
4462 +               return handle->dev->flush(handle->dev, file);
4463 +
4464 +       return 0;
4465 +}
4466 +
4467  void input_close_device(struct input_handle *handle)
4468  {
4469 +       if (handle->dev->pm_dev)
4470 +               pm_dev_idle(handle->dev->pm_dev);
4471         if (handle->dev->close)
4472                 handle->dev->close(handle->dev);
4473         handle->open--;
4474 @@ -210,25 +246,197 @@
4475         handle->handler->handle = handle;
4476  }
4477  
4478 +/**
4479 + *     input_find_and_remove - Find and remove node
4480 + *
4481 + *     @type:          data type
4482 + *     @initval:       initial value
4483 + *     @targ:          node to find
4484 + *     @next:          next node in the list
4485 + *
4486 + *     Searches the linked list for the target node @targ. If the node
4487 + *     is found, it is removed from the list.
4488 + *
4489 + *     If the node is not found, the end of the list will be hit,
4490 + *     indicating that it wasn't in the list to begin with.
4491 + *
4492 + *     Returns nothing.
4493 + */
4494 +#define input_find_and_remove(type, initval, targ, next)               \
4495 +       do {                                                            \
4496 +               type **ptr;                                             \
4497 +               for (ptr = &initval; *ptr; ptr = &((*ptr)->next))       \
4498 +                       if (*ptr == targ) break;                        \
4499 +               if (*ptr) *ptr = (*ptr)->next;                          \
4500 +       } while (0)
4501 +
4502  static void input_unlink_handle(struct input_handle *handle)
4503  {
4504 -       struct input_handle **handleptr;
4505 +       input_find_and_remove(struct input_handle, handle->dev->handle, handle, dnext);
4506 +        input_find_and_remove(struct input_handle, handle->handler->handle, handle, hnext);
4507 +}
4508 +
4509 +#define MATCH_BIT(bit, max) \
4510 +               for (i = 0; i < NBITS(max); i++) \
4511 +                       if ((id->bit[i] & dev->bit[i]) != id->bit[i]) \
4512 +                               break; \
4513 +               if (i != NBITS(max)) \
4514 +                       continue;
4515 +
4516 +static struct input_device_id *input_match_device(struct input_device_id *id, struct input_dev *dev)
4517 +{
4518 +       int i;
4519 +
4520 +       for (; id->flags || id->driver_info; id++) {
4521 +
4522 +               if (id->flags & INPUT_DEVICE_ID_MATCH_BUS)
4523 +                       if (id->idbus != dev->idbus)
4524 +                               continue;
4525  
4526 -       handleptr = &handle->dev->handle;
4527 -       while (*handleptr && (*handleptr != handle))
4528 -               handleptr = &((*handleptr)->dnext);
4529 -       *handleptr = (*handleptr)->dnext;
4530 -
4531 -       handleptr = &handle->handler->handle;
4532 -       while (*handleptr && (*handleptr != handle))
4533 -               handleptr = &((*handleptr)->hnext);
4534 -       *handleptr = (*handleptr)->hnext;
4535 +               if (id->flags & INPUT_DEVICE_ID_MATCH_VENDOR)
4536 +                       if (id->idvendor != dev->idvendor)
4537 +                               continue;
4538 +       
4539 +               if (id->flags & INPUT_DEVICE_ID_MATCH_PRODUCT)
4540 +                       if (id->idproduct != dev->idproduct)
4541 +                               continue;
4542 +               
4543 +               if (id->flags & INPUT_DEVICE_ID_MATCH_BUS)
4544 +                       if (id->idversion != dev->idversion)
4545 +                               continue;
4546 +
4547 +               MATCH_BIT(evbit,  EV_MAX);
4548 +               MATCH_BIT(keybit, KEY_MAX);
4549 +               MATCH_BIT(relbit, REL_MAX);
4550 +               MATCH_BIT(absbit, ABS_MAX);
4551 +               MATCH_BIT(mscbit, MSC_MAX);
4552 +               MATCH_BIT(ledbit, LED_MAX);
4553 +               MATCH_BIT(sndbit, SND_MAX);
4554 +               MATCH_BIT(ffbit,  FF_MAX);
4555 +
4556 +               return id;
4557 +       }
4558 +
4559 +       return NULL;
4560  }
4561  
4562 +/*
4563 + * Input hotplugging interface - loading event handlers based on
4564 + * device bitfields.
4565 + */
4566 +
4567 +#ifdef CONFIG_HOTPLUG
4568 +
4569 +/*
4570 + * Input hotplugging invokes what /proc/sys/kernel/hotplug says
4571 + * (normally /sbin/hotplug) when input devices get added or removed.
4572 + *
4573 + * This invokes a user mode policy agent, typically helping to load driver
4574 + * or other modules, configure the device, and more.  Drivers can provide
4575 + * a MODULE_DEVICE_TABLE to help with module loading subtasks.
4576 + *
4577 + */
4578 +
4579 +#define SPRINTF_BIT_A(bit, name, max) \
4580 +       do { \
4581 +               envp[i++] = scratch; \
4582 +               scratch += sprintf(scratch, name); \
4583 +               for (j = NBITS(max) - 1; j >= 0; j--) \
4584 +                       if (dev->bit[j]) break; \
4585 +               for (; j >= 0; j--) \
4586 +                       scratch += sprintf(scratch, "%lx ", dev->bit[j]); \
4587 +               scratch++; \
4588 +       } while (0)
4589 +
4590 +#define SPRINTF_BIT_A2(bit, name, max, ev) \
4591 +       do { \
4592 +               if (test_bit(ev, dev->evbit)) \
4593 +                       SPRINTF_BIT_A(bit, name, max); \
4594 +       } while (0)
4595 +
4596 +static void input_call_hotplug(char *verb, struct input_dev *dev)
4597 +{
4598 +       char *argv[3], **envp, *buf, *scratch;
4599 +       int i = 0, j, value;
4600 +
4601 +       if (!hotplug_path[0]) {
4602 +               printk(KERN_ERR "input.c: calling hotplug a hotplug agent defined\n");
4603 +               return;
4604 +       }
4605 +       if (in_interrupt()) {
4606 +               printk(KERN_ERR "input.c: calling hotplug from interrupt\n");
4607 +               return; 
4608 +       }
4609 +       if (!current->fs->root) {
4610 +               printk(KERN_WARNING "input.c: calling hotplug without valid filesystem\n");
4611 +               return; 
4612 +       }
4613 +       if (!(envp = (char **) kmalloc(20 * sizeof(char *), GFP_KERNEL))) {
4614 +               printk(KERN_ERR "input.c: not enough memory allocating hotplug environment\n");
4615 +               return;
4616 +       }
4617 +       if (!(buf = kmalloc(1024, GFP_KERNEL))) {
4618 +               kfree (envp);
4619 +               printk(KERN_ERR "input.c: not enough memory allocating hotplug environment\n");
4620 +               return;
4621 +       }
4622 +
4623 +       argv[0] = hotplug_path;
4624 +       argv[1] = "input";
4625 +       argv[2] = 0;
4626 +
4627 +       envp[i++] = "HOME=/";
4628 +       envp[i++] = "PATH=/sbin:/bin:/usr/sbin:/usr/bin";
4629 +
4630 +       scratch = buf;
4631 +
4632 +       envp[i++] = scratch;
4633 +       scratch += sprintf(scratch, "ACTION=%s", verb) + 1;
4634 +
4635 +       envp[i++] = scratch;
4636 +       scratch += sprintf(scratch, "PRODUCT=%x/%x/%x/%x",
4637 +               dev->idbus, dev->idvendor, dev->idproduct, dev->idversion) + 1; 
4638 +       
4639 +       if (dev->name) {
4640 +               envp[i++] = scratch;
4641 +               scratch += sprintf(scratch, "NAME=%s", dev->name) + 1; 
4642 +       }
4643 +
4644 +       if (dev->phys) {
4645 +               envp[i++] = scratch;
4646 +               scratch += sprintf(scratch, "PHYS=%s", dev->phys) + 1; 
4647 +       }       
4648 +
4649 +       SPRINTF_BIT_A(evbit, "EV=", EV_MAX);
4650 +       SPRINTF_BIT_A2(keybit, "KEY=", KEY_MAX, EV_KEY);
4651 +       SPRINTF_BIT_A2(relbit, "REL=", REL_MAX, EV_REL);
4652 +       SPRINTF_BIT_A2(absbit, "ABS=", ABS_MAX, EV_ABS);
4653 +       SPRINTF_BIT_A2(mscbit, "MSC=", MSC_MAX, EV_MSC);
4654 +       SPRINTF_BIT_A2(ledbit, "LED=", LED_MAX, EV_LED);
4655 +       SPRINTF_BIT_A2(sndbit, "SND=", SND_MAX, EV_SND);
4656 +       SPRINTF_BIT_A2(ffbit,  "FF=",  FF_MAX, EV_FF);
4657 +
4658 +       envp[i++] = 0;
4659 +
4660 +       printk(KERN_DEBUG "input.c: calling %s %s [%s %s %s %s %s]\n",
4661 +               argv[0], argv[1], envp[0], envp[1], envp[2], envp[3], envp[4]);
4662 +
4663 +       value = call_usermodehelper(argv [0], argv, envp);
4664 +
4665 +       kfree(buf);
4666 +       kfree(envp);
4667 +
4668 +       if (value != 0)
4669 +               printk(KERN_WARNING "input.c: hotplug returned %d\n", value);
4670 +}
4671 +
4672 +#endif
4673 +
4674  void input_register_device(struct input_dev *dev)
4675  {
4676         struct input_handler *handler = input_handler;
4677         struct input_handle *handle;
4678 +       struct input_device_id *id;
4679  
4680  /*
4681   * Initialize repeat timer to default values.
4682 @@ -244,35 +452,70 @@
4683   * Add the device.
4684   */
4685  
4686 -       if (input_number >= INPUT_DEVICES) {
4687 -               printk(KERN_WARNING "input: ran out of input device numbers!\n");
4688 -               dev->number = input_number;
4689 -       } else {
4690 -               dev->number = find_first_zero_bit(input_devices, INPUT_DEVICES);
4691 -               set_bit(dev->number, input_devices);
4692 -       }
4693 -               
4694         dev->next = input_dev;  
4695         input_dev = dev;
4696 -       input_number++;
4697  
4698  /*
4699   * Notify handlers.
4700   */
4701  
4702         while (handler) {
4703 -               if ((handle = handler->connect(handler, dev)))
4704 -                       input_link_handle(handle);
4705 +               if ((id = input_match_device(handler->id_table, dev)))
4706 +                       if ((handle = handler->connect(handler, dev, id)))
4707 +                               input_link_handle(handle);
4708                 handler = handler->next;
4709         }
4710 +
4711 +/*
4712 + * Notify the hotplug agent.
4713 + */
4714 +
4715 +#ifdef CONFIG_HOTPLUG
4716 +       input_call_hotplug("add", dev);
4717 +#endif
4718 +
4719 +/*
4720 + * Notify /proc.
4721 + */
4722 +
4723 +#ifdef CONFIG_PROC_FS
4724 +       input_devices_state++;
4725 +       wake_up(&input_devices_poll_wait);
4726 +#endif
4727 +}
4728 +
4729 +#define DUMP_ARRAY(n, array) \
4730 +printk(KERN_DEBUG " ");\
4731 +for (i=0; i<NBITS(n); ++i)\
4732 +  printk("%0X ", array[i]);\
4733 +printk("\n");
4734 +
4735 +void dump_id_table(struct input_device_id* id)
4736 +{
4737 +       int i;
4738 +
4739 +       printk(KERN_DEBUG "flags = %0X\n", id->flags);
4740 +       if (id->flags & INPUT_DEVICE_ID_MATCH_EVBIT) {
4741 +               DUMP_ARRAY(NBITS(EV_MAX), id->evbit);
4742 +       }
4743 +       if (id->flags & INPUT_DEVICE_ID_MATCH_KEYBIT) {
4744 +               DUMP_ARRAY(NBITS(KEY_MAX), id->keybit);
4745 +       }
4746  }
4747  
4748  void input_unregister_device(struct input_dev *dev)
4749  {
4750         struct input_handle *handle = dev->handle;
4751 -       struct input_dev **devptr = &input_dev;
4752         struct input_handle *dnext;
4753  
4754 +       if (!dev) return;
4755 +
4756 +/*
4757 + * Turn off power management for the device.
4758 + */
4759 +       if (dev->pm_dev)
4760 +               pm_unregister(dev->pm_dev);
4761 +
4762  /*
4763   * Kill any pending repeat timers.
4764   */
4765 @@ -291,23 +534,35 @@
4766         }
4767  
4768  /*
4769 - * Remove the device.
4770 + * Notify the hotplug agent.
4771   */
4772  
4773 -       while (*devptr && (*devptr != dev))
4774 -               devptr = &((*devptr)->next);
4775 -       *devptr = (*devptr)->next;
4776 +#ifdef CONFIG_HOTPLUG
4777 +       input_call_hotplug("remove", dev);
4778 +#endif
4779 +
4780 +/*
4781 + * Remove the device.
4782 + */
4783 +       input_find_and_remove(struct input_dev, input_dev, dev, next);
4784  
4785 -       input_number--;
4786 +/*
4787 + * Notify /proc.
4788 + */
4789  
4790 -       if (dev->number < INPUT_DEVICES)
4791 -               clear_bit(dev->number, input_devices);
4792 +#ifdef CONFIG_PROC_FS
4793 +       input_devices_state++;
4794 +       wake_up(&input_devices_poll_wait);
4795 +#endif
4796  }
4797  
4798  void input_register_handler(struct input_handler *handler)
4799  {
4800         struct input_dev *dev = input_dev;
4801         struct input_handle *handle;
4802 +       struct input_device_id *id;
4803 +
4804 +       if (!handler) return;
4805  
4806  /*
4807   * Add minors if needed.
4808 @@ -326,17 +581,27 @@
4809  /*
4810   * Notify it about all existing devices.
4811   */
4812 +//     dump_id_table(handler->id_table);
4813  
4814         while (dev) {
4815 -               if ((handle = handler->connect(handler, dev)))
4816 -                       input_link_handle(handle);
4817 +               if ((id = input_match_device(handler->id_table, dev)))
4818 +                       if ((handle = handler->connect(handler, dev, id)))
4819 +                               input_link_handle(handle);
4820                 dev = dev->next;
4821         }
4822 +
4823 +/*
4824 + * Notify /proc.
4825 + */
4826 +
4827 +#ifdef CONFIG_PROC_FS
4828 +       input_devices_state++;
4829 +       wake_up(&input_devices_poll_wait);
4830 +#endif
4831  }
4832  
4833  void input_unregister_handler(struct input_handler *handler)
4834  {
4835 -       struct input_handler **handlerptr = &input_handler;
4836         struct input_handle *handle = handler->handle;
4837         struct input_handle *hnext;
4838  
4839 @@ -354,18 +619,23 @@
4840  /*
4841   * Remove it.
4842   */
4843 -
4844 -       while (*handlerptr && (*handlerptr != handler))
4845 -               handlerptr = &((*handlerptr)->next);
4846 -
4847 -       *handlerptr = (*handlerptr)->next;
4848 +       input_find_and_remove(struct input_handler, input_handler, handler,
4849 +                               next);
4850  
4851  /*
4852   * Remove minors.
4853   */
4854 -
4855         if (handler->fops != NULL)
4856                 input_table[handler->minor >> 5] = NULL;
4857 +
4858 +/*
4859 + * Notify /proc.
4860 + */
4861 +
4862 +#ifdef CONFIG_PROC_FS
4863 +       input_devices_state++;
4864 +       wake_up(&input_devices_poll_wait);
4865 +#endif
4866  }
4867  
4868  static int input_open_file(struct inode *inode, struct file *file)
4869 @@ -389,9 +659,7 @@
4870         old_fops = file->f_op;
4871         file->f_op = new_fops;
4872  
4873 -       lock_kernel();
4874         err = new_fops->open(inode, file);
4875 -       unlock_kernel();
4876  
4877         if (err) {
4878                 fops_put(file->f_op);
4879 @@ -419,18 +687,164 @@
4880         devfs_unregister(handle);
4881  }
4882  
4883 +/*
4884 + * ProcFS interface for the input drivers.
4885 + */
4886 +
4887 +#ifdef CONFIG_PROC_FS
4888 +
4889 +#define SPRINTF_BIT_B(bit, name, max) \
4890 +       do { \
4891 +               len += sprintf(buf + len, "B: %s", name); \
4892 +               for (i = NBITS(max) - 1; i >= 0; i--) \
4893 +                       if (dev->bit[i]) break; \
4894 +               for (; i >= 0; i--) \
4895 +                       len += sprintf(buf + len, "%lx ", dev->bit[i]); \
4896 +               len += sprintf(buf + len, "\n"); \
4897 +       } while (0)
4898 +
4899 +#define SPRINTF_BIT_B2(bit, name, max, ev) \
4900 +       do { \
4901 +               if (test_bit(ev, dev->evbit)) \
4902 +                       SPRINTF_BIT_B(bit, name, max); \
4903 +       } while (0)
4904 +
4905 +
4906 +static unsigned int input_devices_poll(struct file *file, poll_table *wait)
4907 +{
4908 +       int state = input_devices_state;
4909 +       poll_wait(file, &input_devices_poll_wait, wait);
4910 +       if (state != input_devices_state)
4911 +               return POLLIN | POLLRDNORM;
4912 +       return 0;
4913 +}
4914 +
4915 +static int input_devices_read(char *buf, char **start, off_t pos, int count, int *eof, void *data)
4916 +{
4917 +       struct input_dev *dev = input_dev;
4918 +       struct input_handle *handle;
4919 +
4920 +       off_t at = 0;
4921 +       int i, len, cnt = 0;
4922 +
4923 +       while (dev) {
4924 +
4925 +               len = sprintf(buf, "I: Bus=%04x Vendor=%04x Product=%04x Version=%04x\n",
4926 +                       dev->idbus, dev->idvendor, dev->idproduct, dev->idversion);
4927 +
4928 +               len += sprintf(buf + len, "N: Name=\"%s\"\n", dev->name ? dev->name : "");
4929 +               len += sprintf(buf + len, "P: Phys=%s\n", dev->phys ? dev->phys : "");
4930 +               len += sprintf(buf + len, "D: Drivers=");
4931 +
4932 +               handle = dev->handle;
4933 +
4934 +               while (handle) {
4935 +                       len += sprintf(buf + len, "%s ", handle->name);
4936 +                       handle = handle->dnext;
4937 +               }
4938 +
4939 +               len += sprintf(buf + len, "\n");
4940 +
4941 +               SPRINTF_BIT_B(evbit, "EV=", EV_MAX);
4942 +               SPRINTF_BIT_B2(keybit, "KEY=", KEY_MAX, EV_KEY);
4943 +               SPRINTF_BIT_B2(relbit, "REL=", REL_MAX, EV_REL);
4944 +               SPRINTF_BIT_B2(absbit, "ABS=", ABS_MAX, EV_ABS);
4945 +               SPRINTF_BIT_B2(mscbit, "MSC=", MSC_MAX, EV_MSC);
4946 +               SPRINTF_BIT_B2(ledbit, "LED=", LED_MAX, EV_LED);
4947 +               SPRINTF_BIT_B2(sndbit, "SND=", SND_MAX, EV_SND);
4948 +               SPRINTF_BIT_B2(ffbit,  "FF=",  FF_MAX, EV_FF);
4949 +
4950 +               len += sprintf(buf + len, "\n");
4951 +
4952 +               at += len;
4953 +
4954 +               if (at >= pos) {
4955 +                       if (!*start) {
4956 +                               *start = buf + (pos - (at - len));
4957 +                               cnt = at - pos;
4958 +                       } else  cnt += len;
4959 +                       buf += len;
4960 +                       if (cnt >= count)
4961 +                               break;
4962 +               }
4963 +
4964 +               dev = dev->next;
4965 +       }
4966 +
4967 +       if (!dev) *eof = 1;
4968 +
4969 +       return (count > cnt) ? cnt : count;
4970 +}
4971 +
4972 +static int input_handlers_read(char *buf, char **start, off_t pos, int count, int *eof, void *data)
4973 +{
4974 +       struct input_handler *handler = input_handler;
4975 +
4976 +       off_t at = 0;
4977 +       int len = 0, cnt = 0;
4978 +       int i = 0;
4979 +
4980 +       while (handler) {
4981 +
4982 +               if (handler->fops)
4983 +                       len = sprintf(buf, "N: Number=%d Name=%s Minor=%d\n",
4984 +                               i++, handler->name, handler->minor);
4985 +               else
4986 +                       len = sprintf(buf, "N: Number=%d Name=%s\n",
4987 +                               i++, handler->name);
4988 +
4989 +               at += len;
4990 +
4991 +               if (at >= pos) {
4992 +                       if (!*start) {
4993 +                               *start = buf + (pos - (at - len));
4994 +                               cnt = at - pos;
4995 +                       } else  cnt += len;
4996 +                       buf += len;
4997 +                       if (cnt >= count)
4998 +                               break;
4999 +               }
5000 +
5001 +               handler = handler->next;
5002 +       }
5003 +
5004 +       if (!handler) *eof = 1;
5005 +
5006 +       return (count > cnt) ? cnt : count;
5007 +}
5008 +
5009 +#endif
5010 +
5011  static int __init input_init(void)
5012  {
5013 +       struct proc_dir_entry *entry;
5014 +
5015 +#ifdef CONFIG_PROC_FS
5016 +       proc_bus_input_dir = proc_mkdir("input", proc_bus);
5017 +       proc_bus_input_dir->owner = THIS_MODULE;
5018 +       entry = create_proc_read_entry("devices", 0, proc_bus_input_dir, input_devices_read, NULL);
5019 +       entry->owner = THIS_MODULE;
5020 +       entry->proc_fops->poll = input_devices_poll;
5021 +       entry = create_proc_read_entry("handlers", 0, proc_bus_input_dir, input_handlers_read, NULL);
5022 +       entry->owner = THIS_MODULE;
5023 +#endif
5024         if (devfs_register_chrdev(INPUT_MAJOR, "input", &input_fops)) {
5025                 printk(KERN_ERR "input: unable to register char major %d", INPUT_MAJOR);
5026                 return -EBUSY;
5027         }
5028 +
5029         input_devfs_handle = devfs_mk_dir(NULL, "input", NULL);
5030 +
5031         return 0;
5032  }
5033  
5034  static void __exit input_exit(void)
5035  {
5036 +#ifdef CONFIG_PROC_FS
5037 +       remove_proc_entry("devices", proc_bus_input_dir);
5038 +       remove_proc_entry("handlers", proc_bus_input_dir);
5039 +       remove_proc_entry("input", proc_bus);
5040 +#endif
5041         devfs_unregister(input_devfs_handle);
5042          if (devfs_unregister_chrdev(INPUT_MAJOR, "input"))
5043                  printk(KERN_ERR "input: can't unregister char major %d", INPUT_MAJOR);
5044 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/input/joydev.c linux-modified/drivers/input/joydev.c
5045 --- linux-vanilla/drivers/input/joydev.c        Mon Feb  3 20:47:45 2003
5046 +++ linux-modified/drivers/input/joydev.c       Tue Feb  4 21:26:33 2003
5047 @@ -1,12 +1,10 @@
5048  /*
5049 - * $Id$
5050 + * $Id$
5051   *
5052 - *  Copyright (c) 1999-2000 Vojtech Pavlik 
5053 + *  Copyright (c) 1999-2001 Vojtech Pavlik 
5054   *  Copyright (c) 1999 Colin Van Dyke 
5055   *
5056   *  Joystick device driver for the input driver suite.
5057 - *
5058 - *  Sponsored by SuSE and Intel
5059   */
5060  
5061  /*
5062 @@ -25,8 +23,8 @@
5063   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
5064   * 
5065   * Should you need to contact me, the author, you can do so either by
5066 - * e-mail - mail your message to <vojtech@suse.cz>, or by paper mail:
5067 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
5068 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
5069 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
5070   */
5071  
5072  #include <asm/io.h>
5073 @@ -46,6 +44,11 @@
5074  #include <linux/init.h>
5075  #include <linux/smp_lock.h>
5076  
5077 +MODULE_AUTHOR("Vojtech Pavlik <vojtech@ucw.cz>");
5078 +MODULE_DESCRIPTION("Joystick device interfaces");
5079 +MODULE_SUPPORTED_DEVICE("input/js");
5080 +MODULE_LICENSE("GPL");
5081 +
5082  #define JOYDEV_MINOR_BASE      0
5083  #define JOYDEV_MINORS          32
5084  #define JOYDEV_BUFFER_SIZE     64
5085 @@ -56,6 +59,7 @@
5086         int exist;
5087         int open;
5088         int minor;
5089 +       char name[16];
5090         struct input_handle handle;
5091         wait_queue_head_t wait;
5092         devfs_handle_t devfs;
5093 @@ -84,11 +88,6 @@
5094  
5095  static struct joydev *joydev_table[JOYDEV_MINORS];
5096  
5097 -MODULE_AUTHOR("Vojtech Pavlik <vojtech@suse.cz>");
5098 -MODULE_DESCRIPTION("Joystick device driver");
5099 -MODULE_LICENSE("GPL");
5100 -MODULE_SUPPORTED_DEVICE("input/js");
5101 -
5102  static int joydev_correct(int value, struct js_corr *corr)
5103  {
5104         switch (corr->type) {
5105 @@ -167,7 +166,6 @@
5106         struct joydev_list *list = file->private_data;
5107         struct joydev_list **listptr;
5108  
5109 -       lock_kernel();
5110         listptr = &list->joydev->list;
5111         joydev_fasync(-1, file, 0);
5112  
5113 @@ -186,7 +184,6 @@
5114         }
5115  
5116         kfree(list);
5117 -       unlock_kernel();
5118  
5119         return 0;
5120  }
5121 @@ -254,10 +251,15 @@
5122         if (list->head == list->tail && list->startup == joydev->nabs + joydev->nkey) {
5123  
5124                 add_wait_queue(&list->joydev->wait, &wait);
5125 -               current->state = TASK_INTERRUPTIBLE;
5126 +               set_current_state(TASK_INTERRUPTIBLE);
5127  
5128                 while (list->head == list->tail) {
5129  
5130 +                       if (!joydev->exist) {
5131 +                               retval = -ENODEV;
5132 +                               break;
5133 +                       }
5134 +
5135                         if (file->f_flags & O_NONBLOCK) {
5136                                 retval = -EAGAIN;
5137                                 break;
5138 @@ -270,7 +272,7 @@
5139                         schedule();
5140                 }
5141  
5142 -               current->state = TASK_RUNNING;
5143 +               set_current_state(TASK_RUNNING);
5144                 remove_wait_queue(&list->joydev->wait, &wait);
5145         }
5146  
5147 @@ -329,6 +331,8 @@
5148         struct input_dev *dev = joydev->handle.dev;
5149         int i;
5150  
5151 +       if (!joydev->exist) return -ENODEV;
5152 +
5153         switch (cmd) {
5154  
5155                 case JS_SET_CAL:
5156 @@ -410,16 +414,11 @@
5157         fasync:         joydev_fasync,
5158  };
5159  
5160 -static struct input_handle *joydev_connect(struct input_handler *handler, struct input_dev *dev)
5161 +static struct input_handle *joydev_connect(struct input_handler *handler, struct input_dev *dev, struct input_device_id *id)
5162  {
5163         struct joydev *joydev;
5164         int i, j, t, minor;
5165  
5166 -       if (!(test_bit(EV_KEY, dev->evbit) && test_bit(EV_ABS, dev->evbit) &&
5167 -            (test_bit(ABS_X, dev->absbit) || test_bit(ABS_Y, dev->absbit)) &&
5168 -            (test_bit(BTN_TRIGGER, dev->keybit) || test_bit(BTN_A, dev->keybit)
5169 -               || test_bit(BTN_1, dev->keybit)))) return NULL; 
5170 -
5171         for (minor = 0; minor < JOYDEV_MINORS && joydev_table[minor]; minor++);
5172         if (minor == JOYDEV_MINORS) {
5173                 printk(KERN_ERR "joydev: no more free joydev devices\n");
5174 @@ -435,12 +434,13 @@
5175         joydev->minor = minor;
5176         joydev_table[minor] = joydev;
5177  
5178 +       sprintf(joydev->name, "js%d", minor);
5179 +
5180         joydev->handle.dev = dev;
5181 +       joydev->handle.name = joydev->name;
5182         joydev->handle.handler = handler;
5183         joydev->handle.private = joydev;
5184  
5185 -       joydev->exist = 1;
5186 -
5187         for (i = 0; i < ABS_MAX; i++)
5188                 if (test_bit(i, dev->absbit)) {
5189                         joydev->absmap[i] = joydev->nabs;
5190 @@ -484,6 +484,8 @@
5191  
5192  //     printk(KERN_INFO "js%d: Joystick device for input%d\n", minor, dev->number);
5193  
5194 +       joydev->exist = 1;
5195 +
5196         return &joydev->handle;
5197  }
5198  
5199 @@ -502,12 +504,35 @@
5200         }
5201  }
5202  
5203 +static struct input_device_id joydev_ids[] = {
5204 +       {
5205 +               flags: INPUT_DEVICE_ID_MATCH_EVBIT | INPUT_DEVICE_ID_MATCH_ABSBIT,
5206 +               evbit: { BIT(EV_KEY) | BIT(EV_ABS) },
5207 +               absbit: { BIT(ABS_X) },
5208 +       },
5209 +       {
5210 +               flags: INPUT_DEVICE_ID_MATCH_EVBIT | INPUT_DEVICE_ID_MATCH_ABSBIT,
5211 +               evbit: { BIT(EV_KEY) | BIT(EV_ABS) },
5212 +               absbit: { BIT(ABS_WHEEL) },
5213 +       },
5214 +       {
5215 +               flags: INPUT_DEVICE_ID_MATCH_EVBIT | INPUT_DEVICE_ID_MATCH_ABSBIT,
5216 +               evbit: { BIT(EV_KEY) | BIT(EV_ABS) },
5217 +               absbit: { BIT(ABS_THROTTLE) },
5218 +       },
5219 +       { },    /* Terminating entry */
5220 +};
5221 +
5222 +MODULE_DEVICE_TABLE(input, joydev_ids);
5223 +
5224  static struct input_handler joydev_handler = {
5225         event:          joydev_event,
5226         connect:        joydev_connect,
5227         disconnect:     joydev_disconnect,
5228         fops:           &joydev_fops,
5229         minor:          JOYDEV_MINOR_BASE,
5230 +       name:           "joydev",
5231 +       id_table:       joydev_ids,
5232  };
5233  
5234  static int __init joydev_init(void)
5235 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/input/keybdev.c linux-modified/drivers/input/keybdev.c
5236 --- linux-vanilla/drivers/input/keybdev.c       Thu Oct 11 18:14:32 2001
5237 +++ linux-modified/drivers/input/keybdev.c      Mon Jan  6 16:48:20 2003
5238 @@ -177,20 +177,11 @@
5239         tasklet_schedule(&keyboard_tasklet);
5240  }
5241  
5242 -static struct input_handle *keybdev_connect(struct input_handler *handler, struct input_dev *dev)
5243 +static struct input_handle *keybdev_connect(struct input_handler *handler, struct input_dev *dev, struct input_device_id* id)
5244  {
5245         struct input_handle *handle;
5246         int i;
5247  
5248 -       if (!test_bit(EV_KEY, dev->evbit))
5249 -               return NULL;
5250 -
5251 -       for (i = KEY_RESERVED; i < BTN_MISC; i++)
5252 -               if (test_bit(i, dev->keybit)) break;
5253 -
5254 -       if (i == BTN_MISC)
5255 -               return NULL;
5256 -
5257         if (!(handle = kmalloc(sizeof(struct input_handle), GFP_KERNEL)))
5258                 return NULL;
5259         memset(handle, 0, sizeof(struct input_handle));
5260 @@ -212,10 +203,25 @@
5261         kfree(handle);
5262  }
5263         
5264 +static struct input_device_id keybdev_ids[] = {
5265 +       /* If it's got an "esc" key, it's a keyboard */
5266 +       {
5267 +               flags: INPUT_DEVICE_ID_MATCH_EVBIT | INPUT_DEVICE_ID_MATCH_KEYBIT,
5268 +               evbit: { BIT(EV_KEY) | BIT(EV_REL) },
5269 +               keybit: { BIT(KEY_ESC) },
5270 +       },
5271 +         
5272 +       { },    /* Terminating entry */
5273 +};
5274 +
5275 +MODULE_DEVICE_TABLE(input, keybdev_ids);
5276 +       
5277  static struct input_handler keybdev_handler = {
5278         event:          keybdev_event,
5279         connect:        keybdev_connect,
5280         disconnect:     keybdev_disconnect,
5281 +       name:           "keybdev",
5282 +       id_table:       keybdev_ids,
5283  };
5284  
5285  static int __init keybdev_init(void)
5286 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/input/mousedev.c linux-modified/drivers/input/mousedev.c
5287 --- linux-vanilla/drivers/input/mousedev.c      Sun Sep 30 21:26:05 2001
5288 +++ linux-modified/drivers/input/mousedev.c     Mon Jan  6 16:48:20 2003
5289 @@ -1,11 +1,9 @@
5290  /*
5291 - * $Id$
5292 + * $Id$
5293   *
5294 - *  Copyright (c) 1999-2000 Vojtech Pavlik
5295 + *  Copyright (c) 1999-2001 Vojtech Pavlik
5296   *
5297 - *  Input driver to ImExPS/2 device driver module.
5298 - *
5299 - *  Sponsored by SuSE
5300 + *  Input driver to ExplorerPS/2 device driver module.
5301   */
5302  
5303  /*
5304 @@ -24,8 +22,8 @@
5305   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
5306   * 
5307   * Should you need to contact me, the author, you can do so either by
5308 - * e-mail - mail your message to <vojtech@suse.cz>, or by paper mail:
5309 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
5310 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
5311 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
5312   */
5313  
5314  #define MOUSEDEV_MINOR_BASE    32
5315 @@ -41,6 +39,10 @@
5316  #include <linux/smp_lock.h>
5317  #include <linux/random.h>
5318  
5319 +MODULE_AUTHOR("Vojtech Pavlik <vojtech@ucw.cz>");
5320 +MODULE_DESCRIPTION("Mouse (ExplorerPS/2) device interfaces");
5321 +MODULE_LICENSE("GPL");
5322 +
5323  #ifndef CONFIG_INPUT_MOUSEDEV_SCREEN_X
5324  #define CONFIG_INPUT_MOUSEDEV_SCREEN_X 1024
5325  #endif
5326 @@ -52,6 +54,7 @@
5327         int exist;
5328         int open;
5329         int minor;
5330 +       char name[16];
5331         wait_queue_head_t wait;
5332         struct mousedev_list *list;
5333         struct input_handle handle;
5334 @@ -89,8 +92,6 @@
5335         struct mousedev_list *list;
5336         int index, size;
5337  
5338 -       add_mouse_randomness((type << 4) ^ code ^ (code >> 4) ^ value);
5339 -
5340         while (*mousedev) {
5341                 list = (*mousedev)->list;
5342                 while (list) {
5343 @@ -101,13 +102,23 @@
5344                                         switch (code) {
5345                                                 case ABS_X:     
5346                                                         size = handle->dev->absmax[ABS_X] - handle->dev->absmin[ABS_X];
5347 -                                                       list->dx += (value * xres - list->oldx) / size;
5348 -                                                       list->oldx += list->dx * size;
5349 +                                                       if (size != 0) {
5350 +                                                               list->dx += (value * xres - list->oldx) / size;
5351 +                                                               list->oldx += list->dx * size;
5352 +                                                       } else {
5353 +                                                               list->dx += value - list->oldx;
5354 +                                                               list->oldx += list->dx;
5355 +                                                       }
5356                                                         break;
5357                                                 case ABS_Y:
5358                                                         size = handle->dev->absmax[ABS_Y] - handle->dev->absmin[ABS_Y];
5359 -                                                       list->dy -= (value * yres - list->oldy) / size;
5360 -                                                       list->oldy -= list->dy * size;
5361 +                                                       if (size != 0) {
5362 +                                                               list->dy -= (value * yres - list->oldy) / size;
5363 +                                                               list->oldy -= list->dy * size;
5364 +                                                       } else {
5365 +                                                               list->dy -= value - list->oldy;
5366 +                                                               list->oldy -= list->dy;
5367 +                                                       }
5368                                                         break;
5369                                         }
5370                                         break;
5371 @@ -170,7 +181,6 @@
5372         struct mousedev_list *list = file->private_data;
5373         struct mousedev_list **listptr;
5374  
5375 -       lock_kernel();
5376         listptr = &list->mousedev->list;
5377         mousedev_fasync(-1, file, 0);
5378  
5379 @@ -208,7 +218,6 @@
5380         }
5381         
5382         kfree(list);
5383 -       unlock_kernel();
5384  
5385         return 0;
5386  }
5387 @@ -216,7 +225,14 @@
5388  static int mousedev_open(struct inode * inode, struct file * file)
5389  {
5390         struct mousedev_list *list;
5391 -       int i = MINOR(inode->i_rdev) - MOUSEDEV_MINOR_BASE;
5392 +       int i;
5393 +
5394 +#ifdef CONFIG_INPUT_MOUSEDEV_PSAUX
5395 +       if (major(inode->i_rdev) == MISC_MAJOR))
5396 +               i = MOUSEDEV_MIX;
5397 +       else
5398 +#endif
5399 +               i = MINOR(inode->i_rdev) - MOUSEDEV_MINOR_BASE;
5400  
5401         if (i >= MOUSEDEV_MINORS || !mousedev_table[i])
5402                 return -ENODEV;
5403 @@ -346,7 +362,7 @@
5404         if (!list->ready && !list->buffer) {
5405  
5406                 add_wait_queue(&list->mousedev->wait, &wait);
5407 -               current->state = TASK_INTERRUPTIBLE;
5408 +               set_current_state(TASK_INTERRUPTIBLE);
5409  
5410                 while (!list->ready) {
5411  
5412 @@ -362,7 +378,7 @@
5413                         schedule();
5414                 }
5415  
5416 -               current->state = TASK_RUNNING;
5417 +               set_current_state(TASK_RUNNING);
5418                 remove_wait_queue(&list->mousedev->wait, &wait);
5419         }
5420  
5421 @@ -403,19 +419,11 @@
5422         fasync:         mousedev_fasync,
5423  };
5424  
5425 -static struct input_handle *mousedev_connect(struct input_handler *handler, struct input_dev *dev)
5426 +static struct input_handle *mousedev_connect(struct input_handler *handler, struct input_dev *dev, struct input_device_id *id)
5427  {
5428         struct mousedev *mousedev;
5429         int minor = 0;
5430  
5431 -       if (!test_bit(EV_KEY, dev->evbit) ||
5432 -          (!test_bit(BTN_LEFT, dev->keybit) && !test_bit(BTN_TOUCH, dev->keybit)))
5433 -               return NULL;
5434 -
5435 -       if ((!test_bit(EV_REL, dev->evbit) || !test_bit(REL_X, dev->relbit)) &&
5436 -           (!test_bit(EV_ABS, dev->evbit) || !test_bit(ABS_X, dev->absbit)))
5437 -               return NULL;
5438 -
5439         for (minor = 0; minor < MOUSEDEV_MINORS && mousedev_table[minor]; minor++);
5440         if (minor == MOUSEDEV_MINORS) {
5441                 printk(KERN_ERR "mousedev: no more free mousedev devices\n");
5442 @@ -427,11 +435,12 @@
5443         memset(mousedev, 0, sizeof(struct mousedev));
5444         init_waitqueue_head(&mousedev->wait);
5445  
5446 -       mousedev->exist = 1;
5447         mousedev->minor = minor;
5448         mousedev_table[minor] = mousedev;
5449 +       sprintf(mousedev->name, "mouse%d", minor);
5450  
5451         mousedev->handle.dev = dev;
5452 +       mousedev->handle.name = mousedev->name;
5453         mousedev->handle.handler = handler;
5454         mousedev->handle.private = mousedev;
5455  
5456 @@ -440,7 +449,7 @@
5457         if (mousedev_mix.open)
5458                 input_open_device(&mousedev->handle);
5459  
5460 -//     printk(KERN_INFO "mouse%d: PS/2 mouse device for input%d\n", minor, dev->number);
5461 +       mousedev->exist = 1;
5462  
5463         return &mousedev->handle;
5464  }
5465 @@ -461,6 +470,26 @@
5466                 kfree(mousedev);
5467         }
5468  }
5469 +
5470 +static struct input_device_id mousedev_ids[] = {
5471 +       {
5472 +               flags: INPUT_DEVICE_ID_MATCH_EVBIT | INPUT_DEVICE_ID_MATCH_KEYBIT | INPUT_DEVICE_ID_MATCH_RELBIT,
5473 +               evbit: { BIT(EV_KEY) | BIT(EV_REL) },
5474 +               keybit: { [LONG(BTN_LEFT)] = BIT(BTN_LEFT) },
5475 +               relbit: { BIT(REL_X) | BIT(REL_Y) },
5476 +       },      /* A mouse like device, at least one button, two relative axes */
5477 +
5478 +       {
5479 +               flags: INPUT_DEVICE_ID_MATCH_EVBIT | INPUT_DEVICE_ID_MATCH_KEYBIT | INPUT_DEVICE_ID_MATCH_ABSBIT,
5480 +               evbit: { BIT(EV_KEY) | BIT(EV_ABS) },
5481 +               keybit: { [LONG(BTN_TOUCH)] = BIT(BTN_TOUCH) },
5482 +               absbit: { BIT(ABS_X) | BIT(ABS_Y) },
5483 +       },      /* A tablet like device, at least touch detection, two absolute axes */
5484 +
5485 +       { },    /* Terminating entry */
5486 +};
5487 +
5488 +MODULE_DEVICE_TABLE(input, mousedev_ids);
5489         
5490  static struct input_handler mousedev_handler = {
5491         event:          mousedev_event,
5492 @@ -468,7 +497,15 @@
5493         disconnect:     mousedev_disconnect,
5494         fops:           &mousedev_fops,
5495         minor:          MOUSEDEV_MINOR_BASE,
5496 +       name:           "mousedev",
5497 +       id_table:       mousedev_ids,
5498 +};
5499 +
5500 +#ifdef CONFIG_INPUT_MOUSEDEV_PSAUX
5501 +static struct miscdevice psaux_mouse = {
5502 +       PSMOUSE_MINOR, "psaux", &mousedev_fops
5503  };
5504 +#endif
5505  
5506  static int __init mousedev_init(void)
5507  {
5508 @@ -480,6 +517,9 @@
5509         mousedev_mix.exist = 1;
5510         mousedev_mix.minor = MOUSEDEV_MIX;
5511         mousedev_mix.devfs = input_register_minor("mice", MOUSEDEV_MIX, MOUSEDEV_MINOR_BASE);
5512 +#ifdef CONFIG_INPUT_MOUSEDEV_PSAUX
5513 +       misc_register(&psaux_mouse)
5514 +#endif
5515  
5516         printk(KERN_INFO "mice: PS/2 mouse device common for all mice\n");
5517  
5518 @@ -488,16 +528,15 @@
5519  
5520  static void __exit mousedev_exit(void)
5521  {
5522 +#ifdef CONFIG_INPUT_MOUSEDEV_PSAUX
5523 +       misc_deregister(&psaux_mouse)
5524 +#endif
5525         input_unregister_minor(mousedev_mix.devfs);
5526         input_unregister_handler(&mousedev_handler);
5527  }
5528  
5529  module_init(mousedev_init);
5530  module_exit(mousedev_exit);
5531 -
5532 -MODULE_AUTHOR("Vojtech Pavlik <vojtech@suse.cz>");
5533 -MODULE_DESCRIPTION("Input driver to PS/2 or ImPS/2 device driver");
5534 -MODULE_LICENSE("GPL");
5535  
5536  MODULE_PARM(xres, "i");
5537  MODULE_PARM_DESC(xres, "Horizontal screen resolution");
5538 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/Config.in linux-modified/drivers/usb/Config.in
5539 --- linux-vanilla/drivers/usb/Config.in Mon Jan  6 15:58:08 2003
5540 +++ linux-modified/drivers/usb/Config.in        Mon Jan  6 16:48:20 2003
5541 @@ -62,6 +62,8 @@
5542     fi
5543        dep_mbool '    HID input layer support' CONFIG_USB_HIDINPUT $CONFIG_INPUT $CONFIG_USB_HID
5544        dep_mbool '    /dev/hiddev raw HID device support' CONFIG_USB_HIDDEV $CONFIG_USB_HID
5545 +      dep_mbool '    Force feedback support (EXPERIMENTAL)' CONFIG_HID_FF $CONFIG_USB_HID $CONFIG_EXPERIMENTAL
5546 +      dep_mbool '       Logitech WingMan 3D devices (EXPERIMENTAL)' CONFIG_LOGITECH_FF $CONFIG_HID_FF $CONFIG_EXPERIMENTAL 
5547     if [ "$CONFIG_USB_HID" != "y" ]; then
5548        dep_tristate '  USB HIDBP Keyboard (basic) support' CONFIG_USB_KBD $CONFIG_USB $CONFIG_INPUT
5549        dep_tristate '  USB HIDBP Mouse (basic) support' CONFIG_USB_MOUSE $CONFIG_USB $CONFIG_INPUT
5550 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/Makefile linux-modified/drivers/usb/Makefile
5551 --- linux-vanilla/drivers/usb/Makefile  Mon Jan  6 15:58:08 2003
5552 +++ linux-modified/drivers/usb/Makefile Mon Jan  6 16:48:20 2003
5553 @@ -34,6 +34,14 @@
5554         hid-objs        += hid-input.o
5555  endif
5556  
5557 +ifeq ($(CONFIG_HID_FF),y)
5558 +       hid-objs        += hid-ff.o
5559 +endif
5560 +
5561 +ifeq ($(CONFIG_LOGITECH_FF),y)
5562 +       hid-objs        += hid-lgff.o
5563 +endif
5564 +
5565  # Object file lists.
5566  
5567  obj-y  :=
5568 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/fixp-arith.h linux-modified/drivers/usb/fixp-arith.h
5569 --- linux-vanilla/drivers/usb/fixp-arith.h      Thu Jan  1 02:00:00 1970
5570 +++ linux-modified/drivers/usb/fixp-arith.h     Sun Mar  9 17:01:24 2003
5571 @@ -0,0 +1,100 @@
5572 +#ifndef _FIXP_ARITH_H
5573 +#define _FIXP_ARITH_H
5574 +
5575 +/*
5576 + * $$
5577 + *
5578 + * Simplistic fixed-point arithmetics.
5579 + * Hmm, I'm probably duplicating some code :(
5580 + *
5581 + * Copyright (c) 2002 Johann Deneux
5582 + */
5583 +
5584 +/*
5585 + * This program is free software; you can redistribute it and/or modify
5586 + * it under the terms of the GNU General Public License as published by
5587 + * the Free Software Foundation; either version 2 of the License, or
5588 + * (at your option) any later version.
5589 + *
5590 + * This program is distributed in the hope that it will be useful,
5591 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
5592 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
5593 + * GNU General Public License for more details.
5594 + *
5595 + * You should have received a copy of the GNU General Public License
5596 + * along with this program; if not, write to the Free Software
5597 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
5598 + *
5599 + * Should you need to contact me, the author, you can do so by
5600 + * e-mail - mail your message to <deneux@ifrance.com>
5601 + */
5602 +
5603 +#include <linux/types.h>
5604 +
5605 +// The type representing fixed-point values
5606 +typedef s16 fixp_t;
5607 +
5608 +#define FRAC_N 8
5609 +#define FRAC_MASK ((1<<FRAC_N)-1)
5610 +
5611 +// Not to be used directly. Use fixp_{cos,sin}
5612 +fixp_t cos_table[45] = {
5613 +       0x0100, 0x00FF, 0x00FF, 0x00FE, 0x00FD, 0x00FC, 0x00FA, 0x00F8,
5614 +       0x00F6, 0x00F3, 0x00F0, 0x00ED, 0x00E9, 0x00E6, 0x00E2, 0x00DD,
5615 +       0x00D9, 0x00D4, 0x00CF, 0x00C9, 0x00C4, 0x00BE, 0x00B8, 0x00B1,
5616 +       0x00AB, 0x00A4, 0x009D, 0x0096, 0x008F, 0x0087, 0x0080, 0x0078,
5617 +       0x0070, 0x0068, 0x005F, 0x0057, 0x004F, 0x0046, 0x003D, 0x0035,
5618 +       0x002C, 0x0023, 0x001A, 0x0011, 0x0008
5619 +};
5620 +
5621 +
5622 +/* a: 123 -> 123.0 */
5623 +inline fixp_t fixp_new(s16 a)
5624 +{
5625 +       return a<<FRAC_N;
5626 +}
5627 +
5628 +/* a: 0xFFFF -> -1.0
5629 +      0x8000 -> 1.0
5630 +      0x0000 -> 0.0
5631 +*/
5632 +inline fixp_t fixp_new16(s16 a)
5633 +{
5634 +       return ((s32)a)>>(16-FRAC_N);
5635 +}
5636 +
5637 +inline int fixp_toint(fixp_t x)
5638 +{
5639 +       return x>>FRAC_N;
5640 +}
5641 +
5642 +inline fixp_t fixp_cos(unsigned int degrees)
5643 +{
5644 +       int quadrant = (degrees / 90) & 3;
5645 +       unsigned int i = degrees % 90;
5646 +
5647 +       if (quadrant == 1 || quadrant == 3) {
5648 +               i = 89 - i;
5649 +       }
5650 +
5651 +       i >>= 1;
5652 +
5653 +       return (quadrant == 1 || quadrant == 2)? -cos_table[i] : cos_table[i];
5654 +}
5655 +
5656 +inline fixp_t fixp_sin(unsigned int degrees)
5657 +{
5658 +       return -fixp_cos(degrees + 90);
5659 +}
5660 +
5661 +inline fixp_t fixp_mult(fixp_t a, fixp_t b)
5662 +{
5663 +       return ((s32)(a*b))>>FRAC_N;
5664 +}
5665 +
5666 +inline fixp_t fixp_div(fixp_t a, fixp_t b)
5667 +{
5668 +       return (a/b)<<FRAC_N;
5669 +}
5670 +
5671 +#endif
5672 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/hid-core.c linux-modified/drivers/usb/hid-core.c
5673 --- linux-vanilla/drivers/usb/hid-core.c        Mon Jan  6 15:58:08 2003
5674 +++ linux-modified/drivers/usb/hid-core.c       Mon Jan 13 23:41:59 2003
5675 @@ -1,12 +1,10 @@
5676  /*
5677 - * $Id$
5678 + * $Id$
5679   *
5680   *  Copyright (c) 1999 Andreas Gal
5681   *  Copyright (c) 2000-2001 Vojtech Pavlik
5682   *
5683   *  USB HID support for Linux
5684 - *
5685 - *  Sponsored by SuSE
5686   */
5687  
5688  /*
5689 @@ -25,8 +23,8 @@
5690   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
5691   *
5692   * Should you need to contact me, the author, you can do so either by
5693 - * e-mail - mail your message to <vojtech@suse.cz>, or by paper mail:
5694 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
5695 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
5696 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
5697   */
5698  
5699  #include <linux/module.h>
5700 @@ -47,15 +45,19 @@
5701  #include <linux/usb.h>
5702  
5703  #include "hid.h"
5704 +#ifdef CONFIG_USB_HIDDEV
5705  #include <linux/hiddev.h>
5706 +#endif
5707 +
5708  
5709  /*
5710   * Version Information
5711   */
5712  
5713 -#define DRIVER_VERSION "v1.8.1"
5714 -#define DRIVER_AUTHOR "Andreas Gal, Vojtech Pavlik <vojtech@suse.cz>"
5715 -#define DRIVER_DESC "USB HID support drivers"
5716 +#define DRIVER_VERSION "v1.31"
5717 +#define DRIVER_AUTHOR "Andreas Gal, Vojtech Pavlik <vojtech@ucw.cz>"
5718 +#define DRIVER_DESC "USB HID core driver"
5719 +#define DRIVER_LICENSE "GPL"
5720  
5721  static char *hid_types[] = {"Device", "Pointer", "Mouse", "Device", "Joystick",
5722                                 "Gamepad", "Keyboard", "Keypad", "Multi-Axis Controller"};
5723 @@ -206,7 +208,6 @@
5724                 dbg("logical range invalid %d %d", parser->global.logical_minimum, parser->global.logical_maximum);
5725                 return -1;
5726         }
5727 -
5728         usages = parser->local.usage_index;
5729  
5730         offset = report->size;
5731 @@ -322,7 +323,7 @@
5732                         return 0;
5733  
5734                 case HID_GLOBAL_ITEM_TAG_UNIT_EXPONENT:
5735 -                       parser->global.unit_exponent = item_udata(item);
5736 +                       parser->global.unit_exponent = item_sdata(item);
5737                         return 0;
5738  
5739                 case HID_GLOBAL_ITEM_TAG_UNIT:
5740 @@ -507,8 +508,6 @@
5741  
5742         for (n = 0; n < report->maxfield; n++)
5743                 kfree(report->field[n]);
5744 -       if (report->data)
5745 -               kfree(report->data);
5746         kfree(report);
5747  }
5748  
5749 @@ -520,6 +519,10 @@
5750  {
5751         unsigned i,j;
5752  
5753 +#ifdef CONFIG_HID_FF
5754 +       hid_ff_exit(device);
5755 +#endif
5756 +
5757         for (i = 0; i < HID_REPORT_TYPES; i++) {
5758                 struct hid_report_enum *report_enum = device->report_enum + i;
5759  
5760 @@ -537,60 +540,64 @@
5761   * items, though they are not used yet.
5762   */
5763  
5764 -static __u8 *fetch_item(__u8 *start, __u8 *end, struct hid_item *item)
5765 +static u8 *fetch_item(__u8 *start, __u8 *end, struct hid_item *item)
5766  {
5767 -       if ((end - start) > 0) {
5768 +       u8 b;
5769  
5770 -               __u8 b = *start++;
5771 -               item->type = (b >> 2) & 3;
5772 -               item->tag  = (b >> 4) & 15;
5773 +       if ((end - start) <= 0)
5774 +               return NULL;
5775  
5776 -               if (item->tag == HID_ITEM_TAG_LONG) {
5777 +       b = *start++;
5778  
5779 -                       item->format = HID_ITEM_FORMAT_LONG;
5780 +       item->type = (b >> 2) & 3;
5781 +       item->tag  = (b >> 4) & 15;
5782  
5783 -                       if ((end - start) >= 2) {
5784 +       if (item->tag == HID_ITEM_TAG_LONG) {
5785  
5786 -                               item->size = *start++;
5787 -                               item->tag  = *start++;
5788 +               item->format = HID_ITEM_FORMAT_LONG;
5789  
5790 -                               if ((end - start) >= item->size) {
5791 -                                       item->data.longdata = start;
5792 -                                       start += item->size;
5793 -                                       return start;
5794 -                               }
5795 -                       }
5796 -               } else {
5797 +               if ((end - start) < 2)
5798 +                       return NULL;
5799  
5800 -                       item->format = HID_ITEM_FORMAT_SHORT;
5801 -                       item->size = b & 3;
5802 -                       switch (item->size) {
5803 -
5804 -                               case 0:
5805 -                                       return start;
5806 -
5807 -                               case 1:
5808 -                                       if ((end - start) >= 1) {
5809 -                                               item->data.u8 = *start++;
5810 -                                               return start;
5811 -                                       }
5812 -                                       break;
5813 -
5814 -                               case 2:
5815 -                                       if ((end - start) >= 2) {
5816 -                                               item->data.u16 = le16_to_cpu( get_unaligned(((__u16*)start)++));
5817 -                                               return start;
5818 -                                       }
5819 -
5820 -                               case 3:
5821 -                                       item->size++;
5822 -                                       if ((end - start) >= 4) {
5823 -                                               item->data.u32 = le32_to_cpu( get_unaligned(((__u32*)start)++));
5824 -                                               return start;
5825 -                                       }
5826 -                       }
5827 -               }
5828 +               item->size = *start++;
5829 +               item->tag  = *start++;
5830 +
5831 +               if ((end - start) < item->size) 
5832 +                       return NULL;
5833 +
5834 +               item->data.longdata = start;
5835 +               start += item->size;
5836 +               return start;
5837 +       } 
5838 +
5839 +       item->format = HID_ITEM_FORMAT_SHORT;
5840 +       item->size = b & 3;
5841 +
5842 +       switch (item->size) {
5843 +
5844 +               case 0:
5845 +                       return start;
5846 +
5847 +               case 1:
5848 +                       if ((end - start) < 1)
5849 +                               return NULL;
5850 +                       item->data.u8 = *start++;
5851 +                       return start;
5852 +
5853 +               case 2:
5854 +                       if ((end - start) < 2) 
5855 +                               return NULL;
5856 +                       item->data.u16 = le16_to_cpu(get_unaligned(((__u16*)start)++));
5857 +                       return start;
5858 +
5859 +               case 3:
5860 +                       item->size++;
5861 +                       if ((end - start) < 4)
5862 +                               return NULL;
5863 +                       item->data.u32 = le32_to_cpu(get_unaligned(((__u32*)start)++));
5864 +                       return start;
5865         }
5866 +
5867         return NULL;
5868  }
5869  
5870 @@ -637,12 +644,14 @@
5871  
5872         end = start + size;
5873         while ((start = fetch_item(start, end, &item)) != 0) {
5874 +
5875                 if (item.format != HID_ITEM_FORMAT_SHORT) {
5876                         dbg("unexpected long global item");
5877                         hid_free_device(device);
5878                         kfree(parser);
5879                         return NULL;
5880                 }
5881 +
5882                 if (dispatch_type[item.type](parser, &item)) {
5883                         dbg("item %u %u %u %u parsing failed\n",
5884                                 item.format, (unsigned)item.size, (unsigned)item.type, (unsigned)item.tag);
5885 @@ -735,11 +744,24 @@
5886         hid_dump_input(usage, value);
5887         if (hid->claimed & HID_CLAIMED_INPUT)
5888                 hidinput_hid_event(hid, field, usage, value);
5889 -       if (hid->claimed & HID_CLAIMED_HIDDEV)
5890 -               hiddev_hid_event(hid, usage->hid, value);
5891 +#ifdef CONFIG_USB_HIDDEV
5892 +       if (hid->claimed & HID_CLAIMED_HIDDEV) {
5893 +               struct hiddev_usage_ref uref;
5894 +               unsigned type = field->report_type;
5895 +               uref.report_type =
5896 +                       (type == HID_INPUT_REPORT) ? HID_REPORT_TYPE_INPUT :
5897 +                       ((type == HID_OUTPUT_REPORT) ? HID_REPORT_TYPE_OUTPUT :
5898 +                        ((type == HID_FEATURE_REPORT) ? HID_REPORT_TYPE_FEATURE:0));
5899 +               uref.report_id = field->report->id;
5900 +               uref.field_index = field->index;
5901 +               uref.usage_index = (usage - field->usage);
5902 +               uref.usage_code = usage->hid;
5903 +               uref.value = value;
5904 +               hiddev_hid_event(hid, &uref);
5905 +       }
5906 +#endif
5907  }
5908  
5909 -
5910  /*
5911   * Analyse a received field, and fetch the data from it. The field
5912   * content is stored for next report processing (we do differential
5913 @@ -794,9 +816,12 @@
5914         memcpy(field->value, value, count * sizeof(__s32));
5915  }
5916  
5917 -static int hid_input_report(int type, u8 *data, int len, struct hid_device *hid)
5918 +static int hid_input_report(int type, struct urb *urb)
5919  {
5920 +       struct hid_device *hid = urb->context;
5921         struct hid_report_enum *report_enum = hid->report_enum + type;
5922 +       u8 *data = urb->transfer_buffer;
5923 +       int len = urb->actual_length;
5924         struct hid_report *report;
5925         int n, size;
5926  
5927 @@ -815,95 +840,46 @@
5928                 len--;
5929         }
5930  
5931 -       if (!(report = report_enum->report_id_hash[n])) {
5932 -               dbg("undefined report_id %d received", n);
5933 -#ifdef DEBUG
5934 -                       printk(KERN_DEBUG __FILE__ ": report (size %u) = ", len);
5935 -                       for (n = 0; n < len; n++)
5936 -                               printk(" %02x", data[n]);
5937 -                       printk("\n");
5938 +#ifdef DEBUG_DATA
5939 +       {
5940 +               int i;
5941 +               printk(KERN_DEBUG __FILE__ ": report %d (size %u) = ", n, len);
5942 +               for (i = 0; i < n; i++)
5943 +                       printk(" %02x", data[i]);
5944 +               printk("\n");
5945 +       }
5946  #endif
5947  
5948 +       if (!(report = report_enum->report_id_hash[n])) {
5949 +               dbg("undefined report_id %d received", n);
5950                 return -1;
5951         }
5952  
5953         size = ((report->size - 1) >> 3) + 1;
5954  
5955         if (len < size) {
5956 -
5957 -               if (size <= 8) {
5958 -                       dbg("report %d is too short, (%d < %d)", report->id, len, size);
5959 -                       return -1;
5960 -               }
5961 -
5962 -               /*
5963 -                * Some low-speed devices have large reports and maxpacketsize 8.
5964 -                * We buffer the data in that case and parse it when we got it all.
5965 -                * Works only for unnumbered reports. Doesn't make sense for numbered
5966 -                * reports anyway - then they don't need to be large.
5967 -                */
5968 -
5969 -               if (!report->data)
5970 -                       if (!(report->data = kmalloc(size, GFP_ATOMIC))) {
5971 -                               dbg("couldn't allocate report buffer");
5972 -                               return -1;
5973 -                       }
5974 -
5975 -               if (report->idx + len > size) {
5976 -                       dbg("report data buffer overflow");
5977 -                       report->idx = 0;
5978 -                       return -1;
5979 -               }
5980 -
5981 -               memcpy(report->data + report->idx, data, len);
5982 -               report->idx += len;
5983 -
5984 -               if (report->idx < size)
5985 -                       return 0;
5986 -
5987 -               data = report->data;
5988 +               dbg("report %d is too short, (%d < %d)", report->id, len, size);
5989 +               return -1;
5990         }
5991  
5992         for (n = 0; n < report->maxfield; n++)
5993                 hid_input_field(hid, report->field[n], data);
5994  
5995 -       report->idx = 0;
5996         return 0;
5997  }
5998  
5999  /*
6000 - * Interrupt input handler.
6001 + * Input interrupt completion handler.
6002   */
6003  
6004 -static void hid_irq(struct urb *urb)
6005 +static void hid_irq_in(struct urb *urb)
6006  {
6007         if (urb->status) {
6008 -               dbg("nonzero status in irq %d", urb->status);
6009 +               dbg("nonzero status in input irq %d", urb->status);
6010                 return;
6011         }
6012  
6013 -       hid_input_report(HID_INPUT_REPORT, urb->transfer_buffer, urb->actual_length, urb->context);
6014 -}
6015 -
6016 -/*
6017 - * hid_read_report() reads in report values without waiting for an irq urb.
6018 - */
6019 -
6020 -void hid_read_report(struct hid_device *hid, struct hid_report *report)
6021 -{
6022 -       int len = ((report->size - 1) >> 3) + 1 + hid->report_enum[report->type].numbered;
6023 -       u8 data[len];
6024 -       int read;
6025 -
6026 -       if (hid->quirks & HID_QUIRK_NOGET)
6027 -               return;
6028 -
6029 -       if ((read = usb_get_report(hid->dev, hid->ifnum, report->type + 1, report->id, data, len)) != len) {
6030 -               dbg("reading report type %d id %d failed len %d read %d", report->type + 1, report->id, len, read);
6031 -               return;
6032 -       }
6033 -
6034 -       hid_input_report(report->type, data, len, hid);
6035 +       hid_input_report(HID_INPUT_REPORT, urb);
6036  }
6037  
6038  /*
6039 @@ -949,7 +925,8 @@
6040         hid_dump_input(field->usage + offset, value);
6041  
6042         if (offset >= field->report_count) {
6043 -               dbg("offset exceeds report_count");
6044 +               dbg("offset (%d) exceeds report_count (%d)", offset, field->report_count);
6045 +               hid_dump_field(field, 8);
6046                 return -1;
6047         }
6048         if (field->logical_minimum < 0) {
6049 @@ -958,11 +935,6 @@
6050                         return -1;
6051                 }
6052         }
6053 -       if (   (value > field->logical_maximum)
6054 -           || (value < field->logical_minimum)) {
6055 -               dbg("value %d is invalid", value);
6056 -               return -1;
6057 -       }
6058         field->value[offset] = value;
6059         return 0;
6060  }
6061 @@ -986,14 +958,54 @@
6062         return -1;
6063  }
6064  
6065 +/*
6066 + * Find a report with a specified HID usage.
6067 + */
6068 +
6069 +int hid_find_report_by_usage(struct hid_device *hid, __u32 wanted_usage, struct hid_report **report, int type)
6070 +{
6071 +       struct hid_report_enum *report_enum = hid->report_enum + type;
6072 +       struct list_head *list = report_enum->report_list.next;
6073 +       int i, j;
6074 +
6075 +       while (list != &report_enum->report_list) {
6076 +               *report = (struct hid_report *) list;
6077 +               list = list->next;
6078 +               for (i = 0; i < (*report)->maxfield; i++) {
6079 +                       struct hid_field *field = (*report)->field[i];
6080 +                       for (j = 0; j < field->maxusage; j++)
6081 +                               if (field->logical == wanted_usage)
6082 +                                       return j;
6083 +               }
6084 +       }
6085 +       return -1;
6086 +}
6087 +
6088 +int hid_find_field_in_report(struct hid_report *report, __u32 wanted_usage, struct hid_field **field)
6089 +{
6090 +       int i, j;
6091 +
6092 +       for (i = 0; i < report->maxfield; i++) {
6093 +               *field = report->field[i];
6094 +               for (j = 0; j < (*field)->maxusage; j++)
6095 +                       if ((*field)->usage[j].hid == wanted_usage)
6096 +                               return j;
6097 +       }
6098 +
6099 +       return -1;
6100 +}
6101 +
6102  static int hid_submit_out(struct hid_device *hid)
6103  {
6104 -       hid->urbout.transfer_buffer_length = le16_to_cpup(&hid->out[hid->outtail].dr.wLength);
6105 -       hid->urbout.transfer_buffer = hid->out[hid->outtail].buffer;
6106 -       hid->urbout.setup_packet = (void *) &(hid->out[hid->outtail].dr);
6107 -       hid->urbout.dev = hid->dev;
6108 +       struct hid_report *report;
6109  
6110 -       if (usb_submit_urb(&hid->urbout)) {
6111 +       report = hid->out[hid->outtail];
6112 +
6113 +       hid_output_report(report, hid->outbuf);
6114 +       hid->urbout->transfer_buffer_length = ((report->size - 1) >> 3) + 1;
6115 +       hid->urbout->dev = hid->dev;
6116 +
6117 +       if (usb_submit_urb(hid->urbout)) {
6118                 err("usb_submit_urb(out) failed");
6119                 return -1;
6120         }
6121 @@ -1001,33 +1013,168 @@
6122         return 0;
6123  }
6124  
6125 +static int hid_submit_ctrl(struct hid_device *hid)
6126 +{
6127 +       struct hid_report *report;
6128 +       unsigned char dir;
6129 +
6130 +       report = hid->ctrl[hid->ctrltail].report;
6131 +       dir = hid->ctrl[hid->ctrltail].dir;
6132 +
6133 +       if (dir == USB_DIR_OUT)
6134 +               hid_output_report(report, hid->ctrlbuf);
6135 +
6136 +       hid->urbctrl->transfer_buffer_length = ((report->size - 1) >> 3) + 1 + ((report->id > 0) && (dir != USB_DIR_OUT));
6137 +       hid->urbctrl->pipe = (dir == USB_DIR_OUT) ?  usb_sndctrlpipe(hid->dev, 0) : usb_rcvctrlpipe(hid->dev, 0);
6138 +       hid->urbctrl->dev = hid->dev;
6139 +
6140 +       hid->dr.bRequestType = USB_TYPE_CLASS | USB_RECIP_INTERFACE | dir;
6141 +       hid->dr.bRequest = (dir == USB_DIR_OUT) ? HID_REQ_SET_REPORT : HID_REQ_GET_REPORT;
6142 +       hid->dr.wValue = ((report->type + 1) << 8) | report->id;
6143 +       hid->dr.wIndex = cpu_to_le16(hid->ifnum);
6144 +       hid->dr.wLength = cpu_to_le16(hid->urbctrl->transfer_buffer_length);
6145 +
6146 +       if (usb_submit_urb(hid->urbctrl)) {
6147 +               err("usb_submit_urb(ctrl) failed");
6148 +               return -1;
6149 +       }
6150 +
6151 +       return 0;
6152 +}
6153 +
6154 +/*
6155 + * Output interrupt completion handler.
6156 + */
6157 +
6158 +static void hid_irq_out(struct urb *urb)
6159 +{
6160 +       struct hid_device *hid = urb->context;
6161 +       unsigned long flags;
6162 +
6163 +       if (urb->status)
6164 +               warn("output irq status %d received", urb->status);
6165 +
6166 +       spin_lock_irqsave(&hid->outlock, flags);
6167 +
6168 +       hid->outtail = (hid->outtail + 1) & (HID_OUTPUT_FIFO_SIZE - 1);
6169 +
6170 +       if (hid->outhead != hid->outtail) {
6171 +               hid_submit_out(hid);
6172 +               spin_unlock_irqrestore(&hid->outlock, flags);
6173 +               return;
6174 +       }
6175 +
6176 +       clear_bit(HID_OUT_RUNNING, &hid->iofl);
6177 +
6178 +       spin_unlock_irqrestore(&hid->outlock, flags);
6179 +
6180 +       wake_up(&hid->wait);
6181 +}
6182 +
6183 +/*
6184 + * Control pipe completion handler.
6185 + */
6186 +
6187  static void hid_ctrl(struct urb *urb)
6188  {
6189         struct hid_device *hid = urb->context;
6190 +       unsigned long flags;
6191  
6192         if (urb->status)
6193                 warn("ctrl urb status %d received", urb->status);
6194  
6195 -       hid->outtail = (hid->outtail + 1) & (HID_CONTROL_FIFO_SIZE - 1);
6196 +       spin_lock_irqsave(&hid->ctrllock, flags);
6197  
6198 -       if (hid->outhead != hid->outtail)
6199 -               hid_submit_out(hid);
6200 +       if (hid->ctrl[hid->ctrltail].dir == USB_DIR_IN) 
6201 +               hid_input_report(hid->ctrl[hid->ctrltail].report->type, urb);
6202 +
6203 +       hid->ctrltail = (hid->ctrltail + 1) & (HID_CONTROL_FIFO_SIZE - 1);
6204 +
6205 +       if (hid->ctrlhead != hid->ctrltail) {
6206 +               hid_submit_ctrl(hid);
6207 +               spin_unlock_irqrestore(&hid->ctrllock, flags);
6208 +               return;
6209 +       }
6210 +
6211 +       clear_bit(HID_CTRL_RUNNING, &hid->iofl);
6212 +
6213 +       spin_unlock_irqrestore(&hid->ctrllock, flags);
6214 +
6215 +       wake_up(&hid->wait);
6216  }
6217  
6218 -void hid_write_report(struct hid_device *hid, struct hid_report *report)
6219 +void hid_submit_report(struct hid_device *hid, struct hid_report *report, unsigned char dir)
6220  {
6221 -       hid_output_report(report, hid->out[hid->outhead].buffer);
6222 +       int head;
6223 +       unsigned long flags;
6224  
6225 -       hid->out[hid->outhead].dr.wValue = cpu_to_le16(0x200 | report->id);
6226 -       hid->out[hid->outhead].dr.wLength = cpu_to_le16((report->size + 7) >> 3);
6227 +       if (hid->urbout && dir == USB_DIR_OUT && report->type == HID_OUTPUT_REPORT) {
6228  
6229 -       hid->outhead = (hid->outhead + 1) & (HID_CONTROL_FIFO_SIZE - 1);
6230 +               spin_lock_irqsave(&hid->outlock, flags);
6231  
6232 -       if (hid->outhead == hid->outtail)
6233 -               hid->outtail = (hid->outtail + 1) & (HID_CONTROL_FIFO_SIZE - 1);
6234 +               if ((head = (hid->outhead + 1) & (HID_OUTPUT_FIFO_SIZE - 1)) == hid->outtail) {
6235 +                       spin_unlock_irqrestore(&hid->outlock, flags);
6236 +                       warn("output queue full");
6237 +                       return;
6238 +               }
6239  
6240 -       if (hid->urbout.status != -EINPROGRESS)
6241 -               hid_submit_out(hid);
6242 +               hid->out[hid->outhead] = report;
6243 +               hid->outhead = head;
6244 +
6245 +               if (!test_and_set_bit(HID_OUT_RUNNING, &hid->iofl))
6246 +                       hid_submit_out(hid);
6247 +
6248 +               spin_unlock_irqrestore(&hid->outlock, flags);
6249 +               return;
6250 +       }
6251 +
6252 +       spin_lock_irqsave(&hid->ctrllock, flags);
6253 +
6254 +       if ((head = (hid->ctrlhead + 1) & (HID_CONTROL_FIFO_SIZE - 1)) == hid->ctrltail) {
6255 +               spin_unlock_irqrestore(&hid->ctrllock, flags);
6256 +               warn("control queue full");
6257 +               return;
6258 +       }
6259 +
6260 +       hid->ctrl[hid->ctrlhead].report = report;
6261 +       hid->ctrl[hid->ctrlhead].dir = dir;
6262 +       hid->ctrlhead = head;
6263 +
6264 +       if (!test_and_set_bit(HID_CTRL_RUNNING, &hid->iofl))
6265 +               hid_submit_ctrl(hid);
6266 +
6267 +       spin_unlock_irqrestore(&hid->ctrllock, flags);
6268 +}
6269 +
6270 +int hid_wait_io(struct hid_device *hid)
6271 +{
6272 +       DECLARE_WAITQUEUE(wait, current);
6273 +       int timeout = 10*HZ;
6274 +
6275 +       set_current_state(TASK_UNINTERRUPTIBLE);
6276 +       add_wait_queue(&hid->wait, &wait);
6277 +
6278 +       while (timeout && (test_bit(HID_CTRL_RUNNING, &hid->iofl) ||
6279 +                          test_bit(HID_OUT_RUNNING, &hid->iofl)))
6280 +               timeout = schedule_timeout(timeout);
6281 +
6282 +       set_current_state(TASK_RUNNING);
6283 +       remove_wait_queue(&hid->wait, &wait);
6284 +
6285 +       if (!timeout) {
6286 +               dbg("timeout waiting for ctrl or out queue to clear");
6287 +               return -1;
6288 +       }
6289 +
6290 +       return 0;
6291 +}
6292 +#define USB_CTRL_GET_TIMEOUT 5
6293 +static int hid_get_class_descriptor(struct usb_device *dev, int ifnum,
6294 +               unsigned char type, void *buf, int size)
6295 +{
6296 +       return usb_control_msg(dev, usb_rcvctrlpipe(dev, 0),
6297 +               USB_REQ_GET_DESCRIPTOR, USB_RECIP_INTERFACE | USB_DIR_IN,
6298 +               (type << 8), ifnum, buf, size, HZ * USB_CTRL_GET_TIMEOUT);
6299  }
6300  
6301  int hid_open(struct hid_device *hid)
6302 @@ -1035,9 +1182,9 @@
6303         if (hid->open++)
6304                 return 0;
6305  
6306 -       hid->urb.dev = hid->dev;
6307 +       hid->urbin->dev = hid->dev;
6308  
6309 -       if (usb_submit_urb(&hid->urb))
6310 +       if (usb_submit_urb(hid->urbin))
6311                 return -EIO;
6312  
6313         return 0;
6314 @@ -1046,81 +1193,83 @@
6315  void hid_close(struct hid_device *hid)
6316  {
6317         if (!--hid->open)
6318 -               usb_unlink_urb(&hid->urb);
6319 +               usb_unlink_urb(hid->urbin);
6320  }
6321  
6322  /*
6323 - * Initialize all readable reports
6324 + * Initialize all reports
6325   */
6326 +#define USB_CTRL_SET_TIMEOUT 5
6327  void hid_init_reports(struct hid_device *hid)
6328  {
6329 -       int i;
6330 -       struct hid_report *report;
6331         struct hid_report_enum *report_enum;
6332 +       struct hid_report *report;
6333         struct list_head *list;
6334 +       int len;
6335 +       int err, ret;
6336  
6337 -       for (i = 0; i < HID_REPORT_TYPES; i++) {
6338 -               if (i == HID_FEATURE_REPORT || i == HID_INPUT_REPORT) {
6339 -                       report_enum = hid->report_enum + i;
6340 -                       list = report_enum->report_list.next;
6341 -                       while (list != &report_enum->report_list) {
6342 -                               report = (struct hid_report *) list;
6343 -                               hid_read_report(hid, report);
6344 -                               usb_set_idle(hid->dev, hid->ifnum, 0, report->id);
6345 -                               list = list->next;
6346 -                       }
6347 -               }
6348 +       report_enum = hid->report_enum + HID_INPUT_REPORT;
6349 +       list = report_enum->report_list.next;
6350 +       while (list != &report_enum->report_list) {
6351 +               report = (struct hid_report *) list;
6352 +               hid_submit_report(hid, report, USB_DIR_IN);
6353 +               list = list->next;
6354 +       }
6355 +
6356 +       report_enum = hid->report_enum + HID_FEATURE_REPORT;
6357 +       list = report_enum->report_list.next;
6358 +       while (list != &report_enum->report_list) {
6359 +               report = (struct hid_report *) list;
6360 +               hid_submit_report(hid, report, USB_DIR_IN);
6361 +               list = list->next;
6362 +       }
6363 +
6364 +       err = 0;
6365 +       while ((ret = hid_wait_io(hid))) {
6366 +               err |= ret;
6367 +               if (test_bit(HID_CTRL_RUNNING, &hid->iofl))
6368 +                       usb_unlink_urb(hid->urbctrl);
6369 +               if (test_bit(HID_OUT_RUNNING, &hid->iofl))
6370 +                       usb_unlink_urb(hid->urbout);
6371 +       }
6372 +
6373 +       if (err)
6374 +               warn("timeout initializing reports\n");
6375 +
6376 +       report_enum = hid->report_enum + HID_INPUT_REPORT;
6377 +       list = report_enum->report_list.next;
6378 +       while (list != &report_enum->report_list) {
6379 +               report = (struct hid_report *) list;
6380 +               len = ((report->size - 1) >> 3) + 1 + report_enum->numbered;
6381 +               if (len > hid->urbin->transfer_buffer_length)
6382 +                       hid->urbin->transfer_buffer_length = len < HID_BUFFER_SIZE ? len : HID_BUFFER_SIZE;
6383 +               usb_control_msg(hid->dev, usb_sndctrlpipe(hid->dev, 0),
6384 +                       0x0a, USB_TYPE_CLASS | USB_RECIP_INTERFACE, report->id,
6385 +                       hid->ifnum, NULL, 0, HZ * USB_CTRL_SET_TIMEOUT);
6386 +               list = list->next;
6387         }
6388  }
6389  
6390  #define USB_VENDOR_ID_WACOM            0x056a
6391 -#define USB_DEVICE_ID_WACOM_PENPARTNER 0x0000
6392  #define USB_DEVICE_ID_WACOM_GRAPHIRE   0x0010
6393  #define USB_DEVICE_ID_WACOM_INTUOS     0x0020
6394 -#define USB_DEVICE_ID_WACOM_PL         0x0030
6395 -#define USB_DEVICE_ID_WACOM_INTUOS2    0x0041
6396 -
6397 -#define USB_VENDOR_ID_ATEN             0x0557
6398 -#define USB_DEVICE_ID_ATEN_UC100KM     0x2004
6399 -#define USB_DEVICE_ID_ATEN_CS124U      0x2202
6400 -#define USB_DEVICE_ID_ATEN_2PORTKVM    0x2204
6401 -#define USB_DEVICE_ID_ATEN_4PORTKVM    0x2205
6402  
6403  #define USB_VENDOR_ID_GRIFFIN          0x077d
6404 -#define USB_DEVICE_ID_POWERMATE                0x0410 /* Griffin PowerMate */
6405 -#define USB_DEVICE_ID_SOUNDKNOB                0x04AA /* Griffin SoundKnob */
6406 +#define USB_DEVICE_ID_POWERMATE                0x0410
6407 +#define USB_DEVICE_ID_SOUNDKNOB                0x04AA
6408  
6409  struct hid_blacklist {
6410         __u16 idVendor;
6411         __u16 idProduct;
6412 -       unsigned quirks;
6413  } hid_blacklist[] = {
6414 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_PENPARTNER, HID_QUIRK_IGNORE },
6415 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_GRAPHIRE, HID_QUIRK_IGNORE },
6416 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_GRAPHIRE + 1, HID_QUIRK_IGNORE },
6417 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_GRAPHIRE + 2, HID_QUIRK_IGNORE },
6418 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS, HID_QUIRK_IGNORE },
6419 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS + 1, HID_QUIRK_IGNORE },
6420 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS + 2, HID_QUIRK_IGNORE },
6421 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS + 3, HID_QUIRK_IGNORE },
6422 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS + 4, HID_QUIRK_IGNORE },
6423 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_PL, HID_QUIRK_IGNORE },
6424 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_PL + 1, HID_QUIRK_IGNORE },
6425 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_PL + 2, HID_QUIRK_IGNORE },
6426 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_PL + 3, HID_QUIRK_IGNORE },
6427 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_PL + 4, HID_QUIRK_IGNORE },
6428 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_PL + 5, HID_QUIRK_IGNORE },
6429 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS2, HID_QUIRK_IGNORE },
6430 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS2 + 1, HID_QUIRK_IGNORE },
6431 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS2 + 2, HID_QUIRK_IGNORE },
6432 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS2 + 3, HID_QUIRK_IGNORE },
6433 -       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS2 + 4, HID_QUIRK_IGNORE },
6434 -       { USB_VENDOR_ID_ATEN, USB_DEVICE_ID_ATEN_UC100KM, HID_QUIRK_NOGET },
6435 -       { USB_VENDOR_ID_ATEN, USB_DEVICE_ID_ATEN_CS124U, HID_QUIRK_NOGET },
6436 -       { USB_VENDOR_ID_ATEN, USB_DEVICE_ID_ATEN_2PORTKVM, HID_QUIRK_NOGET },
6437 -       { USB_VENDOR_ID_ATEN, USB_DEVICE_ID_ATEN_4PORTKVM, HID_QUIRK_NOGET },
6438 -       { USB_VENDOR_ID_GRIFFIN, USB_DEVICE_ID_POWERMATE, HID_QUIRK_IGNORE },
6439 -       { USB_VENDOR_ID_GRIFFIN, USB_DEVICE_ID_SOUNDKNOB, HID_QUIRK_IGNORE },
6440 +       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_GRAPHIRE },
6441 +       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS },
6442 +       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS + 1},
6443 +       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS + 2},
6444 +       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS + 3},
6445 +       { USB_VENDOR_ID_WACOM, USB_DEVICE_ID_WACOM_INTUOS + 4},
6446 +       { USB_VENDOR_ID_GRIFFIN, USB_DEVICE_ID_POWERMATE },
6447 +       { USB_VENDOR_ID_GRIFFIN, USB_DEVICE_ID_SOUNDKNOB },
6448         { 0, 0 }
6449  };
6450  
6451 @@ -1129,26 +1278,23 @@
6452         struct usb_interface_descriptor *interface = dev->actconfig->interface[ifnum].altsetting + 0;
6453         struct hid_descriptor *hdesc;
6454         struct hid_device *hid;
6455 -       unsigned quirks = 0, rsize = 0;
6456 +       unsigned rsize = 0;
6457 +       u8 *rdesc;
6458         char *buf;
6459         int n;
6460  
6461         for (n = 0; hid_blacklist[n].idVendor; n++)
6462                 if ((hid_blacklist[n].idVendor == dev->descriptor.idVendor) &&
6463 -                       (hid_blacklist[n].idProduct == dev->descriptor.idProduct))
6464 -                               quirks = hid_blacklist[n].quirks;
6465 -
6466 -       if (quirks & HID_QUIRK_IGNORE)
6467 -               return NULL;
6468 +                       (hid_blacklist[n].idProduct == dev->descriptor.idProduct)) return NULL;
6469  
6470 -       if (usb_get_extra_descriptor(interface, USB_DT_HID, &hdesc) && ((!interface->bNumEndpoints) ||
6471 -               usb_get_extra_descriptor(&interface->endpoint[0], USB_DT_HID, &hdesc))) {
6472 +       if (usb_get_extra_descriptor(interface, HID_DT_HID, &hdesc) && ((!interface->bNumEndpoints) ||
6473 +               usb_get_extra_descriptor(&interface->endpoint[0], HID_DT_HID, &hdesc))) {
6474                         dbg("class descriptor not present\n");
6475                         return NULL;
6476         }
6477  
6478         for (n = 0; n < hdesc->bNumDescriptors; n++)
6479 -               if (hdesc->desc[n].bDescriptorType == USB_DT_REPORT)
6480 +               if (hdesc->desc[n].bDescriptorType == HID_DT_REPORT)
6481                         rsize = le16_to_cpu(hdesc->desc[n].wDescriptorLength);
6482  
6483         if (!rsize || rsize > HID_MAX_DESCRIPTOR_SIZE) {
6484 @@ -1156,118 +1302,158 @@
6485                 return NULL;
6486         }
6487  
6488 -       {
6489 -               __u8 rdesc[rsize];
6490 +       if (!(rdesc = kmalloc(rsize, GFP_KERNEL))) {
6491 +               dbg("couldn't allocate rdesc memory");
6492 +               return NULL;
6493 +       }
6494  
6495 -               if ((n = usb_get_class_descriptor(dev, interface->bInterfaceNumber, USB_DT_REPORT, 0, rdesc, rsize)) < 0) {
6496 -                       dbg("reading report descriptor failed");
6497 -                       return NULL;
6498 -               }
6499 +       if ((n = hid_get_class_descriptor(dev, interface->bInterfaceNumber, HID_DT_REPORT, rdesc, rsize)) < 0) {
6500 +               dbg("reading report descriptor failed");
6501 +               kfree(rdesc);
6502 +               return NULL;
6503 +       }
6504  
6505  #ifdef DEBUG_DATA
6506 -               printk(KERN_DEBUG __FILE__ ": report descriptor (size %u, read %d) = ", rsize, n);
6507 -               for (n = 0; n < rsize; n++)
6508 -                       printk(" %02x", (unsigned) rdesc[n]);
6509 -               printk("\n");
6510 +       printk(KERN_DEBUG __FILE__ ": report descriptor (size %u, read %d) = ", rsize, n);
6511 +       for (n = 0; n < rsize; n++)
6512 +               printk(" %02x", (unsigned) rdesc[n]);
6513 +       printk("\n");
6514  #endif
6515  
6516 -               if (!(hid = hid_parse_report(rdesc, rsize))) {
6517 -                       dbg("parsing report descriptor failed");
6518 -                       return NULL;
6519 -               }
6520 +       if (!(hid = hid_parse_report(rdesc, rsize))) {
6521 +               dbg("parsing report descriptor failed");
6522 +               kfree(rdesc);
6523 +               return NULL;
6524         }
6525  
6526 -       hid->quirks = quirks;
6527 +       kfree(rdesc);
6528  
6529         for (n = 0; n < interface->bNumEndpoints; n++) {
6530  
6531                 struct usb_endpoint_descriptor *endpoint = &interface->endpoint[n];
6532 -               int pipe, maxp;
6533 +               int pipe;
6534  
6535                 if ((endpoint->bmAttributes & 3) != 3)          /* Not an interrupt endpoint */
6536                         continue;
6537  
6538 -               if (!(endpoint->bEndpointAddress & 0x80))       /* Not an input endpoint */
6539 -                       continue;
6540 -
6541 -               pipe = usb_rcvintpipe(dev, endpoint->bEndpointAddress);
6542 -               maxp = usb_maxpacket(dev, pipe, usb_pipeout(pipe));
6543 -
6544 -               FILL_INT_URB(&hid->urb, dev, pipe, hid->buffer, maxp > 32 ? 32 : maxp, hid_irq, hid, endpoint->bInterval);
6545 -
6546 -               break;
6547 +               if (endpoint->bEndpointAddress & USB_DIR_IN) {
6548 +                       if (hid->urbin)
6549 +                               continue;
6550 +                       if (!(hid->urbin = usb_alloc_urb(0)))
6551 +                               goto fail;
6552 +                       pipe = usb_rcvintpipe(dev, endpoint->bEndpointAddress);
6553 +                       FILL_INT_URB(hid->urbin, dev, pipe, hid->inbuf, 0, hid_irq_in, hid, endpoint->bInterval);
6554 +               } else {
6555 +                       if (hid->urbout)
6556 +                               continue;
6557 +                       if (!(hid->urbout = usb_alloc_urb(0)))
6558 +                               goto fail;
6559 +                       pipe = usb_sndbulkpipe(dev, endpoint->bEndpointAddress);
6560 +                       FILL_BULK_URB(hid->urbout, dev, pipe, hid->outbuf, 0, hid_irq_out, hid);
6561 +                       hid->urbout->transfer_flags |= USB_ASYNC_UNLINK;
6562 +               }
6563         }
6564  
6565 -       if (n == interface->bNumEndpoints) {
6566 -               dbg("couldn't find an input interrupt endpoint");
6567 -               hid_free_device(hid);
6568 -               return NULL;
6569 +       if (!hid->urbin) {
6570 +               err("couldn't find an input interrupt endpoint");
6571 +               goto fail;
6572         }
6573  
6574 +       init_waitqueue_head(&hid->wait);
6575 +       
6576 +       hid->outlock = SPIN_LOCK_UNLOCKED;
6577 +       hid->ctrllock = SPIN_LOCK_UNLOCKED;
6578 +
6579         hid->version = hdesc->bcdHID;
6580         hid->country = hdesc->bCountryCode;
6581         hid->dev = dev;
6582         hid->ifnum = interface->bInterfaceNumber;
6583  
6584 -       for (n = 0; n < HID_CONTROL_FIFO_SIZE; n++) {
6585 -               hid->out[n].dr.bRequestType = USB_TYPE_CLASS | USB_RECIP_INTERFACE;
6586 -               hid->out[n].dr.bRequest = USB_REQ_SET_REPORT;
6587 -               hid->out[n].dr.wIndex = cpu_to_le16(hid->ifnum);
6588 -       }
6589 -
6590         hid->name[0] = 0;
6591  
6592 -       if (!(buf = kmalloc(63, GFP_KERNEL)))
6593 -               return NULL;
6594 +       if (!(buf = kmalloc(64, GFP_KERNEL)))
6595 +               goto fail;
6596  
6597 -       if (usb_string(dev, dev->descriptor.iManufacturer, buf, 63) > 0) {
6598 +       if (usb_string(dev, dev->descriptor.iManufacturer, buf, 64) > 0) {
6599                 strcat(hid->name, buf);
6600 -               if (usb_string(dev, dev->descriptor.iProduct, buf, 63) > 0)
6601 +               if (usb_string(dev, dev->descriptor.iProduct, buf, 64) > 0)
6602                         sprintf(hid->name, "%s %s", hid->name, buf);
6603         } else
6604                 sprintf(hid->name, "%04x:%04x", dev->descriptor.idVendor, dev->descriptor.idProduct);
6605  
6606 -       kfree(buf);
6607 +       usb_make_path(dev, buf, 63);
6608 +       sprintf(hid->phys, "%s/input%d", buf, ifnum);
6609  
6610 -       FILL_CONTROL_URB(&hid->urbout, dev, usb_sndctrlpipe(dev, 0),
6611 -               (void*) &hid->out[0].dr, hid->out[0].buffer, 1, hid_ctrl, hid);
6612 +       if (usb_string(dev, dev->descriptor.iSerialNumber, hid->uniq, 64) <= 0)
6613 +               hid->uniq[0] = 0;
6614  
6615 -/*
6616 - * Some devices don't like this and crash. I don't know of any devices
6617 - * needing this, so it is disabled for now.
6618 - */
6619 +       kfree(buf);
6620  
6621 -#if 0
6622 -       if (interface->bInterfaceSubClass == 1)
6623 -               usb_set_protocol(dev, hid->ifnum, 1);
6624 -#endif
6625 +       hid->urbctrl = usb_alloc_urb(0);
6626 +       FILL_CONTROL_URB(hid->urbctrl, dev, 0, (void*) &hid->dr, hid->ctrlbuf, 1, hid_ctrl, hid);
6627 +       hid->urbctrl->transfer_flags |= USB_ASYNC_UNLINK;
6628  
6629         return hid;
6630 +
6631 +fail:
6632 +       hid_free_device(hid);
6633 +       if (hid->urbin) usb_free_urb(hid->urbin);
6634 +       if (hid->urbout) usb_free_urb(hid->urbout);
6635 +       if (hid->urbctrl) usb_free_urb(hid->urbctrl);
6636 +
6637 +       return NULL;
6638  }
6639  
6640  static void* hid_probe(struct usb_device *dev, unsigned int ifnum,
6641                        const struct usb_device_id *id)
6642  {
6643         struct hid_device *hid;
6644 +       char path[64];
6645         int i;
6646         char *c;
6647  
6648         dbg("HID probe called for ifnum %d", ifnum);
6649  
6650 -       if (!(hid = usb_hid_configure(dev, ifnum)))
6651 +       if (!(hid = usb_hid_configure(dev, ifnum))) {
6652 +               err("usb_hid_configure failed");
6653                 return NULL;
6654 +       }
6655  
6656         hid_init_reports(hid);
6657         hid_dump_device(hid);
6658  
6659 +#ifdef CONFIG_HID_FF
6660 +       switch (hid_ff_init(hid)) {
6661 +       case 0:
6662 +               break;
6663 +
6664 +       case -ENOSYS:
6665 +               info("No force feedback support for this hid device");
6666 +               break;
6667 +
6668 +       default:
6669 +               err("hid_ff_init failed");
6670 +               hid_free_device(hid);
6671 +               return NULL;
6672 +       }
6673 +#endif
6674 +
6675         if (!hidinput_connect(hid))
6676                 hid->claimed |= HID_CLAIMED_INPUT;
6677 +#ifdef CONFIG_USB_HIDDEV
6678         if (!hiddev_connect(hid))
6679                 hid->claimed |= HID_CLAIMED_HIDDEV;
6680 +#endif
6681 +
6682 +       if (!hid->claimed) {
6683 +               hid_free_device(hid);
6684 +               return NULL;
6685 +       }
6686 +
6687         printk(KERN_INFO);
6688  
6689         if (hid->claimed & HID_CLAIMED_INPUT)
6690 -               printk("input%d", hid->input.number);
6691 +               printk("input");
6692         if (hid->claimed == (HID_CLAIMED_INPUT | HID_CLAIMED_HIDDEV))
6693                 printk(",");
6694         if (hid->claimed & HID_CLAIMED_HIDDEV)
6695 @@ -1280,9 +1466,10 @@
6696                         break;
6697                 }
6698  
6699 -       printk(": USB HID v%x.%02x %s [%s] on usb%d:%d.%d\n",
6700 -               hid->version >> 8, hid->version & 0xff, c, hid->name,
6701 -               dev->bus->busnum, dev->devnum, ifnum);
6702 +       usb_make_path(dev, path, 63);
6703 +
6704 +       printk(": USB HID v%x.%02x %s [%s] on %s\n",
6705 +               hid->version >> 8, hid->version & 0xff, c, hid->name, path);
6706  
6707         return hid;
6708  }
6709 @@ -1291,12 +1478,22 @@
6710  {
6711         struct hid_device *hid = ptr;
6712  
6713 -       dbg("cleanup called");
6714 -       usb_unlink_urb(&hid->urb);
6715 +       usb_unlink_urb(hid->urbin);
6716 +       usb_unlink_urb(hid->urbout);
6717 +       usb_unlink_urb(hid->urbctrl);
6718 +
6719         if (hid->claimed & HID_CLAIMED_INPUT)
6720                 hidinput_disconnect(hid);
6721 +#ifdef CONFIG_USB_HIDDEV
6722         if (hid->claimed & HID_CLAIMED_HIDDEV)
6723                 hiddev_disconnect(hid);
6724 +#endif
6725 +
6726 +       usb_free_urb(hid->urbin);
6727 +       usb_free_urb(hid->urbctrl);
6728 +       if (hid->urbout)
6729 +               usb_free_urb(hid->urbout);
6730 +
6731         hid_free_device(hid);
6732  }
6733  
6734 @@ -1317,23 +1514,26 @@
6735  
6736  static int __init hid_init(void)
6737  {
6738 +#ifdef CONFIG_USB_HIDDEV
6739         hiddev_init();
6740 +#endif
6741         usb_register(&hid_driver);
6742 -       info(DRIVER_VERSION " " DRIVER_AUTHOR);
6743 -       info(DRIVER_DESC);
6744 +       info(DRIVER_VERSION ":" DRIVER_DESC);
6745  
6746         return 0;
6747  }
6748  
6749  static void __exit hid_exit(void)
6750  {
6751 +#ifdef CONFIG_USB_HIDDEV
6752         hiddev_exit();
6753 +#endif
6754         usb_deregister(&hid_driver);
6755  }
6756  
6757  module_init(hid_init);
6758  module_exit(hid_exit);
6759  
6760 -MODULE_AUTHOR( DRIVER_AUTHOR );
6761 -MODULE_DESCRIPTION( DRIVER_DESC );
6762 -MODULE_LICENSE("GPL");
6763 +MODULE_AUTHOR(DRIVER_AUTHOR);
6764 +MODULE_DESCRIPTION(DRIVER_DESC);
6765 +MODULE_LICENSE(DRIVER_LICENSE);
6766 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/hid-debug.h linux-modified/drivers/usb/hid-debug.h
6767 --- linux-vanilla/drivers/usb/hid-debug.h       Thu Sep 13 00:34:06 2001
6768 +++ linux-modified/drivers/usb/hid-debug.h      Mon Jan  6 16:48:21 2003
6769 @@ -1,12 +1,10 @@
6770  /*
6771 - * $Id$
6772 + * $Id$
6773   *
6774   *  (c) 1999 Andreas Gal               <gal@cs.uni-magdeburg.de>
6775 - *  (c) 2000-2001 Vojtech Pavlik       <vojtech@suse.cz>
6776 + *  (c) 2000-2001 Vojtech Pavlik       <vojtech@ucw.cz>
6777   *
6778   *  Some debug stuff for the HID parser.
6779 - *
6780 - *  Sponsored by SuSE
6781   */
6782  
6783  /*
6784 @@ -25,8 +23,8 @@
6785   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
6786   *
6787   * Should you need to contact me, the author, you can do so either by
6788 - * e-mail - mail your message to <vojtech@suse.cz>, or by paper mail:
6789 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
6790 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
6791 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
6792   */
6793  
6794  struct hid_usage_entry {
6795 @@ -36,6 +34,7 @@
6796  };
6797  
6798  static struct hid_usage_entry hid_usage_table[] = {
6799 +  {  0,      0, "Undefined" },
6800    {  1,      0, "GenericDesktop" },
6801      {0, 0x01, "Pointer"},
6802      {0, 0x02, "Mouse"},
6803 @@ -87,6 +86,7 @@
6804    {  7, 0, "Keyboard" },
6805    {  8, 0, "LED" },
6806    {  9, 0, "Button" },
6807 +  { 10, 0, "Ordinal" },
6808    { 12, 0, "Hotkey" },
6809    { 13, 0, "Digitizers" },
6810      {0, 0x01, "Digitizer"},
6811 @@ -112,6 +112,112 @@
6812      {0, 0x45, "Eraser"},
6813      {0, 0x46, "TabletPick"},
6814    { 15, 0, "PhysicalInterfaceDevice" },
6815 +    {0, 0x00, "Undefined"},
6816 +    {0, 0x01, "Physical_Interface_Device"},
6817 +      {0, 0x20, "Normal"},
6818 +    {0, 0x21, "Set_Effect_Report"},
6819 +      {0, 0x22, "Effect_Block_Index"},
6820 +      {0, 0x23, "Parameter_Block_Offset"},
6821 +      {0, 0x24, "ROM_Flag"},
6822 +      {0, 0x25, "Effect_Type"},
6823 +        {0, 0x26, "ET_Constant_Force"},
6824 +        {0, 0x27, "ET_Ramp"},
6825 +        {0, 0x28, "ET_Custom_Force_Data"},
6826 +        {0, 0x30, "ET_Square"},
6827 +        {0, 0x31, "ET_Sine"},
6828 +        {0, 0x32, "ET_Triangle"},
6829 +        {0, 0x33, "ET_Sawtooth_Up"},
6830 +        {0, 0x34, "ET_Sawtooth_Down"},
6831 +        {0, 0x40, "ET_Spring"},
6832 +        {0, 0x41, "ET_Damper"},
6833 +        {0, 0x42, "ET_Inertia"},
6834 +        {0, 0x43, "ET_Friction"},
6835 +      {0, 0x50, "Duration"},
6836 +      {0, 0x51, "Sample_Period"},
6837 +      {0, 0x52, "Gain"},
6838 +      {0, 0x53, "Trigger_Button"},
6839 +      {0, 0x54, "Trigger_Repeat_Interval"},
6840 +      {0, 0x55, "Axes_Enable"},
6841 +        {0, 0x56, "Direction_Enable"},
6842 +      {0, 0x57, "Direction"},
6843 +      {0, 0x58, "Type_Specific_Block_Offset"},
6844 +        {0, 0x59, "Block_Type"},
6845 +        {0, 0x5A, "Set_Envelope_Report"},
6846 +          {0, 0x5B, "Attack_Level"},
6847 +          {0, 0x5C, "Attack_Time"},
6848 +          {0, 0x5D, "Fade_Level"},
6849 +          {0, 0x5E, "Fade_Time"},
6850 +        {0, 0x5F, "Set_Condition_Report"},
6851 +        {0, 0x60, "CP_Offset"},
6852 +        {0, 0x61, "Positive_Coefficient"},
6853 +        {0, 0x62, "Negative_Coefficient"},
6854 +        {0, 0x63, "Positive_Saturation"},
6855 +        {0, 0x64, "Negative_Saturation"},
6856 +        {0, 0x65, "Dead_Band"},
6857 +      {0, 0x66, "Download_Force_Sample"},
6858 +      {0, 0x67, "Isoch_Custom_Force_Enable"},
6859 +      {0, 0x68, "Custom_Force_Data_Report"},
6860 +        {0, 0x69, "Custom_Force_Data"},
6861 +        {0, 0x6A, "Custom_Force_Vendor_Defined_Data"},
6862 +      {0, 0x6B, "Set_Custom_Force_Report"},
6863 +        {0, 0x6C, "Custom_Force_Data_Offset"},
6864 +        {0, 0x6D, "Sample_Count"},
6865 +      {0, 0x6E, "Set_Periodic_Report"},
6866 +        {0, 0x6F, "Offset"},
6867 +        {0, 0x70, "Magnitude"},
6868 +        {0, 0x71, "Phase"},
6869 +        {0, 0x72, "Period"},
6870 +      {0, 0x73, "Set_Constant_Force_Report"},
6871 +        {0, 0x74, "Set_Ramp_Force_Report"},
6872 +        {0, 0x75, "Ramp_Start"},
6873 +        {0, 0x76, "Ramp_End"},
6874 +      {0, 0x77, "Effect_Operation_Report"},
6875 +        {0, 0x78, "Effect_Operation"},
6876 +          {0, 0x79, "Op_Effect_Start"},
6877 +          {0, 0x7A, "Op_Effect_Start_Solo"},
6878 +          {0, 0x7B, "Op_Effect_Stop"},
6879 +          {0, 0x7C, "Loop_Count"},
6880 +      {0, 0x7D, "Device_Gain_Report"},
6881 +        {0, 0x7E, "Device_Gain"},
6882 +    {0, 0x7F, "PID_Pool_Report"},
6883 +      {0, 0x80, "RAM_Pool_Size"},
6884 +      {0, 0x81, "ROM_Pool_Size"},
6885 +      {0, 0x82, "ROM_Effect_Block_Count"},
6886 +      {0, 0x83, "Simultaneous_Effects_Max"},
6887 +      {0, 0x84, "Pool_Alignment"},
6888 +    {0, 0x85, "PID_Pool_Move_Report"},
6889 +      {0, 0x86, "Move_Source"},
6890 +      {0, 0x87, "Move_Destination"},
6891 +      {0, 0x88, "Move_Length"},
6892 +    {0, 0x89, "PID_Block_Load_Report"},
6893 +      {0, 0x8B, "Block_Load_Status"},
6894 +      {0, 0x8C, "Block_Load_Success"},
6895 +      {0, 0x8D, "Block_Load_Full"},
6896 +      {0, 0x8E, "Block_Load_Error"},
6897 +      {0, 0x8F, "Block_Handle"},
6898 +      {0, 0x90, "PID_Block_Free_Report"},
6899 +      {0, 0x91, "Type_Specific_Block_Handle"},
6900 +    {0, 0x92, "PID_State_Report"},
6901 +      {0, 0x94, "Effect_Playing"},
6902 +      {0, 0x95, "PID_Device_Control_Report"},
6903 +        {0, 0x96, "PID_Device_Control"},
6904 +        {0, 0x97, "DC_Enable_Actuators"},
6905 +        {0, 0x98, "DC_Disable_Actuators"},
6906 +        {0, 0x99, "DC_Stop_All_Effects"},
6907 +        {0, 0x9A, "DC_Device_Reset"},
6908 +        {0, 0x9B, "DC_Device_Pause"},
6909 +        {0, 0x9C, "DC_Device_Continue"},
6910 +      {0, 0x9F, "Device_Paused"},
6911 +      {0, 0xA0, "Actuators_Enabled"},
6912 +      {0, 0xA4, "Safety_Switch"},
6913 +      {0, 0xA5, "Actuator_Override_Switch"},
6914 +      {0, 0xA6, "Actuator_Power"},
6915 +    {0, 0xA7, "Start_Delay"},
6916 +    {0, 0xA8, "Parameter_Block_Size"},
6917 +    {0, 0xA9, "Device_Managed_Pool"},
6918 +    {0, 0xAA, "Shared_Parameter_Blocks"},
6919 +    {0, 0xAB, "Create_New_Effect_Report"},
6920 +    {0, 0xAC, "RAM_Pool_Available"},
6921    { 0, 0, NULL }
6922  };
6923  
6924 @@ -176,7 +282,50 @@
6925                 tab(n); printk("Unit Exponent(%d)\n", field->unit_exponent);
6926         }
6927         if (field->unit) {
6928 -               tab(n); printk("Unit(%u)\n", field->unit);
6929 +               char *systems[5] = { "None", "SI Linear", "SI Rotation", "English Linear", "English Rotation" };
6930 +               char *units[5][8] = {
6931 +                       { "None", "None", "None", "None", "None", "None", "None", "None" },
6932 +                       { "None", "Centimeter", "Gram", "Seconds", "Kelvin",     "Ampere", "Candela", "None" },
6933 +                       { "None", "Radians",    "Gram", "Seconds", "Kelvin",     "Ampere", "Candela", "None" },
6934 +                       { "None", "Inch",       "Slug", "Seconds", "Fahrenheit", "Ampere", "Candela", "None" },
6935 +                       { "None", "Degrees",    "Slug", "Seconds", "Fahrenheit", "Ampere", "Candela", "None" }
6936 +               };
6937 +
6938 +               int i;
6939 +               int sys;
6940 +                __u32 data = field->unit;
6941 +
6942 +               /* First nibble tells us which system we're in. */
6943 +               sys = data & 0xf;
6944 +               data >>= 4;
6945 +
6946 +               if(sys > 4) {
6947 +                       tab(n); printk("Unit(Invalid)\n");
6948 +               }
6949 +               else {
6950 +                       int earlier_unit = 0;
6951 +
6952 +                       tab(n); printk("Unit(%s : ", systems[sys]);
6953 +
6954 +                       for (i=1 ; i<sizeof(__u32)*2 ; i++) {
6955 +                               char nibble = data & 0xf;
6956 +                               data >>= 4;
6957 +                               if (nibble != 0) {
6958 +                                       if(earlier_unit++ > 0)
6959 +                                               printk("*");
6960 +                                       printk("%s", units[sys][i]);
6961 +                                       if(nibble != 1) {
6962 +                                               /* This is a _signed_ nibble(!) */
6963 +       
6964 +                                               int val = nibble & 0x7;
6965 +                                               if(nibble & 0x08)
6966 +                                                       val = -((0x7 & ~val) +1);
6967 +                                               printk("^%d", val);
6968 +                                       }
6969 +                               }
6970 +                       }
6971 +                       printk(")\n");
6972 +               }
6973         }
6974         tab(n); printk("Report Size(%u)\n", field->report_size);
6975         tab(n); printk("Report Count(%u)\n", field->report_count);
6976 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/hid-ff.c linux-modified/drivers/usb/hid-ff.c
6977 --- linux-vanilla/drivers/usb/hid-ff.c  Thu Jan  1 02:00:00 1970
6978 +++ linux-modified/drivers/usb/hid-ff.c Mon Jan  6 16:48:21 2003
6979 @@ -0,0 +1,69 @@
6980 +/*
6981 + *  Force feedback support for hid devices.
6982 + *  Not all hid devices use the same protocol. For example, some use PID,
6983 + *  other use their own proprietary procotol.
6984 + *
6985 + *  Copyright (c) 2002 Johann Deneux
6986 + */
6987 +
6988 +/*
6989 + * This program is free software; you can redistribute it and/or modify
6990 + * it under the terms of the GNU General Public License as published by
6991 + * the Free Software Foundation; either version 2 of the License, or
6992 + * (at your option) any later version.
6993 + *
6994 + * This program is distributed in the hope that it will be useful,
6995 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
6996 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
6997 + * GNU General Public License for more details.
6998 + *
6999 + * You should have received a copy of the GNU General Public License
7000 + * along with this program; if not, write to the Free Software
7001 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
7002 + *
7003 + * Should you need to contact me, the author, you can do so by
7004 + * e-mail - mail your message to <deneux@ifrance.com>
7005 + */
7006 +
7007 +#include <linux/input.h>
7008 +
7009 +#define DEBUG
7010 +#include <linux/usb.h>
7011 +
7012 +#include "hid.h"
7013 +
7014 +/* Drivers' initializing functions */
7015 +extern int hid_lgff_init(struct hid_device* hid);
7016 +extern int hid_pid_init(struct hid_device* hid);
7017 +
7018 +/* Each hid force feedback driver must provide an init function.
7019 +   It must return 1 if the driver does not handle this device,
7020 +   0 if it could and the initialization itself went smoothly,
7021 +   <0 if the driver should have been able to handle the device, but failed
7022 +*/
7023 +static int (*inits[])(struct hid_device*) = {
7024 +#ifdef CONFIG_LOGITECH_FF
7025 +       hid_lgff_init,
7026 +#endif
7027 +#ifdef CONFIG_HID_PID
7028 +       hid_pid_init,
7029 +#endif
7030 +       NULL
7031 +};
7032 +
7033 +int hid_ff_init(struct hid_device* hid)
7034 +{
7035 +       int i;
7036 +       int status;
7037 +
7038 +       for (i=0; inits[i]; ++i) {
7039 +               switch (status = inits[i](hid)) {
7040 +               case 0: return 0;  // Device handled and init ok
7041 +               case 1: break;     // Device not handled
7042 +               default: return status; // Device handled, init failed
7043 +               }
7044 +       }
7045 +
7046 +       dbg("hid_ff_init could not find initializer");
7047 +       return -ENOSYS;
7048 +}
7049 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/hid-input.c linux-modified/drivers/usb/hid-input.c
7050 --- linux-vanilla/drivers/usb/hid-input.c       Sun Nov 11 20:09:37 2001
7051 +++ linux-modified/drivers/usb/hid-input.c      Mon Jan  6 16:48:21 2003
7052 @@ -1,11 +1,9 @@
7053  /*
7054 - * $Id$
7055 + * $Id$
7056   *
7057   *  Copyright (c) 2000-2001 Vojtech Pavlik
7058   *
7059 - *  USB HID to Linux Input mapping module
7060 - *
7061 - *  Sponsored by SuSE
7062 + *  USB HID to Linux Input mapping
7063   */
7064  
7065  /*
7066 @@ -24,13 +22,12 @@
7067   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
7068   *
7069   * Should you need to contact me, the author, you can do so either by
7070 - * e-mail - mail your message to <vojtech@suse.cz>, or by paper mail:
7071 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
7072 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
7073 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
7074   */
7075  
7076  #include <linux/module.h>
7077  #include <linux/slab.h>
7078 -#include <linux/init.h>
7079  #include <linux/kernel.h>
7080  #include <linux/input.h>
7081  #include <linux/usb.h>
7082 @@ -61,12 +58,13 @@
7083  static struct {
7084         __s32 x;
7085         __s32 y;
7086 -}  hid_hat_to_axis[] = {{0, 0}, { 0,-1}, { 1,-1}, { 1, 0}, { 1, 1}, { 0, 1}, {-1, 1}, {-1, 0}, {-1,-1}};
7087 +}  hid_hat_to_axis[] = {{ 0, 0}, { 0,-1}, { 1,-1}, { 1, 0}, { 1, 1}, { 0, 1}, {-1, 1}, {-1, 0}, {-1,-1}};
7088  
7089  static void hidinput_configure_usage(struct hid_device *device, struct hid_field *field, struct hid_usage *usage)
7090  {
7091         struct input_dev *input = &device->input;
7092         int max;
7093 +       int is_abs = 0;
7094         unsigned long *bit;
7095  
7096         switch (usage->hid & HID_USAGE_PAGE) {
7097 @@ -198,6 +196,7 @@
7098  
7099                 case HID_UP_CONSUMER:   /* USB HUT v1.1, pages 56-62 */
7100  
7101 +                       set_bit(EV_REP, input->evbit);
7102                         switch (usage->hid & HID_USAGE) {
7103                                 case 0x000: usage->code = 0; break;
7104                                 case 0x034: usage->code = KEY_SLEEP;            break;
7105 @@ -205,14 +204,21 @@
7106                                 case 0x08a: usage->code = KEY_WWW;              break;
7107                                 case 0x095: usage->code = KEY_HELP;             break;
7108  
7109 +                               case 0x0b0: usage->code = KEY_PLAY;             break;
7110 +                               case 0x0b1: usage->code = KEY_PAUSE;            break;
7111 +                               case 0x0b2: usage->code = KEY_RECORD;           break;
7112 +                               case 0x0b3: usage->code = KEY_FASTFORWARD;      break;
7113                                 case 0x0b4: usage->code = KEY_REWIND;           break;
7114                                 case 0x0b5: usage->code = KEY_NEXTSONG;         break;
7115                                 case 0x0b6: usage->code = KEY_PREVIOUSSONG;     break;
7116                                 case 0x0b7: usage->code = KEY_STOPCD;           break;
7117                                 case 0x0b8: usage->code = KEY_EJECTCD;          break;
7118                                 case 0x0cd: usage->code = KEY_PLAYPAUSE;        break;
7119 -
7120 +                               case 0x0e0: is_abs = 1;
7121 +                                           usage->code = ABS_VOLUME;
7122 +                                           break;
7123                                 case 0x0e2: usage->code = KEY_MUTE;             break;
7124 +                               case 0x0e5: usage->code = KEY_BASSBOOST;        break;
7125                                 case 0x0e9: usage->code = KEY_VOLUMEUP;         break;
7126                                 case 0x0ea: usage->code = KEY_VOLUMEDOWN;       break;
7127  
7128 @@ -220,7 +226,6 @@
7129                                 case 0x18a: usage->code = KEY_MAIL;             break;
7130                                 case 0x192: usage->code = KEY_CALC;             break;
7131                                 case 0x194: usage->code = KEY_FILE;             break;
7132 -
7133                                 case 0x21a: usage->code = KEY_UNDO;             break;
7134                                 case 0x21b: usage->code = KEY_COPY;             break;
7135                                 case 0x21c: usage->code = KEY_CUT;              break;
7136 @@ -235,6 +240,34 @@
7137                                 case 0x22a: usage->code = KEY_BOOKMARKS;        break;
7138  
7139                                 default:    usage->code = KEY_UNKNOWN;          break;
7140 +                       }
7141 +
7142 +                       if (is_abs) {
7143 +                               usage->type = EV_ABS; bit = input->absbit; max = ABS_MAX;
7144 +                       } else  {
7145 +                               usage->type = EV_KEY; bit = input->keybit; max = KEY_MAX;
7146 +                       }
7147 +                       break;
7148 +
7149 +               case HID_UP_HPVENDOR:   /* Reported on a Dutch layout HP5308 */
7150 +
7151 +                       set_bit(EV_REP, input->evbit);
7152 +                       switch (usage->hid & HID_USAGE) {
7153 +                               case 0x021: usage->code = KEY_PRINT;            break;
7154 +                               case 0x070: usage->code = KEY_HP;               break;
7155 +                               case 0x071: usage->code = KEY_CAMERA;           break;
7156 +                               case 0x072: usage->code = KEY_SOUND;            break;
7157 +                               case 0x073: usage->code = KEY_QUESTION;         break;
7158 +
7159 +                               case 0x080: usage->code = KEY_EMAIL;            break;
7160 +                               case 0x081: usage->code = KEY_CHAT;             break;
7161 +                               case 0x082: usage->code = KEY_SEARCH;           break;
7162 +                               case 0x083: usage->code = KEY_CONNECT;          break;
7163 +                               case 0x084: usage->code = KEY_FINANCE;          break;
7164 +                               case 0x085: usage->code = KEY_SPORT;            break;
7165 +                               case 0x086: usage->code = KEY_SHOP;             break;
7166 +
7167 +                               default:    usage->code = KEY_UNKNOWN;          break;
7168  
7169                         }
7170  
7171 @@ -344,16 +377,28 @@
7172  static int hidinput_input_event(struct input_dev *dev, unsigned int type, unsigned int code, int value)
7173  {
7174         struct hid_device *hid = dev->private;
7175 -       struct hid_field *field = NULL;
7176 -       int offset;
7177  
7178 -       if ((offset = hid_find_field(hid, type, code, &field)) == -1) {
7179 -               warn("event field not found");
7180 -               return -1;
7181 +       warn("hid input event");
7182 +
7183 +#ifdef CONFIG_HID_FF
7184 +       if (type == EV_FF) {
7185 +               return hid_ff_event(hid, dev, type, code, value);
7186         }
7187 +#else
7188 +       if (0) {}
7189 +#endif         
7190 +       else {
7191 +               struct hid_field *field = NULL;
7192 +               int offset;
7193 +
7194 +               if ((offset = hid_find_field(hid, type, code, &field)) == -1) {
7195 +                       warn("event field not found");
7196 +                       return -1;
7197 +               }
7198  
7199 -       hid_set_field(field, offset, value);
7200 -       hid_write_report(hid, field->report);
7201 +               hid_set_field(field, offset, value);
7202 +               hid_submit_report(hid, field->report, USB_DIR_OUT);
7203 +       }
7204  
7205         return 0;
7206  }
7207 @@ -361,12 +406,22 @@
7208  static int hidinput_open(struct input_dev *dev)
7209  {
7210         struct hid_device *hid = dev->private;
7211 +/*
7212 +#ifdef CONFIG_HID_FF
7213 +       hid_ff_open(hid);
7214 +#endif
7215 +*/
7216         return hid_open(hid);
7217  }
7218  
7219  static void hidinput_close(struct input_dev *dev)
7220  {
7221         struct hid_device *hid = dev->private;
7222 +/*
7223 +#ifdef CONFIG_HID_FF
7224 +       hid_ff_close(hid);
7225 +#endif
7226 +*/
7227         hid_close(hid);
7228  }
7229  
7230 @@ -395,8 +450,9 @@
7231         hid->input.event = hidinput_input_event;
7232         hid->input.open = hidinput_open;
7233         hid->input.close = hidinput_close;
7234 -
7235         hid->input.name = hid->name;
7236 +       hid->input.phys = hid->phys;
7237 +       hid->input.uniq = hid->uniq;
7238         hid->input.idbus = BUS_USB;
7239         hid->input.idvendor = dev->descriptor.idVendor;
7240         hid->input.idproduct = dev->descriptor.idProduct;
7241 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/hid-lgff.c linux-modified/drivers/usb/hid-lgff.c
7242 --- linux-vanilla/drivers/usb/hid-lgff.c        Thu Jan  1 02:00:00 1970
7243 +++ linux-modified/drivers/usb/hid-lgff.c       Sun Mar  9 18:03:20 2003
7244 @@ -0,0 +1,588 @@
7245 +/*
7246 + * Force feedback support for hid-compliant for some of the devices from
7247 + * Logitech, namely:
7248 + * - WingMan Cordless RumblePad
7249 + * - WingMan Force 3D
7250 + * - WingMan Strike Force 3D
7251 + * Other possibly supported devices:
7252 + * Apparently *not* supported:
7253 + * - WingMan Formula Force GP
7254 + * - WingMan RumblePad (ie the non-cordless one)
7255 + *
7256 + *  Copyright (c) 2002 Johann Deneux
7257 + */
7258 +
7259 +/*
7260 + * This program is free software; you can redistribute it and/or modify
7261 + * it under the terms of the GNU General Public License as published by
7262 + * the Free Software Foundation; either version 2 of the License, or
7263 + * (at your option) any later version.
7264 + *
7265 + * This program is distributed in the hope that it will be useful,
7266 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
7267 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
7268 + * GNU General Public License for more details.
7269 + *
7270 + * You should have received a copy of the GNU General Public License
7271 + * along with this program; if not, write to the Free Software
7272 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
7273 + *
7274 + * Should you need to contact me, the author, you can do so by
7275 + * e-mail - mail your message to <deneux@ifrance.com>
7276 + */
7277 +
7278 +/* TODO:
7279 +   Support periodic, custom and condition effects.
7280 +   Support gain setting + default spring.
7281 +*/
7282 +
7283 +#include <linux/input.h>
7284 +#include <linux/sched.h>
7285 +
7286 +#define DEBUG
7287 +#include <linux/usb.h>
7288 +
7289 +#include <linux/circ_buf.h>
7290 +
7291 +#include "hid.h"
7292 +#include "fixp-arith.h"
7293 +
7294 +
7295 +/* Periodicity of the update */
7296 +#define PERIOD (HZ/10)
7297 +
7298 +#define RUN_AT(t) (jiffies + (t))
7299 +
7300 +/* Effect status */
7301 +#define EFFECT_STARTED 0     /* Effect is going to play after some time
7302 +                               (ff_replay.delay) */
7303 +#define EFFECT_PLAYING 1     /* Effect is being played */
7304 +#define EFFECT_USED    2
7305 +
7306 +// For lgff_device::flags
7307 +#define DEVICE_CLOSING 0     /* The driver is being unitialised */
7308 +
7309 +#define LGFF_EFFECTS 8
7310 +
7311 +struct device_type {
7312 +       u16 idVendor;
7313 +       u16 idProduct;
7314 +       signed short *ff;
7315 +};
7316 +
7317 +struct lgff_effect {
7318 +       pid_t owner;
7319 +
7320 +       struct ff_effect effect;
7321 +
7322 +       unsigned long flags[1];
7323 +       unsigned int count;          /* Number of times left to play */
7324 +       unsigned long started_at;    /* When the effect started to play */
7325 +};
7326 +
7327 +struct lgff_device {
7328 +       struct hid_device* hid;
7329 +
7330 +       struct hid_report* constant;
7331 +       struct hid_report* rumble;
7332 +       struct hid_report* condition;
7333 +
7334 +       struct lgff_effect effects[LGFF_EFFECTS];
7335 +       spinlock_t lock;             /* device-level lock. Having locks on
7336 +                                       a per-effect basis could be nice, but
7337 +                                       isn't really necessary */
7338 +
7339 +       unsigned long flags[1];      /* Contains various information about the
7340 +                                       state of the driver for this device */  
7341 +
7342 +       struct timer_list timer;
7343 +};
7344 +
7345 +/* Callbacks */
7346 +static void hid_lgff_exit(struct hid_device* hid);
7347 +static int hid_lgff_event(struct hid_device *hid, struct input_dev *input,
7348 +                         unsigned int type, unsigned int code, int value);
7349 +static int hid_lgff_flush(struct input_dev *input, struct file *file);
7350 +static int hid_lgff_upload_effect(struct input_dev *input,
7351 +                                 struct ff_effect *effect);
7352 +static int hid_lgff_erase(struct input_dev *input, int id);
7353 +
7354 +/* Local functions */
7355 +static void hid_lgff_input_init(struct hid_device* hid);
7356 +static void hid_lgff_timer(unsigned long timer_data);
7357 +static struct hid_report* hid_lgff_duplicate_report(struct hid_report*);
7358 +static void hid_lgff_delete_report(struct hid_report*);
7359 +
7360 +static signed short ff_rumble[] = {
7361 +       FF_RUMBLE,
7362 +       -1
7363 +};
7364 +
7365 +static signed short ff_joystick[] = {
7366 +       FF_CONSTANT,
7367 +       ABS_X,
7368 +       ABS_Y,
7369 +       -1
7370 +};
7371 +
7372 +static struct device_type devices[] = {
7373 +       {0x046d, 0xc211, ff_rumble},
7374 +       {0x046d, 0xc283, ff_joystick},
7375 +       {0x046d, 0xc285, ff_joystick},
7376 +       {0x0000, 0x0000, ff_joystick}
7377 +};
7378 +
7379 +int hid_lgff_init(struct hid_device* hid)
7380 +{
7381 +       struct lgff_device *private;
7382 +       struct hid_report* report;
7383 +       struct hid_field* field;
7384 +
7385 +       switch (hid->dev->descriptor.idVendor) {
7386 +       case 0x46d: // Logitech
7387 +               switch (hid->dev->descriptor.idProduct) {
7388 +               /* Supported devices */
7389 +               case 0xc211: // Cordless rumblepad
7390 +               case 0xc283: // Force 3D
7391 +               case 0xc285: // Strike Force 3D
7392 +                       break;
7393 +               /* Unsupported or unknown devices */
7394 +               default: return 1;
7395 +               } 
7396 +               break;
7397 +
7398 +       case 0x6a3: // Saitek
7399 +               switch (hid->dev->descriptor.idProduct) {
7400 +               case 0xff12: // Cyborg 3D Force
7401 +                       break;
7402 +               default: return 1;
7403 +               }
7404 +               break;
7405 +
7406 +       default: return 1;
7407 +       }
7408 +
7409 +       /* Find the report to use */
7410 +       if (list_empty(&hid->report_enum[HID_OUTPUT_REPORT].report_list)) {
7411 +               err("No output report found");
7412 +               return -1;
7413 +       }
7414 +       /* Check that the report looks ok */
7415 +       report = (struct hid_report*)hid->report_enum[HID_OUTPUT_REPORT].report_list.next;
7416 +       if (!report) {
7417 +               err("NULL output report");
7418 +               return -1;
7419 +       }
7420 +       field = report->field[0];
7421 +       if (!field) {
7422 +               err("NULL field");
7423 +               return -1;
7424 +       }
7425 +
7426 +       private = kmalloc(sizeof(struct lgff_device), GFP_KERNEL);
7427 +       if (!private) return -1;
7428 +       memset(private, 0, sizeof(struct lgff_device));
7429 +       hid->ff_private = private;
7430 +
7431 +       /* Input init */
7432 +       hid_lgff_input_init(hid);
7433 +
7434 +
7435 +       private->constant = hid_lgff_duplicate_report(report);
7436 +       if (!private->constant) {
7437 +               kfree(private);
7438 +               return -1;
7439 +       }
7440 +       private->constant->field[0]->value[0] = 0x51;
7441 +       private->constant->field[0]->value[1] = 0x08;
7442 +       private->constant->field[0]->value[2] = 0x7f;
7443 +       private->constant->field[0]->value[3] = 0x7f;
7444 +
7445 +       private->rumble = hid_lgff_duplicate_report(report);
7446 +       if (!private->rumble) {
7447 +               hid_lgff_delete_report(private->constant);
7448 +               kfree(private);
7449 +               return -1;
7450 +       }
7451 +       private->rumble->field[0]->value[0] = 0x03;
7452 +       private->rumble->field[0]->value[1] = 0x42;
7453 +
7454 +
7455 +       private->condition = hid_lgff_duplicate_report(report);
7456 +       if (!private->condition) {
7457 +               hid_lgff_delete_report(private->rumble);
7458 +               hid_lgff_delete_report(private->constant);
7459 +               kfree(private);
7460 +               return -1;
7461 +       }
7462 +
7463 +       private->hid = hid;
7464 +
7465 +       spin_lock_init(&private->lock);
7466 +       init_timer(&private->timer);
7467 +       private->timer.data = (unsigned long)private;
7468 +       private->timer.function = hid_lgff_timer;
7469 +
7470 +       /* Event and exit callbacks */
7471 +       hid->ff_exit = hid_lgff_exit;
7472 +       hid->ff_event = hid_lgff_event;
7473 +
7474 +       /* Start the update task */
7475 +       private->timer.expires = RUN_AT(PERIOD);
7476 +       add_timer(&private->timer);  /*TODO: only run the timer when at least
7477 +                                      one effect is playing */
7478 +
7479 +       printk(KERN_INFO "Force feedback for Logitech force feedback devices by Johann Deneux <deneux@ifrance.com>\n");
7480 +
7481 +       return 0;
7482 +}
7483 +
7484 +static struct hid_report* hid_lgff_duplicate_report(struct hid_report* report)
7485 +{
7486 +       struct hid_report* ret;
7487 +
7488 +       ret = kmalloc(sizeof(struct lgff_device), GFP_KERNEL);
7489 +       if (!ret) return NULL;
7490 +       *ret = *report;
7491 +
7492 +       ret->field[0] = kmalloc(sizeof(struct hid_field), GFP_KERNEL);
7493 +       if (!ret->field[0]) {
7494 +               kfree(ret);
7495 +               return NULL;
7496 +       }
7497 +       *ret->field[0] = *report->field[0];
7498 +
7499 +       ret->field[0]->value = kmalloc(sizeof(s32[8]), GFP_KERNEL);
7500 +       if (!ret->field[0]->value) {
7501 +               kfree(ret->field[0]);
7502 +               kfree(ret);
7503 +               return NULL;
7504 +       }
7505 +       memset(ret->field[0]->value, 0, sizeof(s32[8]));        
7506 +
7507 +       return ret;
7508 +}
7509 +
7510 +static void hid_lgff_delete_report(struct hid_report* report)
7511 +{
7512 +       if (report) {
7513 +               kfree(report->field[0]->value);
7514 +               kfree(report->field[0]);
7515 +               kfree(report);
7516 +       }
7517 +}
7518 +
7519 +static void hid_lgff_input_init(struct hid_device* hid)
7520 +{
7521 +       struct device_type* dev = devices;
7522 +       signed short* ff;
7523 +       u16 idVendor = hid->dev->descriptor.idVendor;
7524 +       u16 idProduct = hid->dev->descriptor.idProduct;
7525 +
7526 +       while (dev->idVendor && (idVendor != dev->idVendor || idProduct != dev->idProduct))
7527 +               dev++;
7528 +
7529 +       ff = dev->ff;
7530 +
7531 +       while (*ff >= 0) {
7532 +               set_bit(*ff, hid->input.ffbit);
7533 +               ++ff;
7534 +       }
7535 +
7536 +       hid->input.upload_effect = hid_lgff_upload_effect;
7537 +       hid->input.flush = hid_lgff_flush;
7538 +
7539 +       set_bit(EV_FF, hid->input.evbit);
7540 +       hid->input.ff_effects_max = LGFF_EFFECTS;
7541 +}
7542 +
7543 +static void hid_lgff_exit(struct hid_device* hid)
7544 +{
7545 +       struct lgff_device *lgff = hid->ff_private;
7546 +
7547 +       set_bit(DEVICE_CLOSING, lgff->flags);
7548 +       del_timer_sync(&lgff->timer);
7549 +
7550 +       hid_lgff_delete_report(lgff->condition);
7551 +       hid_lgff_delete_report(lgff->rumble);
7552 +       hid_lgff_delete_report(lgff->constant);
7553 +
7554 +       kfree(lgff);
7555 +}
7556 +
7557 +static int hid_lgff_event(struct hid_device *hid, struct input_dev* input,
7558 +                         unsigned int type, unsigned int code, int value)
7559 +{
7560 +       struct lgff_device *lgff = hid->ff_private;
7561 +       struct lgff_effect *effect = lgff->effects + code;
7562 +       unsigned long flags;
7563 +
7564 +       if (type != EV_FF)                     return -EINVAL;
7565 +       if (value < 0)                         return -EINVAL;
7566 +
7567 +       spin_lock_irqsave(&lgff->lock, flags);
7568 +       
7569 +       if (value > 0) {
7570 +               if (test_bit(EFFECT_STARTED, effect->flags)) {
7571 +                       spin_unlock_irqrestore(&lgff->lock, flags);
7572 +                       return -EBUSY;
7573 +               }
7574 +               if (test_bit(EFFECT_PLAYING, effect->flags)) {
7575 +                       spin_unlock_irqrestore(&lgff->lock, flags);
7576 +                       return -EBUSY;
7577 +               }
7578 +
7579 +               effect->count = value;
7580 +
7581 +               if (effect->effect.replay.delay) {
7582 +                       set_bit(EFFECT_STARTED, effect->flags);
7583 +               } else {
7584 +                       set_bit(EFFECT_PLAYING, effect->flags);
7585 +               }
7586 +               effect->started_at = jiffies;
7587 +       }
7588 +       else { /* value == 0 */
7589 +               clear_bit(EFFECT_STARTED, effect->flags);
7590 +               clear_bit(EFFECT_PLAYING, effect->flags);
7591 +       }
7592 +
7593 +       spin_unlock_irqrestore(&lgff->lock, flags);
7594 +
7595 +       return 0;
7596 +
7597 +}
7598 +
7599 +/* Erase all effects this process owns */
7600 +static int hid_lgff_flush(struct input_dev *dev, struct file *file)
7601 +{
7602 +       struct hid_device *hid = dev->private;
7603 +       struct lgff_device *lgff = hid->ff_private;
7604 +       int i;
7605 +
7606 +       for (i=0; i<dev->ff_effects_max; ++i) {
7607 +
7608 +               /*NOTE: no need to lock here. The only times EFFECT_USED is
7609 +                 modified is when effects are uploaded or when an effect is
7610 +                 erased. But a process cannot close its dev/input/eventX fd
7611 +                 and perform ioctls on the same fd all at the same time */
7612 +               if ( current->pid == lgff->effects[i].owner
7613 +                    && test_bit(EFFECT_USED, lgff->effects[i].flags)) {
7614 +                       
7615 +                       if (hid_lgff_erase(dev, i))
7616 +                               warn("erase effect %d failed", i);
7617 +               }
7618 +
7619 +       }
7620 +
7621 +       return 0;
7622 +}
7623 +
7624 +static int hid_lgff_erase(struct input_dev *dev, int id)
7625 +{
7626 +       struct hid_device *hid = dev->private;
7627 +       struct lgff_device *lgff = hid->ff_private;
7628 +       unsigned long flags;
7629 +
7630 +       spin_lock_irqsave(&lgff->lock, flags);
7631 +       lgff->effects[id].flags[0] = 0;
7632 +       spin_unlock_irqrestore(&lgff->lock, flags);
7633 +
7634 +       return 0;
7635 +}
7636 +
7637 +static int hid_lgff_upload_effect(struct input_dev* input,
7638 +                                 struct ff_effect* effect)
7639 +{
7640 +       struct hid_device *hid = input->private;
7641 +       struct lgff_device *lgff = hid->ff_private;
7642 +       struct lgff_effect new;
7643 +       int id;
7644 +       unsigned long flags;
7645 +       
7646 +       dbg("ioctl rumble");
7647 +
7648 +       if (!test_bit(effect->type, input->ffbit)) return -EINVAL;
7649 +
7650 +       spin_lock_irqsave(&lgff->lock, flags);
7651 +
7652 +       if (effect->id == -1) {
7653 +               int i;
7654 +
7655 +               for (i=0; i<LGFF_EFFECTS && test_bit(EFFECT_USED, lgff->effects[i].flags); ++i);
7656 +               if (i >= LGFF_EFFECTS) {
7657 +                       spin_unlock_irqrestore(&lgff->lock, flags);
7658 +                       return -ENOSPC;
7659 +               }
7660 +
7661 +               effect->id = i;
7662 +               lgff->effects[i].owner = current->pid;
7663 +               lgff->effects[i].flags[0] = 0;
7664 +               set_bit(EFFECT_USED, lgff->effects[i].flags);
7665 +       }
7666 +
7667 +       id = effect->id;
7668 +       new = lgff->effects[id];
7669 +
7670 +       new.effect = *effect;
7671 +
7672 +       if (test_bit(EFFECT_STARTED, lgff->effects[id].flags)
7673 +           || test_bit(EFFECT_STARTED, lgff->effects[id].flags)) {
7674 +
7675 +               /* Changing replay parameters is not allowed (for the time
7676 +                  being) */
7677 +               if (new.effect.replay.delay != lgff->effects[id].effect.replay.delay
7678 +                   || new.effect.replay.length != lgff->effects[id].effect.replay.length) {
7679 +                       spin_unlock_irqrestore(&lgff->lock, flags);
7680 +                       return -ENOSYS;
7681 +               }
7682 +
7683 +               lgff->effects[id] = new;
7684 +
7685 +       } else {
7686 +               lgff->effects[id] = new;
7687 +       }
7688 +
7689 +       spin_unlock_irqrestore(&lgff->lock, flags);
7690 +       return 0;
7691 +}
7692 +
7693 +static void hid_lgff_compute_constant(struct lgff_effect *effect,
7694 +                                     int *x, int *y)
7695 +{
7696 +       int level;
7697 +       unsigned long now = jiffies;
7698 +       int degrees;
7699 +
7700 +       // During attack ?
7701 +       if (effect->effect.u.constant.envelope.attack_length &&
7702 +           !time_after(now,
7703 +                       effect->started_at
7704 +                       + (effect->effect.u.constant.envelope.attack_length + effect->effect.replay.delay)*HZ/1000)) {
7705 +               level = effect->effect.u.constant.level
7706 +                       - effect->effect.u.constant.envelope.attack_level;
7707 +               //TODO compute incrementally, to save mults and divs
7708 +               level *= now - effect->started_at - effect->effect.replay.delay;
7709 +               level /= effect->effect.u.constant.envelope.attack_length;
7710 +//             dbg("During attack");
7711 +       }
7712 +       // During fade ?
7713 +       else if (effect->effect.replay.length &&
7714 +                effect->effect.u.constant.envelope.fade_length &&
7715 +                time_after(now,
7716 +                           effect->started_at
7717 +                           + (effect->effect.replay.delay + effect->effect.replay.length) * HZ/1000)) {
7718 +               level = effect->effect.u.constant.envelope.fade_level
7719 +                       - effect->effect.u.constant.level;
7720 +               //TODO compute incrementally, to save mults and divs
7721 +               level *= now - (effect->started_at + effect->effect.replay.delay + effect->effect.replay.length - effect->effect.u.constant.envelope.fade_length) ;
7722 +               level /= effect->effect.u.constant.envelope.fade_length;                
7723 +//             dbg("During fade");
7724 +       }
7725 +       else {
7726 +               level = effect->effect.u.constant.level;
7727 +//             dbg("During middle");
7728 +       }
7729 +//     dbg("level = %d", level);
7730 +
7731 +       degrees = effect->effect.direction * 360 >> 16;
7732 +       *x += fixp_mult(fixp_sin(degrees),
7733 +                       level);
7734 +       *y += fixp_mult(-fixp_cos(degrees),
7735 +                       level);
7736 +}
7737 +
7738 +static void hid_lgff_timer(unsigned long timer_data)
7739 +{
7740 +       struct lgff_device *lgff = (struct lgff_device*)timer_data;
7741 +       struct hid_device *hid = lgff->hid;
7742 +       unsigned long flags;
7743 +       int x=0x7fff, y=0x7fff;   // Coordinates of constant effects
7744 +       unsigned int left = 0, right = 0;   // Rumbling
7745 +       int i;
7746 +
7747 +       spin_lock_irqsave(&lgff->lock, flags);
7748 +
7749 +       for (i=0; i<LGFF_EFFECTS; ++i) {
7750 +               struct lgff_effect* effect = lgff->effects +i;
7751 +
7752 +               if (test_bit(EFFECT_PLAYING, effect->flags)) {
7753 +
7754 +                       switch (effect->effect.type) {
7755 +                       case FF_CONSTANT:
7756 +                               hid_lgff_compute_constant(effect, &x, &y);
7757 +                               break;
7758 +                       case FF_RUMBLE:
7759 +                               right += effect->effect.u.rumble.strong_magnitude;
7760 +                               left += effect->effect.u.rumble.weak_magnitude;
7761 +                               break;
7762 +                       };
7763 +
7764 +                       /* One run of the effect is finished playing */
7765 +                       if (effect->effect.replay.length &&
7766 +                           time_after(jiffies,
7767 +                                       effect->started_at
7768 +                                       + effect->effect.replay.delay*HZ/1000
7769 +                                       + effect->effect.replay.length*HZ/1000)) {
7770 +                               dbg("Finished playing once %d", i);
7771 +                               if (--effect->count <= 0) {
7772 +                                       dbg("Stopped %d", i);
7773 +                                       clear_bit(EFFECT_PLAYING, effect->flags);
7774 +                               }
7775 +                               else {
7776 +                                       dbg("Start again %d", i);
7777 +                                       if (effect->effect.replay.length != 0) {
7778 +                                               clear_bit(EFFECT_PLAYING, effect->flags);
7779 +                                               set_bit(EFFECT_STARTED, effect->flags);
7780 +                                       }
7781 +                                       effect->started_at = jiffies;
7782 +                               }
7783 +                       }
7784 +
7785 +               } else if (test_bit(EFFECT_STARTED, lgff->effects[i].flags)) {
7786 +                       /* Check if we should start playing the effect */
7787 +                       if (time_after(jiffies,
7788 +                                       lgff->effects[i].started_at
7789 +                                       + lgff->effects[i].effect.replay.delay*HZ/1000)) {
7790 +                               dbg("Now playing %d", i);
7791 +                               clear_bit(EFFECT_STARTED, lgff->effects[i].flags);
7792 +                               set_bit(EFFECT_PLAYING, lgff->effects[i].flags);
7793 +                       }
7794 +               }
7795 +       }
7796 +
7797 +       x >>= 8;
7798 +       y >>= 8;
7799 +
7800 +#define CLAMP(x) if (x < 0) x = 0; if (x > 0xff) x = 0xff
7801 +
7802 +       // Clamp values
7803 +       CLAMP(x);
7804 +       CLAMP(y);
7805 +       CLAMP(left);
7806 +       CLAMP(right);
7807 +
7808 +#undef CLAMP
7809 +
7810 +       if (x != lgff->constant->field[0]->value[2]
7811 +           || y != lgff->constant->field[0]->value[3]) {
7812 +               lgff->constant->field[0]->value[2] = x;
7813 +               lgff->constant->field[0]->value[3] = y;
7814 +               dbg("(x,y)=(%04x, %04x)", x, y);
7815 +               hid_submit_report(hid, lgff->constant, USB_DIR_OUT);
7816 +       }
7817 +
7818 +       if (left != lgff->rumble->field[0]->value[3]
7819 +           || right != lgff->rumble->field[0]->value[4]) {
7820 +               lgff->rumble->field[0]->value[3] = left;
7821 +               lgff->rumble->field[0]->value[4] = right;
7822 +               dbg("(left,right)=(%04x, %04x)", left, right);
7823 +               hid_submit_report(hid, lgff->rumble, USB_DIR_OUT);
7824 +       }
7825 +
7826 +       if (!test_bit(DEVICE_CLOSING, lgff->flags)) {
7827 +               lgff->timer.expires = RUN_AT(PERIOD);
7828 +               add_timer(&lgff->timer);
7829 +       }
7830 +
7831 +       spin_unlock_irqrestore(&lgff->lock, flags);
7832 +}
7833 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/hid.h linux-modified/drivers/usb/hid.h
7834 --- linux-vanilla/drivers/usb/hid.h     Fri Nov 29 01:53:14 2002
7835 +++ linux-modified/drivers/usb/hid.h    Sun Mar  9 17:01:16 2003
7836 @@ -2,12 +2,10 @@
7837  #define __HID_H
7838  
7839  /*
7840 - * $Id$
7841 + * $Id$
7842   *
7843   *  Copyright (c) 1999 Andreas Gal
7844   *  Copyright (c) 2000-2001 Vojtech Pavlik
7845 - *
7846 - *  Sponsored by SuSE
7847   */
7848  
7849  /*
7850 @@ -26,8 +24,8 @@
7851   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
7852   *
7853   * Should you need to contact me, the author, you can do so either by
7854 - * e-mail - mail your message to <vojtech@suse.cz>, or by paper mail:
7855 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
7856 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
7857 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
7858   */
7859  
7860  #include <linux/types.h>
7861 @@ -41,6 +39,25 @@
7862  #define USB_INTERFACE_CLASS_HID                3
7863  
7864  /*
7865 + * HID class requests
7866 + */
7867 +
7868 +#define HID_REQ_GET_REPORT             0x01
7869 +#define HID_REQ_GET_IDLE               0x02
7870 +#define HID_REQ_GET_PROTOCOL           0x03
7871 +#define HID_REQ_SET_REPORT             0x09
7872 +#define HID_REQ_SET_IDLE               0x0A
7873 +#define HID_REQ_SET_PROTOCOL           0x0B
7874 +
7875 +/*
7876 + * HID class descriptor types
7877 + */
7878 +
7879 +#define HID_DT_HID                     (USB_TYPE_CLASS | 0x01)
7880 +#define HID_DT_REPORT                  (USB_TYPE_CLASS | 0x02)
7881 +#define HID_DT_PHYSICAL                        (USB_TYPE_CLASS | 0x03)
7882 +
7883 +/*
7884   * We parse each description item into this structure. Short items data
7885   * values are expanded to 32-bit signed int, long items contain a pointer
7886   * into the data area.
7887 @@ -158,9 +175,11 @@
7888  #define HID_UP_KEYBOARD        0x00070000
7889  #define HID_UP_LED             0x00080000
7890  #define HID_UP_BUTTON          0x00090000
7891 +#define HID_UP_ORDINAL                 0x000a0000
7892  #define HID_UP_CONSUMER                0x000c0000
7893  #define HID_UP_DIGITIZER       0x000d0000
7894  #define HID_UP_PID             0x000f0000
7895 +#define HID_UP_HPVENDOR         0xff7f0000
7896  
7897  #define HID_USAGE              0x0000ffff
7898  
7899 @@ -199,7 +218,7 @@
7900         __s32    logical_maximum;
7901         __s32    physical_minimum;
7902         __s32    physical_maximum;
7903 -       unsigned unit_exponent;
7904 +       __s32    unit_exponent;
7905         unsigned unit;
7906         unsigned report_id;
7907         unsigned report_size;
7908 @@ -256,9 +275,10 @@
7909         __s32     logical_maximum;
7910         __s32     physical_minimum;
7911         __s32     physical_maximum;
7912 -       unsigned  unit_exponent;
7913 +       __s32     unit_exponent;
7914         unsigned  unit;
7915         struct hid_report *report;      /* associated report */
7916 +       unsigned index;                 /* index into report->field[] */
7917  };
7918  
7919  #define HID_MAX_FIELDS 64
7920 @@ -270,8 +290,6 @@
7921         struct hid_field *field[HID_MAX_FIELDS];        /* fields of the report */
7922         unsigned maxfield;                              /* maximum valid field index */
7923         unsigned size;                                  /* size of the report (bits) */
7924 -       unsigned idx;                                   /* where we're in data */
7925 -       unsigned char *data;                            /* data for multi-packet reports */
7926         struct hid_device *device;                      /* associated device */
7927  };
7928  
7929 @@ -284,16 +302,20 @@
7930  #define HID_REPORT_TYPES 3
7931  
7932  #define HID_BUFFER_SIZE                32
7933 -#define HID_CONTROL_FIFO_SIZE  8
7934 +#define HID_CONTROL_FIFO_SIZE  64
7935 +#define HID_OUTPUT_FIFO_SIZE   64
7936  
7937  struct hid_control_fifo {
7938 -       struct usb_ctrlrequest dr;
7939 -       char buffer[HID_BUFFER_SIZE];
7940 +       unsigned char dir;
7941 +       struct hid_report *report;
7942  };
7943  
7944  #define HID_CLAIMED_INPUT      1
7945  #define HID_CLAIMED_HIDDEV     2
7946  
7947 +#define HID_CTRL_RUNNING       1
7948 +#define HID_OUT_RUNNING                2
7949 +
7950  struct hid_device {                                                    /* device report descriptor */
7951          __u8 *rdesc;
7952         unsigned rsize;
7953 @@ -306,12 +328,23 @@
7954         struct usb_device *dev;                                         /* USB device */
7955         int ifnum;                                                      /* USB interface number */
7956  
7957 -       struct urb urb;                                                 /* USB URB structure */
7958 -       char buffer[HID_BUFFER_SIZE];                                   /* Rx buffer */
7959 +       unsigned long iofl;                                             /* I/O flags (CTRL_RUNNING, OUT_RUNNING) */
7960  
7961 -       struct urb urbout;                                              /* Output URB */
7962 -       struct hid_control_fifo out[HID_CONTROL_FIFO_SIZE];             /* Transmit buffer */
7963 -       unsigned char outhead, outtail;                                 /* Tx buffer head & tail */
7964 +       struct urb *urbin;                                              /* Input URB */
7965 +       char inbuf[HID_BUFFER_SIZE];                                    /* Input buffer */
7966 +
7967 +       struct urb *urbctrl;                                            /* Control URB */
7968 +       struct usb_ctrlrequest dr;                                                      /* Control request struct */
7969 +       struct hid_control_fifo ctrl[HID_CONTROL_FIFO_SIZE];            /* Control fifo */
7970 +       unsigned char ctrlhead, ctrltail;                               /* Control fifo head & tail */
7971 +       char ctrlbuf[HID_BUFFER_SIZE];                                  /* Control buffer */
7972 +       spinlock_t ctrllock;                                            /* Control fifo spinlock */
7973 +
7974 +       struct urb *urbout;                                             /* Output URB */
7975 +       struct hid_report *out[HID_CONTROL_FIFO_SIZE];                  /* Output pipe fifo */
7976 +       unsigned char outhead, outtail;                                 /* Output pipe fifo head & tail */
7977 +       char outbuf[HID_BUFFER_SIZE];                                   /* Output buffer */
7978 +       spinlock_t outlock;                                             /* Output fifo spinlock */
7979  
7980         unsigned claimed;                                               /* Claimed by hidinput, hiddev? */      
7981         unsigned quirks;                                                /* Various quirks the device can pull on us */
7982 @@ -320,8 +353,17 @@
7983         void *hiddev;                                                   /* The hiddev structure */
7984         int minor;                                                      /* Hiddev minor number */
7985  
7986 +       wait_queue_head_t wait;                                         /* For sleeping */
7987 +
7988         int open;                                                       /* is the device open by anyone? */
7989         char name[128];                                                 /* Device name */
7990 +       char phys[64];                                                  /* Device physical location */
7991 +       char uniq[64];                                                  /* Device unique identifier (serial #) */
7992 +
7993 +       void *ff_private;                                               /* Private data for the force-feedback driver */
7994 +       void (*ff_exit)(struct hid_device*);                            /* Called by hid_exit_ff(hid) */
7995 +       int (*ff_event)(struct hid_device *hid, struct input_dev *input,
7996 +                       unsigned int type, unsigned int code, int value);
7997  };
7998  
7999  #define HID_GLOBAL_STACK_SIZE 4
8000 @@ -352,32 +394,44 @@
8001         struct hid_class_descriptor desc[1];
8002  } __attribute__ ((packed));
8003  
8004 +void hidinput_hid_event(struct hid_device *, struct hid_field *, struct hid_usage *, __s32);
8005 +int hidinput_connect(struct hid_device *);
8006 +void hidinput_disconnect(struct hid_device *);
8007  
8008  #ifdef DEBUG
8009  #include "hid-debug.h"
8010  #else
8011  #define hid_dump_input(a,b)    do { } while (0)
8012  #define hid_dump_device(c)     do { } while (0)
8013 +#define hid_dump_field(a,b)    do { } while (0)
8014  #endif
8015  
8016  #endif
8017  
8018 -#ifdef CONFIG_USB_HIDINPUT
8019 -#define IS_INPUT_APPLICATION(a) (((a >= 0x00010000) && (a <= 0x00010008)) || (a == 0x00010080) || ( a == 0x000c0001))
8020 -extern void hidinput_hid_event(struct hid_device *, struct hid_field *, struct hid_usage *, __s32);
8021 -extern int hidinput_connect(struct hid_device *);
8022 -extern void hidinput_disconnect(struct hid_device *);
8023 -#else
8024 -#define IS_INPUT_APPLICATION(a) (0)
8025 -static inline void hidinput_hid_event(struct hid_device *hid, struct hid_field *field, struct hid_usage *usage, __s32 value) { }
8026 -static inline int hidinput_connect(struct hid_device *hid) { return -ENODEV; }
8027 -static inline void hidinput_disconnect(struct hid_device *hid) { }
8028 -#endif
8029 +/* Applications from HID Usage Tables 4/8/99 Version 1.1 */
8030 +/* We ignore a few input applications that are not widely used */
8031 +#define IS_INPUT_APPLICATION(a) (((a >= 0x00010000) && (a <= 0x00010008)) || ( a == 0x00010080) || ( a == 0x000c0001))
8032  
8033  int hid_open(struct hid_device *);
8034  void hid_close(struct hid_device *);
8035  int hid_find_field(struct hid_device *, unsigned int, unsigned int, struct hid_field **);
8036  int hid_set_field(struct hid_field *, unsigned, __s32);
8037 -void hid_write_report(struct hid_device *, struct hid_report *);
8038 -void hid_read_report(struct hid_device *, struct hid_report *);
8039 +void hid_submit_report(struct hid_device *, struct hid_report *, unsigned char dir);
8040  void hid_init_reports(struct hid_device *hid);
8041 +
8042 +
8043 +#ifdef CONFIG_HID_FF
8044 +
8045 +int hid_ff_init(struct hid_device *hid);
8046 +static inline void hid_ff_exit(struct hid_device *hid)
8047 +{
8048 +       if (hid->ff_exit) hid->ff_exit(hid);
8049 +}
8050 +
8051 +static inline int hid_ff_event(struct hid_device *hid, struct input_dev *input,
8052 +                       unsigned int type, unsigned int code, int value)
8053 +{
8054 +       if (hid->ff_event) return hid->ff_event(hid, input, type, code, value);
8055 +       return -ENOSYS;
8056 +}
8057 +#endif
8058 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/hiddev.c linux-modified/drivers/usb/hiddev.c
8059 --- linux-vanilla/drivers/usb/hiddev.c  Sun Oct 21 04:13:11 2001
8060 +++ linux-modified/drivers/usb/hiddev.c Mon Jan  6 16:48:21 2003
8061 @@ -50,9 +50,10 @@
8062  };
8063  
8064  struct hiddev_list {
8065 -       struct hiddev_event buffer[HIDDEV_BUFFER_SIZE];
8066 +       struct hiddev_usage_ref buffer[HIDDEV_BUFFER_SIZE];
8067         int head;
8068         int tail;
8069 +       unsigned flags;
8070         struct fasync_struct *fasync;
8071         struct hiddev *hiddev;
8072         struct hiddev_list *next;
8073 @@ -146,17 +147,19 @@
8074   * This is where hid.c calls into hiddev to pass an event that occurred over
8075   * the interrupt pipe
8076   */
8077 -void hiddev_hid_event(struct hid_device *hid, unsigned int usage, int value)
8078 +void hiddev_hid_event(struct hid_device *hid, struct hiddev_usage_ref *uref)
8079  {
8080         struct hiddev *hiddev = hid->hiddev;
8081         struct hiddev_list *list = hiddev->list;
8082  
8083         while (list) {
8084 -               list->buffer[list->head].hid = usage;
8085 -               list->buffer[list->head].value = value;
8086 -               list->head = (list->head + 1) & (HIDDEV_BUFFER_SIZE - 1);
8087 -
8088 -               kill_fasync(&list->fasync, SIGIO, POLL_IN);
8089 +               if (uref->field_index != HID_FIELD_INDEX_NONE ||
8090 +                   (list->flags & HIDDEV_FLAG_REPORT) != 0) {
8091 +                       list->buffer[list->head] = *uref;
8092 +                       list->head = (list->head + 1) & 
8093 +                               (HIDDEV_BUFFER_SIZE - 1);
8094 +                       kill_fasync(&list->fasync, SIGIO, POLL_IN);
8095 +               }
8096  
8097                 list = list->next;
8098         }
8099 @@ -193,7 +196,6 @@
8100         struct hiddev_list *list = file->private_data;
8101         struct hiddev_list **listptr;
8102  
8103 -       lock_kernel();
8104         listptr = &list->hiddev->list;
8105         hiddev_fasync(-1, file, 0);
8106  
8107 @@ -209,7 +211,6 @@
8108         }
8109  
8110         kfree(list);
8111 -       unlock_kernel();
8112  
8113         return 0;
8114  }
8115 @@ -220,7 +221,7 @@
8116  static int hiddev_open(struct inode * inode, struct file * file) {
8117         struct hiddev_list *list;
8118  
8119 -       int i = MINOR(inode->i_rdev) - HIDDEV_MINOR_BASE;
8120 +       int i = minor(inode->i_rdev) - HIDDEV_MINOR_BASE;
8121  
8122         if (i >= HIDDEV_MINORS || !hiddev_table[i])
8123                 return -ENODEV;
8124 @@ -259,43 +260,67 @@
8125  {
8126         DECLARE_WAITQUEUE(wait, current);
8127         struct hiddev_list *list = file->private_data;
8128 +       int event_size;
8129         int retval = 0;
8130  
8131 -       if (list->head == list->tail) {
8132 -
8133 -               add_wait_queue(&list->hiddev->wait, &wait);
8134 -               set_current_state(TASK_INTERRUPTIBLE);
8135 +       event_size = ((list->flags & HIDDEV_FLAG_UREF) != 0) ?
8136 +               sizeof(struct hiddev_usage_ref) : sizeof(struct hiddev_event);
8137  
8138 -               while (list->head == list->tail) {
8139 +       if (count < event_size) return 0;
8140  
8141 -                       if (file->f_flags & O_NONBLOCK) {
8142 -                               retval = -EAGAIN;
8143 -                               break;
8144 -                       }
8145 -                       if (signal_pending(current)) {
8146 -                               retval = -ERESTARTSYS;
8147 -                               break;
8148 -                       }
8149 -                       if (!list->hiddev->exist) {
8150 -                               retval = -EIO;
8151 -                               break;
8152 +       while (retval == 0) {
8153 +               if (list->head == list->tail) {
8154 +                       add_wait_queue(&list->hiddev->wait, &wait);
8155 +                       set_current_state(TASK_INTERRUPTIBLE);
8156 +                       
8157 +                       while (list->head == list->tail) {
8158 +                               if (file->f_flags & O_NONBLOCK) {
8159 +                                       retval = -EAGAIN;
8160 +                                       break;
8161 +                               }
8162 +                               if (signal_pending(current)) {
8163 +                                       retval = -ERESTARTSYS;
8164 +                                       break;
8165 +                               }
8166 +                               if (!list->hiddev->exist) {
8167 +                                       retval = -EIO;
8168 +                                       break;
8169 +                               }
8170 +                               
8171 +                               schedule();
8172                         }
8173  
8174 -                       schedule();
8175 +                       set_current_state(TASK_RUNNING);
8176 +                       remove_wait_queue(&list->hiddev->wait, &wait);
8177                 }
8178  
8179 -               set_current_state(TASK_RUNNING);
8180 -               remove_wait_queue(&list->hiddev->wait, &wait);
8181 -       }
8182 +               if (retval)
8183 +                       return retval;
8184  
8185 -       if (retval)
8186 -               return retval;
8187  
8188 -       while (list->head != list->tail && retval + sizeof(struct hiddev_event) <= count) {
8189 -               if (copy_to_user(buffer + retval, list->buffer + list->tail,
8190 -                                sizeof(struct hiddev_event))) return -EFAULT;
8191 -               list->tail = (list->tail + 1) & (HIDDEV_BUFFER_SIZE - 1);
8192 -               retval += sizeof(struct hiddev_event);
8193 +               while (list->head != list->tail && 
8194 +                      retval + event_size <= count) {
8195 +                       if ((list->flags & HIDDEV_FLAG_UREF) == 0) {
8196 +                               if (list->buffer[list->tail].field_index !=
8197 +                                   HID_FIELD_INDEX_NONE) {
8198 +                                       struct hiddev_event event;
8199 +                                       event.hid = list->buffer[list->tail].usage_code;
8200 +                                       event.value = list->buffer[list->tail].value;
8201 +                                       if (copy_to_user(buffer + retval, &event, sizeof(struct hiddev_event)))
8202 +                                               return -EFAULT;
8203 +                                       retval += sizeof(struct hiddev_event);
8204 +                               }
8205 +                       } else {
8206 +                               if (list->buffer[list->tail].field_index != HID_FIELD_INDEX_NONE ||
8207 +                                   (list->flags & HIDDEV_FLAG_REPORT) != 0) {
8208 +                                       if (copy_to_user(buffer + retval, list->buffer + list->tail, sizeof(struct hiddev_usage_ref)))
8209 +                                               return -EFAULT;
8210 +                                       retval += sizeof(struct hiddev_usage_ref);
8211 +                               }
8212 +                       }
8213 +                       list->tail = (list->tail + 1) & (HIDDEV_BUFFER_SIZE - 1);
8214 +               }
8215 +
8216         }
8217  
8218         return retval;
8219 @@ -360,6 +385,25 @@
8220                 return copy_to_user((void *) arg, &dinfo, sizeof(dinfo));
8221         }
8222  
8223 +       case HIDIOCGFLAG:
8224 +               return put_user(list->flags, (int *) arg);
8225 +
8226 +       case HIDIOCSFLAG:
8227 +               {
8228 +                       int newflags;
8229 +                       if (get_user(newflags, (int *) arg))
8230 +                               return -EFAULT;
8231 +
8232 +                       if ((newflags & ~HIDDEV_FLAGS) != 0 ||
8233 +                           ((newflags & HIDDEV_FLAG_REPORT) != 0 &&
8234 +                            (newflags & HIDDEV_FLAG_UREF) == 0))
8235 +                               return -EINVAL;
8236 +
8237 +                       list->flags = newflags;
8238 +
8239 +                       return 0;
8240 +               }
8241 +
8242         case HIDIOCGSTRING:
8243                 {
8244                         int idx, len;
8245 @@ -402,7 +446,7 @@
8246                 if ((report = hiddev_lookup_report(hid, &rinfo)) == NULL)
8247                         return -EINVAL;
8248  
8249 -               hid_read_report(hid, report);
8250 +               hid_submit_report(hid, report, USB_DIR_IN);
8251  
8252                 return 0;
8253  
8254 @@ -416,7 +460,7 @@
8255                 if ((report = hiddev_lookup_report(hid, &rinfo)) == NULL)
8256                         return -EINVAL;
8257  
8258 -               hid_write_report(hid, report);
8259 +               hid_submit_report(hid, report, USB_DIR_OUT);
8260  
8261                 return 0;
8262  
8263 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/usb-ohci.c linux-modified/drivers/usb/usb-ohci.c
8264 --- linux-vanilla/drivers/usb/usb-ohci.c        Fri Nov 29 01:53:15 2002
8265 +++ linux-modified/drivers/usb/usb-ohci.c       Mon Jan  6 16:48:21 2003
8266 @@ -74,7 +74,7 @@
8267  #include <asm/unaligned.h>
8268  
8269  #define OHCI_USE_NPS           // force NoPowerSwitching mode
8270 -// #define OHCI_VERBOSE_DEBUG  /* not always helpful */
8271 +#undef OHCI_VERBOSE_DEBUG      /* not always helpful */
8272  
8273  #include "usb-ohci.h"
8274  
8275 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/usbkbd.c linux-modified/drivers/usb/usbkbd.c
8276 --- linux-vanilla/drivers/usb/usbkbd.c  Fri Nov 29 01:53:15 2002
8277 +++ linux-modified/drivers/usb/usbkbd.c Mon Jan  6 16:48:21 2003
8278 @@ -250,8 +250,8 @@
8279                         
8280         input_register_device(&kbd->dev);
8281  
8282 -       printk(KERN_INFO "input%d: %s on usb%d:%d.%d\n",
8283 -                kbd->dev.number, kbd->name, dev->bus->busnum, dev->devnum, ifnum);
8284 +       printk(KERN_INFO "input: %s on usb%d:%d.%d\n",
8285 +                kbd->name, dev->bus->busnum, dev->devnum, ifnum);
8286  
8287         return kbd;
8288  }
8289 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/usbmouse.c linux-modified/drivers/usb/usbmouse.c
8290 --- linux-vanilla/drivers/usb/usbmouse.c        Sat Aug  3 02:39:45 2002
8291 +++ linux-modified/drivers/usb/usbmouse.c       Mon Jan  6 16:48:21 2003
8292 @@ -166,8 +166,8 @@
8293  
8294         input_register_device(&mouse->dev);
8295  
8296 -       printk(KERN_INFO "input%d: %s on usb%d:%d.%d\n",
8297 -                mouse->dev.number, mouse->name, dev->bus->busnum, dev->devnum, ifnum);
8298 +       printk(KERN_INFO "input: %s on usb%d:%d.%d\n",
8299 +                mouse->name, dev->bus->busnum, dev->devnum, ifnum);
8300  
8301         return mouse;
8302  }
8303 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/drivers/usb/wacom.c linux-modified/drivers/usb/wacom.c
8304 --- linux-vanilla/drivers/usb/wacom.c   Fri Nov 29 01:53:15 2002
8305 +++ linux-modified/drivers/usb/wacom.c  Mon Jan  6 16:48:21 2003
8306 @@ -491,8 +491,8 @@
8307         usb_set_report(dev, ifnum, 3, 5, rep_data, 0);
8308         usb_set_report(dev, ifnum, 3, 6, rep_data, 0);
8309         
8310 -       printk(KERN_INFO "input%d: %s on usb%d:%d.%d\n",
8311 -              wacom->dev.number, wacom->features->name, dev->bus->busnum, dev->devnum, ifnum);
8312 +       printk(KERN_INFO "input: %s on usb%d:%d.%d\n",
8313 +              wacom->features->name, dev->bus->busnum, dev->devnum, ifnum);
8314  
8315         return wacom;
8316  }
8317 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/include/linux/hiddev.h linux-modified/include/linux/hiddev.h
8318 --- linux-vanilla/include/linux/hiddev.h        Fri Nov 29 01:53:15 2002
8319 +++ linux-modified/include/linux/hiddev.h       Sun Mar  9 17:01:16 2003
8320 @@ -2,7 +2,7 @@
8321  #define _HIDDEV_H
8322  
8323  /*
8324 - * $Id$
8325 + * $Id$
8326   *
8327   *  Copyright (c) 1999-2000 Vojtech Pavlik
8328   *
8329 @@ -25,8 +25,8 @@
8330   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
8331   * 
8332   * Should you need to contact me, the author, you can do so either by
8333 - * e-mail - mail your message to <vojtech@suse.cz>, or by paper mail:
8334 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
8335 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
8336 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
8337   */
8338  
8339  /*
8340 @@ -119,12 +119,17 @@
8341         __s32 value;
8342  };
8343  
8344 +/* FIELD_INDEX_NONE is returned in read() data from the kernel when flags
8345 + * is set to (HIDDEV_FLAG_UREF | HIDDEV_FLAG_REPORT) and a new report has
8346 + * been sent by the device 
8347 + */
8348 +#define HID_FIELD_INDEX_NONE 0xffffffff
8349  
8350  /*
8351   * Protocol version.
8352   */
8353  
8354 -#define HID_VERSION            0x010002
8355 +#define HID_VERSION            0x010003
8356  
8357  /*
8358   * IOCTLs (0x00 - 0x7f)
8359 @@ -138,11 +143,20 @@
8360  #define HIDIOCGNAME(len)       _IOC(_IOC_READ, 'H', 0x06, len)
8361  #define HIDIOCGREPORT          _IOW('H', 0x07, struct hiddev_report_info)
8362  #define HIDIOCSREPORT          _IOW('H', 0x08, struct hiddev_report_info)
8363 -#define HIDIOCGREPORTINFO       _IOWR('H', 0x09, struct hiddev_report_info)
8364 -#define HIDIOCGFIELDINFO        _IOWR('H', 0x0A, struct hiddev_field_info)
8365 -#define HIDIOCGUSAGE            _IOWR('H', 0x0B, struct hiddev_usage_ref)
8366 -#define HIDIOCSUSAGE            _IOW('H', 0x0C, struct hiddev_usage_ref)
8367 -#define HIDIOCGUCODE            _IOWR('H', 0x0D, struct hiddev_usage_ref)
8368 +#define HIDIOCGREPORTINFO      _IOWR('H', 0x09, struct hiddev_report_info)
8369 +#define HIDIOCGFIELDINFO       _IOWR('H', 0x0A, struct hiddev_field_info)
8370 +#define HIDIOCGUSAGE           _IOWR('H', 0x0B, struct hiddev_usage_ref)
8371 +#define HIDIOCSUSAGE           _IOW('H', 0x0C, struct hiddev_usage_ref)
8372 +#define HIDIOCGUCODE           _IOWR('H', 0x0D, struct hiddev_usage_ref)
8373 +#define HIDIOCGFLAG            _IOR('H', 0x0E, int)
8374 +#define HIDIOCSFLAG            _IOW('H', 0x0F, int)
8375 +
8376 +/* 
8377 + * Flags to be used in HIDIOCSFLAG
8378 + */
8379 +#define HIDDEV_FLAG_UREF       0x1
8380 +#define HIDDEV_FLAG_REPORT     0x2
8381 +#define HIDDEV_FLAGS           0x3
8382  
8383  /* To traverse the input report descriptor info for a HID device, perform the 
8384   * following:
8385 @@ -179,13 +193,13 @@
8386  #ifdef CONFIG_USB_HIDDEV
8387  int hiddev_connect(struct hid_device *);
8388  void hiddev_disconnect(struct hid_device *);
8389 -void hiddev_hid_event(struct hid_device *, unsigned int usage, int value);
8390 +void hiddev_hid_event(struct hid_device *, struct hiddev_usage_ref *ref);
8391  int __init hiddev_init(void);
8392  void __exit hiddev_exit(void);
8393  #else
8394  static inline int hiddev_connect(struct hid_device *hid) { return -1; }
8395  static inline void hiddev_disconnect(struct hid_device *hid) { }
8396 -static inline void hiddev_hid_event(struct hid_device *hid, unsigned int usage, int value) { }
8397 +static inline void hiddev_hid_event(struct hid_device *, struct hiddev_usage_ref *ref) { }
8398  static inline int hiddev_init(void) { return 0; }
8399  static inline void hiddev_exit(void) { }
8400  #endif
8401 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/include/linux/input.h linux-modified/include/linux/input.h
8402 --- linux-vanilla/include/linux/input.h Sun Jan 26 16:09:49 2003
8403 +++ linux-modified/include/linux/input.h        Sun Mar  9 16:58:14 2003
8404 @@ -2,11 +2,9 @@
8405  #define _INPUT_H
8406  
8407  /*
8408 - * $Id$
8409 + * $Id$
8410   *
8411 - *  Copyright (c) 1999-2000 Vojtech Pavlik
8412 - *
8413 - *  Sponsored by SuSE
8414 + *  Copyright (c) 1999-2001 Vojtech Pavlik
8415   */
8416  
8417  /*
8418 @@ -17,7 +15,7 @@
8419   *
8420   * This program is distributed in the hope that it will be useful,
8421   * but WITHOUT ANY WARRANTY; without even the implied warranty of
8422 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
8423 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
8424   * GNU General Public License for more details.
8425   *
8426   * You should have received a copy of the GNU General Public License
8427 @@ -25,8 +23,8 @@
8428   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
8429   *
8430   * Should you need to contact me, the author, you can do so either by
8431 - * e-mail - mail your message to <vojtech@suse.cz>, or by paper mail:
8432 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
8433 + * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
8434 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
8435   */
8436  
8437  #ifdef __KERNEL__
8438 @@ -64,17 +62,20 @@
8439  #define EVIOCSREP              _IOW('E', 0x03, int[2])                 /* get repeat settings */
8440  #define EVIOCGKEYCODE          _IOR('E', 0x04, int[2])                 /* get keycode */
8441  #define EVIOCSKEYCODE          _IOW('E', 0x04, int[2])                 /* set keycode */
8442 -#define EVIOCGKEY              _IOR('E', 0x05, int[2])                 /* get key value */
8443 +
8444  #define EVIOCGNAME(len)                _IOC(_IOC_READ, 'E', 0x06, len)         /* get device name */
8445 -#define EVIOCGBUS              _IOR('E', 0x07, short[4])               /* get bus address */
8446 +#define EVIOCGPHYS(len)                _IOC(_IOC_READ, 'E', 0x07, len)         /* get physical location */
8447 +#define EVIOCGUNIQ(len)                _IOC(_IOC_READ, 'E', 0x08, len)         /* get unique identifier */
8448 +
8449 +#define EVIOCGKEY(len)         _IOC(_IOC_READ, 'E', 0x18, len)         /* get global keystate */
8450 +#define EVIOCGLED(len)         _IOC(_IOC_READ, 'E', 0x19, len)         /* get all LEDs */
8451 +#define EVIOCGSND(len)         _IOC(_IOC_READ, 'E', 0x1a, len)         /* get all sounds status */
8452  
8453  #define EVIOCGBIT(ev,len)      _IOC(_IOC_READ, 'E', 0x20 + ev, len)    /* get event bits */
8454  #define EVIOCGABS(abs)         _IOR('E', 0x40 + abs, int[5])           /* get abs value/limits */
8455  
8456  #define EVIOCSFF               _IOC(_IOC_WRITE, 'E', 0x80, sizeof(struct ff_effect))   /* send a force effect to a force feedback device */
8457  #define EVIOCRMFF              _IOW('E', 0x81, int)                    /* Erase a force effect */
8458 -#define EVIOCSGAIN             _IOW('E', 0x82, unsigned short)         /* Set overall gain */
8459 -#define EVIOCSAUTOCENTER       _IOW('E', 0x83, unsigned short)         /* Enable or disable auto-centering */
8460  #define EVIOCGEFFECTS          _IOR('E', 0x84, int)                    /* Report number of effects playable at the same time */
8461  
8462  /*
8463 @@ -90,6 +91,8 @@
8464  #define EV_SND                 0x12
8465  #define EV_REP                 0x14
8466  #define EV_FF                  0x15
8467 +#define EV_PWR                 0x16
8468 +#define EV_FF_STATUS           0x17
8469  #define EV_MAX                 0x1f
8470  
8471  /*
8472 @@ -304,8 +307,27 @@
8473  #define KEY_PROG4              203
8474  #define KEY_SUSPEND            205
8475  #define KEY_CLOSE              206
8476 +#define KEY_PLAY               207
8477 +#define KEY_FASTFORWARD                208
8478 +#define KEY_BASSBOOST          209
8479 +#define KEY_PRINT              210
8480 +#define KEY_HP                 211
8481 +#define KEY_CAMERA             212
8482 +#define KEY_SOUND              213
8483 +#define KEY_QUESTION           214
8484 +#define KEY_EMAIL              215
8485 +#define KEY_CHAT               216
8486 +#define KEY_SEARCH             217
8487 +#define KEY_CONNECT            218
8488 +#define KEY_FINANCE            219
8489 +#define KEY_SPORT              220
8490 +#define KEY_SHOP               221
8491 +#define KEY_ALTERASE           222
8492 +#define KEY_CANCEL             223
8493 +#define KEY_BRIGHTNESSDOWN     224
8494 +#define KEY_BRIGHTNESSUP       225
8495  
8496 -#define KEY_UNKNOWN            220
8497 +#define KEY_UNKNOWN            240
8498  
8499  #define KEY_BRIGHTNESSDOWN     224
8500  #define KEY_BRIGHTNESSUP       225
8501 @@ -376,6 +398,10 @@
8502  #define BTN_STYLUS             0x14b
8503  #define BTN_STYLUS2            0x14c
8504  
8505 +#define BTN_WHEEL              0x150
8506 +#define BTN_GEAR_DOWN          0x150
8507 +#define BTN_GEAR_UP            0x151
8508 +
8509  #define KEY_MAX                        0x1ff
8510  
8511  /*
8512 @@ -419,7 +445,8 @@
8513  #define ABS_TILT_X             0x1a
8514  #define ABS_TILT_Y             0x1b
8515  #define ABS_MISC               0x1c
8516 -#define ABS_MAX                        0x1f
8517 +#define ABS_VOLUME             0x20
8518 +#define ABS_MAX                        0x3f
8519  
8520  /*
8521   * Misc events
8522 @@ -485,67 +512,89 @@
8523  #define BUS_I2C                        0x18
8524  
8525  /*
8526 + * Values describing the status of an effect
8527 + */
8528 +#define FF_STATUS_STOPPED      0x00
8529 +#define FF_STATUS_PLAYING      0x01
8530 +#define FF_STATUS_MAX          0x01
8531 +
8532 +/*
8533   * Structures used in ioctls to upload effects to a device
8534   * The first structures are not passed directly by using ioctls.
8535   * They are sub-structures of the actually sent structure (called ff_effect)
8536   */
8537  
8538  struct ff_replay {
8539 -       __u16 length;           /* Duration of an effect */
8540 +       __u16 length;           /* Duration of an effect in ms.
8541 +                                  All other times are also expressed in ms.
8542 +                                  0 means "play for ever" */
8543         __u16 delay;            /* Time to wait before to start playing an effect */
8544  };
8545  
8546  struct ff_trigger {
8547         __u16 button;           /* Number of button triggering an effect */
8548 -       __u16 interval;         /* Time to wait before an effect can be re-triggered */
8549 +       __u16 interval;         /* Time to wait before an effect can be re-triggered (ms) */
8550  };
8551  
8552 -struct ff_shape {
8553 -       __u16 attack_length;    /* Duration of attack */
8554 -       __s16 attack_level;     /* Level at beginning of attack */
8555 -       __u16 fade_length;      /* Duration of fade */
8556 -       __s16 fade_level;       /* Level at end of fade */
8557 +struct ff_envelope {
8558 +       __u16 attack_length;    /* Duration of attack (ms) */
8559 +       __u16 attack_level;     /* Level at beginning of attack */
8560 +       __u16 fade_length;      /* Duration of fade (ms) */
8561 +       __u16 fade_level;       /* Level at end of fade */
8562  };
8563  
8564  /* FF_CONSTANT */
8565  struct ff_constant_effect {
8566 -       __s16 level;            /* Strength of effect */
8567 -       __u16 direction;        /* Direction of effect (see periodic effects) */
8568 -       struct ff_shape shape;
8569 +       __s16 level;            /* Strength of effect. Negative values are OK */
8570 +       struct ff_envelope envelope;
8571  };
8572  
8573 -/* FF_SPRING of FF_FRICTION */
8574 -struct ff_interactive_effect {
8575 -/* Axis along which effect must be created. If null, the field named direction
8576 - * is used
8577 - * It is a bit array (ie to enable axes X and Y, use BIT(ABS_X) | BIT(ABS_Y)
8578 - */
8579 -       __u16 axis;
8580 -       __u16 direction;
8581 +/* FF_RAMP */
8582 +struct ff_ramp_effect {
8583 +       __s16 start_level;
8584 +       __s16 end_level;
8585 +       struct ff_envelope envelope;
8586 +};
8587  
8588 -       __s16 right_saturation; /* Max level when joystick is on the right */
8589 -       __s16 left_saturation;  /* Max level when joystick in on the left */
8590 +/* FF_SPRING of FF_FRICTION */
8591 +struct ff_condition_effect {
8592 +       __u16 right_saturation; /* Max level when joystick is on the right */
8593 +       __u16 left_saturation;  /* Max level when joystick in on the left */
8594  
8595         __s16 right_coeff;      /* Indicates how fast the force grows when the
8596                                    joystick moves to the right */
8597         __s16 left_coeff;       /* Same for left side */
8598  
8599         __u16 deadband;         /* Size of area where no force is produced */
8600 -       __s16 center;           /* Position of dead dead zone */
8601 +       __s16 center;           /* Position of dead zone */
8602  
8603  };
8604  
8605  /* FF_PERIODIC */
8606  struct ff_periodic_effect {
8607         __u16 waveform;         /* Kind of wave (sine, square...) */
8608 -       __u16 period;
8609 +       __u16 period;           /* in ms */
8610         __s16 magnitude;        /* Peak value */
8611         __s16 offset;           /* Mean value of wave (roughly) */
8612         __u16 phase;            /* 'Horizontal' shift */
8613 -       __u16 direction;        /* Direction. 0 deg -> 0x0000
8614 -                                            90 deg -> 0x4000 */
8615  
8616 -       struct ff_shape shape;
8617 +       struct ff_envelope envelope;
8618 +
8619 +/* Only used if waveform == FF_CUSTOM */
8620 +       __u32 custom_len;       /* Number of samples  */        
8621 +       __s16 *custom_data;     /* Buffer of samples */
8622 +/* Note: the data pointed by custom_data is copied by the driver. You can
8623 + * therefore dispose of the memory after the upload/update */
8624 +};
8625 +
8626 +/* FF_RUMBLE */
8627 +/* Some rumble pads have two motors of different weight.
8628 +   strong_magnitude represents the magnitude of the vibration generated
8629 +   by the heavy motor.
8630 +*/
8631 +struct ff_rumble_effect {
8632 +        __u16 strong_magnitude;  /* Magnitude of the heavy motor */
8633 +        __u16 weak_magnitude;    /* Magnitude of the light one */
8634  };
8635  
8636  /*
8637 @@ -554,36 +603,30 @@
8638  struct ff_effect {
8639         __u16 type;
8640  /* Following field denotes the unique id assigned to an effect.
8641 - * It is set by the driver.
8642 + * If user sets if to -1, a new effect is created, and its id is returned in the same field
8643 + * Else, the user sets it to the effect id it wants to update.
8644   */
8645         __s16 id;
8646  
8647 +       __u16 direction;        /* Direction. 0 deg -> 0x0000 (down)
8648 +                                            90 deg -> 0x4000 (left)
8649 +                                           180 deg -> 0x8000 (up)
8650 +                                           270 deg -> 0xC000 (right)
8651 +                               */
8652 +
8653         struct ff_trigger trigger;
8654         struct ff_replay replay;
8655  
8656         union {
8657                 struct ff_constant_effect constant;
8658 +               struct ff_ramp_effect ramp;
8659                 struct ff_periodic_effect periodic;
8660 -               struct ff_interactive_effect interactive;
8661 +               struct ff_condition_effect condition[2];        /* One for each axis */
8662 +                struct ff_rumble_effect rumble;
8663         } u;
8664  };
8665  
8666  /*
8667 - * Buttons that can trigger effects.  Use for example FF_BTN(BTN_TRIGGER) to
8668 - * access the bitmap.
8669 - */
8670 -
8671 -#define FF_BTN(x)      ((x) - BTN_MISC + FF_BTN_OFFSET)
8672 -#define FF_BTN_OFFSET  0x00
8673 -
8674 -/*
8675 - * Force feedback axis mappings. Use FF_ABS() to access the bitmap.
8676 - */
8677 -
8678 -#define FF_ABS(x)      ((x) + FF_ABS_OFFSET)
8679 -#define FF_ABS_OFFSET  0x40
8680 -
8681 -/*
8682   * Force feedback effect types
8683   */
8684  
8685 @@ -592,6 +635,9 @@
8686  #define FF_CONSTANT    0x52
8687  #define FF_SPRING      0x53
8688  #define FF_FRICTION    0x54
8689 +#define FF_DAMPER      0x55
8690 +#define FF_INERTIA     0x56
8691 +#define FF_RAMP                0x57
8692  
8693  /*
8694   * Force feedback periodic effect types
8695 @@ -630,8 +676,9 @@
8696  
8697         void *private;
8698  
8699 -       int number;
8700         char *name;
8701 +       char *phys;
8702 +       char *uniq;
8703         unsigned short idbus;
8704         unsigned short idvendor;
8705         unsigned short idproduct;
8706 @@ -654,6 +701,9 @@
8707         unsigned int repeat_key;
8708         struct timer_list timer;
8709  
8710 +       struct pm_dev *pm_dev;
8711 +       int state;
8712 +
8713         int abs[ABS_MAX + 1];
8714         int rep[REP_MAX + 1];
8715  
8716 @@ -668,6 +718,8 @@
8717  
8718         int (*open)(struct input_dev *dev);
8719         void (*close)(struct input_dev *dev);
8720 +       int (*accept)(struct input_dev *dev, struct file *file);
8721 +       int (*flush)(struct input_dev *dev, struct file *file);
8722         int (*event)(struct input_dev *dev, unsigned int type, unsigned int code, int value);
8723         int (*upload_effect)(struct input_dev *dev, struct ff_effect *effect);
8724         int (*erase_effect)(struct input_dev *dev, int effect_id);
8725 @@ -676,16 +728,63 @@
8726         struct input_dev *next;
8727  };
8728  
8729 +/*
8730 + * Structure for hotplug & device<->driver matching.
8731 + */
8732 +
8733 +#define INPUT_DEVICE_ID_MATCH_BUS      1
8734 +#define INPUT_DEVICE_ID_MATCH_VENDOR   2
8735 +#define INPUT_DEVICE_ID_MATCH_PRODUCT  4
8736 +#define INPUT_DEVICE_ID_MATCH_VERSION  8
8737 +
8738 +#define INPUT_DEVICE_ID_MATCH_EVBIT    0x010
8739 +#define INPUT_DEVICE_ID_MATCH_KEYBIT   0x020
8740 +#define INPUT_DEVICE_ID_MATCH_RELBIT   0x040
8741 +#define INPUT_DEVICE_ID_MATCH_ABSBIT   0x080
8742 +#define INPUT_DEVICE_ID_MATCH_MSCIT    0x100
8743 +#define INPUT_DEVICE_ID_MATCH_LEDBIT   0x200
8744 +#define INPUT_DEVICE_ID_MATCH_SNDBIT   0x400
8745 +#define INPUT_DEVICE_ID_MATCH_FFBIT    0x800
8746 +
8747 +#define INPUT_DEVICE_ID_MATCH_DEVICE\
8748 +       (INPUT_DEVICE_ID_MATCH_BUS | INPUT_DEVICE_ID_MATCH_VENDOR | INPUT_DEVICE_ID_MATCH_PRODUCT)
8749 +#define INPUT_DEVICE_ID_MATCH_DEVICE_AND_VERSION\
8750 +       (INPUT_DEVICE_ID_MATCH_DEVICE | INPUT_DEVICE_ID_MATCH_VERSION)
8751 +
8752 +struct input_device_id {
8753 +
8754 +       unsigned long flags;
8755 +
8756 +       unsigned short idbus;
8757 +       unsigned short idvendor;
8758 +       unsigned short idproduct;
8759 +       unsigned short idversion;
8760 +
8761 +       unsigned long evbit[NBITS(EV_MAX)];
8762 +       unsigned long keybit[NBITS(KEY_MAX)];
8763 +       unsigned long relbit[NBITS(REL_MAX)];
8764 +       unsigned long absbit[NBITS(ABS_MAX)];
8765 +       unsigned long mscbit[NBITS(MSC_MAX)];
8766 +       unsigned long ledbit[NBITS(LED_MAX)];
8767 +       unsigned long sndbit[NBITS(SND_MAX)];
8768 +       unsigned long ffbit[NBITS(FF_MAX)];
8769 +
8770 +       unsigned long driver_info;
8771 +};
8772 +
8773  struct input_handler {
8774  
8775         void *private;
8776  
8777         void (*event)(struct input_handle *handle, unsigned int type, unsigned int code, int value);
8778 -       struct input_handle* (*connect)(struct input_handler *handler, struct input_dev *dev);
8779 +       struct input_handle* (*connect)(struct input_handler *handler, struct input_dev *dev, struct input_device_id *id);
8780         void (*disconnect)(struct input_handle *handle);
8781  
8782         struct file_operations *fops;
8783         int minor;
8784 +       char *name;
8785 +
8786 +       struct input_device_id *id_table;
8787  
8788         struct input_handle *handle;
8789         struct input_handler *next;
8790 @@ -696,6 +795,7 @@
8791         void *private;
8792  
8793         int open;
8794 +       char *name;
8795  
8796         struct input_dev *dev;
8797         struct input_handler *handler;
8798 @@ -713,6 +813,9 @@
8799  int input_open_device(struct input_handle *);
8800  void input_close_device(struct input_handle *);
8801  
8802 +int input_accept_process(struct input_handle *handle, struct file *file);
8803 +int input_flush_device(struct input_handle* handle, struct file* file);
8804 +
8805  devfs_handle_t input_register_minor(char *name, int minor, int minor_base);
8806  void input_unregister_minor(devfs_handle_t handle);
8807  
8808 @@ -721,6 +824,8 @@
8809  #define input_report_key(a,b,c) input_event(a, EV_KEY, b, !!(c))
8810  #define input_report_rel(a,b,c) input_event(a, EV_REL, b, c)
8811  #define input_report_abs(a,b,c) input_event(a, EV_ABS, b, c)
8812 +#define input_report_ff(a,b,c) input_event(a, EV_FF, b, c)
8813 +#define input_report_ff_status(a,b,c)  input_event(a, EV_FF_STATUS, b, c)
8814  
8815  #endif
8816  #endif
8817 diff -u -N -r --exclude=*.rej --exclude=CVS --exclude=.* --exclude=*~ linux-vanilla/include/linux/serio.h linux-modified/include/linux/serio.h
8818 --- linux-vanilla/include/linux/serio.h Fri Nov 29 01:53:15 2002
8819 +++ linux-modified/include/linux/serio.h        Mon Jan 13 22:42:43 2003
8820 @@ -2,38 +2,38 @@
8821  #define _SERIO_H
8822  
8823  /*
8824 - * $Id$
8825 + * $Id$
8826   *
8827 - * Copyright (C) 1999 Vojtech Pavlik
8828 - *
8829 - * Sponsored by SuSE
8830 + * Copyright (C) 1999-2001 Vojtech Pavlik
8831   */
8832  
8833  /*
8834   * This program is free software; you can redistribute it and/or modify
8835   * it under the terms of the GNU General Public License as published by
8836 - * the Free Software Foundation; either version 2 of the License, or 
8837 + * the Free Software Foundation; either version 2 of the License, or
8838   * (at your option) any later version.
8839 - * 
8840 + *
8841   * This program is distributed in the hope that it will be useful,
8842   * but WITHOUT ANY WARRANTY; without even the implied warranty of
8843   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
8844   * GNU General Public License for more details.
8845 - * 
8846 + *
8847   * You should have received a copy of the GNU General Public License
8848   * along with this program; if not, write to the Free Software
8849   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
8850 - * 
8851 + *
8852   * Should you need to contact me, the author, you can do so either by
8853   * e-mail - mail your message to <vojtech@ucw.cz>, or by paper mail:
8854 - * Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic
8855 + * Vojtech Pavlik, Simunkova 1594, Prague 8, 182 00 Czech Republic
8856   */
8857  
8858  /*
8859   * The serial port set type ioctl.
8860   */
8861  
8862 +#include <asm/errno.h>
8863  #include <linux/ioctl.h>
8864 +
8865  #define SPIOCSTYPE     _IOW('q', 0x01, unsigned long)
8866  
8867  struct serio;
8868 @@ -42,23 +42,30 @@
8869  
8870         void *private;
8871         void *driver;
8872 +       char *name;
8873 +       char *phys;
8874 +
8875 +       unsigned short idbus;
8876 +       unsigned short idvendor;
8877 +       unsigned short idproduct;
8878 +       unsigned short idversion;
8879  
8880         unsigned long type;
8881 -       int number;
8882  
8883         int (*write)(struct serio *, unsigned char);
8884         int (*open)(struct serio *);
8885         void (*close)(struct serio *);
8886  
8887         struct serio_dev *dev;
8888 -
8889         struct serio *next;
8890  };
8891  
8892  struct serio_dev {
8893  
8894         void *private;
8895 +       char *name;
8896  
8897 +       void (*write_wakeup)(struct serio *);
8898         void (*interrupt)(struct serio *, unsigned char, unsigned int);
8899         void (*connect)(struct serio *, struct serio_dev *dev);
8900         void (*disconnect)(struct serio *);
8901 @@ -77,7 +84,14 @@
8902  
8903  static __inline__ int serio_write(struct serio *serio, unsigned char data)
8904  {
8905 -       return serio->write(serio, data);
8906 +       return serio->write?serio->write(serio, data):-ENOSYS;
8907 +}
8908 +
8909 +static __inline__ void serio_dev_write_wakeup(struct serio *serio)
8910 +{
8911 +       if (serio->dev && serio->dev->write_wakeup) {
8912 +               serio->dev->write_wakeup(serio);
8913 +       }
8914  }
8915  
8916  #define SERIO_TIMEOUT  1
8917 @@ -109,6 +123,8 @@
8918  #define SERIO_STOWAWAY 0x20
8919  #define SERIO_H3600    0x21
8920  #define SERIO_PS2SER   0x22
8921 +#define SERIO_TWIDKBD  0x23
8922 +#define SERIO_TWIDJOY  0x24
8923  #define SERIO_HIL      0x25
8924  
8925  #define SERIO_ID       0xff00UL
This page took 0.814507 seconds and 3 git commands to generate.