Linux Audio

Check our new training course

Loading...
v3.1
   1/*
   2 * Sony Programmable I/O Control Device driver for VAIO
   3 *
   4 * Copyright (C) 2007 Mattia Dongili <malattia@linux.it>
   5 *
   6 * Copyright (C) 2001-2005 Stelian Pop <stelian@popies.net>
   7 *
   8 * Copyright (C) 2005 Narayanan R S <nars@kadamba.org>
   9 *
  10 * Copyright (C) 2001-2002 AlcĂ´ve <www.alcove.com>
  11 *
  12 * Copyright (C) 2001 Michael Ashley <m.ashley@unsw.edu.au>
  13 *
  14 * Copyright (C) 2001 Junichi Morita <jun1m@mars.dti.ne.jp>
  15 *
  16 * Copyright (C) 2000 Takaya Kinjo <t-kinjo@tc4.so-net.ne.jp>
  17 *
  18 * Copyright (C) 2000 Andrew Tridgell <tridge@valinux.com>
  19 *
  20 * Earlier work by Werner Almesberger, Paul `Rusty' Russell and Paul Mackerras.
  21 *
  22 * This program is free software; you can redistribute it and/or modify
  23 * it under the terms of the GNU General Public License as published by
  24 * the Free Software Foundation; either version 2 of the License, or
  25 * (at your option) any later version.
  26 *
  27 * This program is distributed in the hope that it will be useful,
  28 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  29 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  30 * GNU General Public License for more details.
  31 *
  32 * You should have received a copy of the GNU General Public License
  33 * along with this program; if not, write to the Free Software
  34 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  35 *
  36 */
  37
  38#include <linux/module.h>
  39#include <linux/sched.h>
  40#include <linux/input.h>
  41#include <linux/pci.h>
  42#include <linux/init.h>
  43#include <linux/interrupt.h>
  44#include <linux/miscdevice.h>
  45#include <linux/poll.h>
  46#include <linux/delay.h>
  47#include <linux/wait.h>
  48#include <linux/acpi.h>
  49#include <linux/dmi.h>
  50#include <linux/err.h>
  51#include <linux/kfifo.h>
  52#include <linux/platform_device.h>
  53#include <linux/gfp.h>
  54
  55#include <asm/uaccess.h>
  56#include <asm/io.h>
  57#include <asm/system.h>
  58
  59#include <linux/sonypi.h>
  60
  61#define SONYPI_DRIVER_VERSION	 "1.26"
  62
  63MODULE_AUTHOR("Stelian Pop <stelian@popies.net>");
  64MODULE_DESCRIPTION("Sony Programmable I/O Control Device driver");
  65MODULE_LICENSE("GPL");
  66MODULE_VERSION(SONYPI_DRIVER_VERSION);
  67
  68static int minor = -1;
  69module_param(minor, int, 0);
  70MODULE_PARM_DESC(minor,
  71		 "minor number of the misc device, default is -1 (automatic)");
  72
  73static int verbose;		/* = 0 */
  74module_param(verbose, int, 0644);
  75MODULE_PARM_DESC(verbose, "be verbose, default is 0 (no)");
  76
  77static int fnkeyinit;		/* = 0 */
  78module_param(fnkeyinit, int, 0444);
  79MODULE_PARM_DESC(fnkeyinit,
  80		 "set this if your Fn keys do not generate any event");
  81
  82static int camera;		/* = 0 */
  83module_param(camera, int, 0444);
  84MODULE_PARM_DESC(camera,
  85		 "set this if you have a MotionEye camera (PictureBook series)");
  86
  87static int compat;		/* = 0 */
  88module_param(compat, int, 0444);
  89MODULE_PARM_DESC(compat,
  90		 "set this if you want to enable backward compatibility mode");
  91
  92static unsigned long mask = 0xffffffff;
  93module_param(mask, ulong, 0644);
  94MODULE_PARM_DESC(mask,
  95		 "set this to the mask of event you want to enable (see doc)");
  96
  97static int useinput = 1;
  98module_param(useinput, int, 0444);
  99MODULE_PARM_DESC(useinput,
 100		 "set this if you would like sonypi to feed events to the input subsystem");
 101
 102static int check_ioport = 1;
 103module_param(check_ioport, int, 0444);
 104MODULE_PARM_DESC(check_ioport,
 105		 "set this to 0 if you think the automatic ioport check for sony-laptop is wrong");
 106
 107#define SONYPI_DEVICE_MODEL_TYPE1	1
 108#define SONYPI_DEVICE_MODEL_TYPE2	2
 109#define SONYPI_DEVICE_MODEL_TYPE3	3
 110
 111/* type1 models use those */
 112#define SONYPI_IRQ_PORT			0x8034
 113#define SONYPI_IRQ_SHIFT		22
 114#define SONYPI_TYPE1_BASE		0x50
 115#define SONYPI_G10A			(SONYPI_TYPE1_BASE+0x14)
 116#define SONYPI_TYPE1_REGION_SIZE	0x08
 117#define SONYPI_TYPE1_EVTYPE_OFFSET	0x04
 118
 119/* type2 series specifics */
 120#define SONYPI_SIRQ			0x9b
 121#define SONYPI_SLOB			0x9c
 122#define SONYPI_SHIB			0x9d
 123#define SONYPI_TYPE2_REGION_SIZE	0x20
 124#define SONYPI_TYPE2_EVTYPE_OFFSET	0x12
 125
 126/* type3 series specifics */
 127#define SONYPI_TYPE3_BASE		0x40
 128#define SONYPI_TYPE3_GID2		(SONYPI_TYPE3_BASE+0x48) /* 16 bits */
 129#define SONYPI_TYPE3_MISC		(SONYPI_TYPE3_BASE+0x6d) /* 8 bits  */
 130#define SONYPI_TYPE3_REGION_SIZE	0x20
 131#define SONYPI_TYPE3_EVTYPE_OFFSET	0x12
 132
 133/* battery / brightness addresses */
 134#define SONYPI_BAT_FLAGS	0x81
 135#define SONYPI_LCD_LIGHT	0x96
 136#define SONYPI_BAT1_PCTRM	0xa0
 137#define SONYPI_BAT1_LEFT	0xa2
 138#define SONYPI_BAT1_MAXRT	0xa4
 139#define SONYPI_BAT2_PCTRM	0xa8
 140#define SONYPI_BAT2_LEFT	0xaa
 141#define SONYPI_BAT2_MAXRT	0xac
 142#define SONYPI_BAT1_MAXTK	0xb0
 143#define SONYPI_BAT1_FULL	0xb2
 144#define SONYPI_BAT2_MAXTK	0xb8
 145#define SONYPI_BAT2_FULL	0xba
 146
 147/* FAN0 information (reverse engineered from ACPI tables) */
 148#define SONYPI_FAN0_STATUS	0x93
 149#define SONYPI_TEMP_STATUS	0xC1
 150
 151/* ioports used for brightness and type2 events */
 152#define SONYPI_DATA_IOPORT	0x62
 153#define SONYPI_CST_IOPORT	0x66
 154
 155/* The set of possible ioports */
 156struct sonypi_ioport_list {
 157	u16	port1;
 158	u16	port2;
 159};
 160
 161static struct sonypi_ioport_list sonypi_type1_ioport_list[] = {
 162	{ 0x10c0, 0x10c4 },	/* looks like the default on C1Vx */
 163	{ 0x1080, 0x1084 },
 164	{ 0x1090, 0x1094 },
 165	{ 0x10a0, 0x10a4 },
 166	{ 0x10b0, 0x10b4 },
 167	{ 0x0, 0x0 }
 168};
 169
 170static struct sonypi_ioport_list sonypi_type2_ioport_list[] = {
 171	{ 0x1080, 0x1084 },
 172	{ 0x10a0, 0x10a4 },
 173	{ 0x10c0, 0x10c4 },
 174	{ 0x10e0, 0x10e4 },
 175	{ 0x0, 0x0 }
 176};
 177
 178/* same as in type 2 models */
 179static struct sonypi_ioport_list *sonypi_type3_ioport_list =
 180	sonypi_type2_ioport_list;
 181
 182/* The set of possible interrupts */
 183struct sonypi_irq_list {
 184	u16	irq;
 185	u16	bits;
 186};
 187
 188static struct sonypi_irq_list sonypi_type1_irq_list[] = {
 189	{ 11, 0x2 },	/* IRQ 11, GO22=0,GO23=1 in AML */
 190	{ 10, 0x1 },	/* IRQ 10, GO22=1,GO23=0 in AML */
 191	{  5, 0x0 },	/* IRQ  5, GO22=0,GO23=0 in AML */
 192	{  0, 0x3 }	/* no IRQ, GO22=1,GO23=1 in AML */
 193};
 194
 195static struct sonypi_irq_list sonypi_type2_irq_list[] = {
 196	{ 11, 0x80 },	/* IRQ 11, 0x80 in SIRQ in AML */
 197	{ 10, 0x40 },	/* IRQ 10, 0x40 in SIRQ in AML */
 198	{  9, 0x20 },	/* IRQ  9, 0x20 in SIRQ in AML */
 199	{  6, 0x10 },	/* IRQ  6, 0x10 in SIRQ in AML */
 200	{  0, 0x00 }	/* no IRQ, 0x00 in SIRQ in AML */
 201};
 202
 203/* same as in type2 models */
 204static struct sonypi_irq_list *sonypi_type3_irq_list = sonypi_type2_irq_list;
 205
 206#define SONYPI_CAMERA_BRIGHTNESS		0
 207#define SONYPI_CAMERA_CONTRAST			1
 208#define SONYPI_CAMERA_HUE			2
 209#define SONYPI_CAMERA_COLOR			3
 210#define SONYPI_CAMERA_SHARPNESS			4
 211
 212#define SONYPI_CAMERA_PICTURE			5
 213#define SONYPI_CAMERA_EXPOSURE_MASK		0xC
 214#define SONYPI_CAMERA_WHITE_BALANCE_MASK	0x3
 215#define SONYPI_CAMERA_PICTURE_MODE_MASK		0x30
 216#define SONYPI_CAMERA_MUTE_MASK			0x40
 217
 218/* the rest don't need a loop until not 0xff */
 219#define SONYPI_CAMERA_AGC			6
 220#define SONYPI_CAMERA_AGC_MASK			0x30
 221#define SONYPI_CAMERA_SHUTTER_MASK 		0x7
 222
 223#define SONYPI_CAMERA_SHUTDOWN_REQUEST		7
 224#define SONYPI_CAMERA_CONTROL			0x10
 225
 226#define SONYPI_CAMERA_STATUS 			7
 227#define SONYPI_CAMERA_STATUS_READY 		0x2
 228#define SONYPI_CAMERA_STATUS_POSITION		0x4
 229
 230#define SONYPI_DIRECTION_BACKWARDS 		0x4
 231
 232#define SONYPI_CAMERA_REVISION 			8
 233#define SONYPI_CAMERA_ROMVERSION 		9
 234
 235/* Event masks */
 236#define SONYPI_JOGGER_MASK			0x00000001
 237#define SONYPI_CAPTURE_MASK			0x00000002
 238#define SONYPI_FNKEY_MASK			0x00000004
 239#define SONYPI_BLUETOOTH_MASK			0x00000008
 240#define SONYPI_PKEY_MASK			0x00000010
 241#define SONYPI_BACK_MASK			0x00000020
 242#define SONYPI_HELP_MASK			0x00000040
 243#define SONYPI_LID_MASK				0x00000080
 244#define SONYPI_ZOOM_MASK			0x00000100
 245#define SONYPI_THUMBPHRASE_MASK			0x00000200
 246#define SONYPI_MEYE_MASK			0x00000400
 247#define SONYPI_MEMORYSTICK_MASK			0x00000800
 248#define SONYPI_BATTERY_MASK			0x00001000
 249#define SONYPI_WIRELESS_MASK			0x00002000
 250
 251struct sonypi_event {
 252	u8	data;
 253	u8	event;
 254};
 255
 256/* The set of possible button release events */
 257static struct sonypi_event sonypi_releaseev[] = {
 258	{ 0x00, SONYPI_EVENT_ANYBUTTON_RELEASED },
 259	{ 0, 0 }
 260};
 261
 262/* The set of possible jogger events  */
 263static struct sonypi_event sonypi_joggerev[] = {
 264	{ 0x1f, SONYPI_EVENT_JOGDIAL_UP },
 265	{ 0x01, SONYPI_EVENT_JOGDIAL_DOWN },
 266	{ 0x5f, SONYPI_EVENT_JOGDIAL_UP_PRESSED },
 267	{ 0x41, SONYPI_EVENT_JOGDIAL_DOWN_PRESSED },
 268	{ 0x1e, SONYPI_EVENT_JOGDIAL_FAST_UP },
 269	{ 0x02, SONYPI_EVENT_JOGDIAL_FAST_DOWN },
 270	{ 0x5e, SONYPI_EVENT_JOGDIAL_FAST_UP_PRESSED },
 271	{ 0x42, SONYPI_EVENT_JOGDIAL_FAST_DOWN_PRESSED },
 272	{ 0x1d, SONYPI_EVENT_JOGDIAL_VFAST_UP },
 273	{ 0x03, SONYPI_EVENT_JOGDIAL_VFAST_DOWN },
 274	{ 0x5d, SONYPI_EVENT_JOGDIAL_VFAST_UP_PRESSED },
 275	{ 0x43, SONYPI_EVENT_JOGDIAL_VFAST_DOWN_PRESSED },
 276	{ 0x40, SONYPI_EVENT_JOGDIAL_PRESSED },
 277	{ 0, 0 }
 278};
 279
 280/* The set of possible capture button events */
 281static struct sonypi_event sonypi_captureev[] = {
 282	{ 0x05, SONYPI_EVENT_CAPTURE_PARTIALPRESSED },
 283	{ 0x07, SONYPI_EVENT_CAPTURE_PRESSED },
 284	{ 0x01, SONYPI_EVENT_CAPTURE_PARTIALRELEASED },
 285	{ 0, 0 }
 286};
 287
 288/* The set of possible fnkeys events */
 289static struct sonypi_event sonypi_fnkeyev[] = {
 290	{ 0x10, SONYPI_EVENT_FNKEY_ESC },
 291	{ 0x11, SONYPI_EVENT_FNKEY_F1 },
 292	{ 0x12, SONYPI_EVENT_FNKEY_F2 },
 293	{ 0x13, SONYPI_EVENT_FNKEY_F3 },
 294	{ 0x14, SONYPI_EVENT_FNKEY_F4 },
 295	{ 0x15, SONYPI_EVENT_FNKEY_F5 },
 296	{ 0x16, SONYPI_EVENT_FNKEY_F6 },
 297	{ 0x17, SONYPI_EVENT_FNKEY_F7 },
 298	{ 0x18, SONYPI_EVENT_FNKEY_F8 },
 299	{ 0x19, SONYPI_EVENT_FNKEY_F9 },
 300	{ 0x1a, SONYPI_EVENT_FNKEY_F10 },
 301	{ 0x1b, SONYPI_EVENT_FNKEY_F11 },
 302	{ 0x1c, SONYPI_EVENT_FNKEY_F12 },
 303	{ 0x1f, SONYPI_EVENT_FNKEY_RELEASED },
 304	{ 0x21, SONYPI_EVENT_FNKEY_1 },
 305	{ 0x22, SONYPI_EVENT_FNKEY_2 },
 306	{ 0x31, SONYPI_EVENT_FNKEY_D },
 307	{ 0x32, SONYPI_EVENT_FNKEY_E },
 308	{ 0x33, SONYPI_EVENT_FNKEY_F },
 309	{ 0x34, SONYPI_EVENT_FNKEY_S },
 310	{ 0x35, SONYPI_EVENT_FNKEY_B },
 311	{ 0x36, SONYPI_EVENT_FNKEY_ONLY },
 312	{ 0, 0 }
 313};
 314
 315/* The set of possible program key events */
 316static struct sonypi_event sonypi_pkeyev[] = {
 317	{ 0x01, SONYPI_EVENT_PKEY_P1 },
 318	{ 0x02, SONYPI_EVENT_PKEY_P2 },
 319	{ 0x04, SONYPI_EVENT_PKEY_P3 },
 320	{ 0x5c, SONYPI_EVENT_PKEY_P1 },
 321	{ 0, 0 }
 322};
 323
 324/* The set of possible bluetooth events */
 325static struct sonypi_event sonypi_blueev[] = {
 326	{ 0x55, SONYPI_EVENT_BLUETOOTH_PRESSED },
 327	{ 0x59, SONYPI_EVENT_BLUETOOTH_ON },
 328	{ 0x5a, SONYPI_EVENT_BLUETOOTH_OFF },
 329	{ 0, 0 }
 330};
 331
 332/* The set of possible wireless events */
 333static struct sonypi_event sonypi_wlessev[] = {
 334	{ 0x59, SONYPI_EVENT_WIRELESS_ON },
 335	{ 0x5a, SONYPI_EVENT_WIRELESS_OFF },
 336	{ 0, 0 }
 337};
 338
 339/* The set of possible back button events */
 340static struct sonypi_event sonypi_backev[] = {
 341	{ 0x20, SONYPI_EVENT_BACK_PRESSED },
 342	{ 0, 0 }
 343};
 344
 345/* The set of possible help button events */
 346static struct sonypi_event sonypi_helpev[] = {
 347	{ 0x3b, SONYPI_EVENT_HELP_PRESSED },
 348	{ 0, 0 }
 349};
 350
 351
 352/* The set of possible lid events */
 353static struct sonypi_event sonypi_lidev[] = {
 354	{ 0x51, SONYPI_EVENT_LID_CLOSED },
 355	{ 0x50, SONYPI_EVENT_LID_OPENED },
 356	{ 0, 0 }
 357};
 358
 359/* The set of possible zoom events */
 360static struct sonypi_event sonypi_zoomev[] = {
 361	{ 0x39, SONYPI_EVENT_ZOOM_PRESSED },
 362	{ 0, 0 }
 363};
 364
 365/* The set of possible thumbphrase events */
 366static struct sonypi_event sonypi_thumbphraseev[] = {
 367	{ 0x3a, SONYPI_EVENT_THUMBPHRASE_PRESSED },
 368	{ 0, 0 }
 369};
 370
 371/* The set of possible motioneye camera events */
 372static struct sonypi_event sonypi_meyeev[] = {
 373	{ 0x00, SONYPI_EVENT_MEYE_FACE },
 374	{ 0x01, SONYPI_EVENT_MEYE_OPPOSITE },
 375	{ 0, 0 }
 376};
 377
 378/* The set of possible memorystick events */
 379static struct sonypi_event sonypi_memorystickev[] = {
 380	{ 0x53, SONYPI_EVENT_MEMORYSTICK_INSERT },
 381	{ 0x54, SONYPI_EVENT_MEMORYSTICK_EJECT },
 382	{ 0, 0 }
 383};
 384
 385/* The set of possible battery events */
 386static struct sonypi_event sonypi_batteryev[] = {
 387	{ 0x20, SONYPI_EVENT_BATTERY_INSERT },
 388	{ 0x30, SONYPI_EVENT_BATTERY_REMOVE },
 389	{ 0, 0 }
 390};
 391
 392static struct sonypi_eventtypes {
 393	int			model;
 394	u8			data;
 395	unsigned long		mask;
 396	struct sonypi_event *	events;
 397} sonypi_eventtypes[] = {
 398	{ SONYPI_DEVICE_MODEL_TYPE1, 0, 0xffffffff, sonypi_releaseev },
 399	{ SONYPI_DEVICE_MODEL_TYPE1, 0x70, SONYPI_MEYE_MASK, sonypi_meyeev },
 400	{ SONYPI_DEVICE_MODEL_TYPE1, 0x30, SONYPI_LID_MASK, sonypi_lidev },
 401	{ SONYPI_DEVICE_MODEL_TYPE1, 0x60, SONYPI_CAPTURE_MASK, sonypi_captureev },
 402	{ SONYPI_DEVICE_MODEL_TYPE1, 0x10, SONYPI_JOGGER_MASK, sonypi_joggerev },
 403	{ SONYPI_DEVICE_MODEL_TYPE1, 0x20, SONYPI_FNKEY_MASK, sonypi_fnkeyev },
 404	{ SONYPI_DEVICE_MODEL_TYPE1, 0x30, SONYPI_BLUETOOTH_MASK, sonypi_blueev },
 405	{ SONYPI_DEVICE_MODEL_TYPE1, 0x40, SONYPI_PKEY_MASK, sonypi_pkeyev },
 406	{ SONYPI_DEVICE_MODEL_TYPE1, 0x30, SONYPI_MEMORYSTICK_MASK, sonypi_memorystickev },
 407	{ SONYPI_DEVICE_MODEL_TYPE1, 0x40, SONYPI_BATTERY_MASK, sonypi_batteryev },
 408
 409	{ SONYPI_DEVICE_MODEL_TYPE2, 0, 0xffffffff, sonypi_releaseev },
 410	{ SONYPI_DEVICE_MODEL_TYPE2, 0x38, SONYPI_LID_MASK, sonypi_lidev },
 411	{ SONYPI_DEVICE_MODEL_TYPE2, 0x11, SONYPI_JOGGER_MASK, sonypi_joggerev },
 412	{ SONYPI_DEVICE_MODEL_TYPE2, 0x61, SONYPI_CAPTURE_MASK, sonypi_captureev },
 413	{ SONYPI_DEVICE_MODEL_TYPE2, 0x21, SONYPI_FNKEY_MASK, sonypi_fnkeyev },
 414	{ SONYPI_DEVICE_MODEL_TYPE2, 0x31, SONYPI_BLUETOOTH_MASK, sonypi_blueev },
 415	{ SONYPI_DEVICE_MODEL_TYPE2, 0x08, SONYPI_PKEY_MASK, sonypi_pkeyev },
 416	{ SONYPI_DEVICE_MODEL_TYPE2, 0x11, SONYPI_BACK_MASK, sonypi_backev },
 417	{ SONYPI_DEVICE_MODEL_TYPE2, 0x21, SONYPI_HELP_MASK, sonypi_helpev },
 418	{ SONYPI_DEVICE_MODEL_TYPE2, 0x21, SONYPI_ZOOM_MASK, sonypi_zoomev },
 419	{ SONYPI_DEVICE_MODEL_TYPE2, 0x20, SONYPI_THUMBPHRASE_MASK, sonypi_thumbphraseev },
 420	{ SONYPI_DEVICE_MODEL_TYPE2, 0x31, SONYPI_MEMORYSTICK_MASK, sonypi_memorystickev },
 421	{ SONYPI_DEVICE_MODEL_TYPE2, 0x41, SONYPI_BATTERY_MASK, sonypi_batteryev },
 422	{ SONYPI_DEVICE_MODEL_TYPE2, 0x31, SONYPI_PKEY_MASK, sonypi_pkeyev },
 423
 424	{ SONYPI_DEVICE_MODEL_TYPE3, 0, 0xffffffff, sonypi_releaseev },
 425	{ SONYPI_DEVICE_MODEL_TYPE3, 0x21, SONYPI_FNKEY_MASK, sonypi_fnkeyev },
 426	{ SONYPI_DEVICE_MODEL_TYPE3, 0x31, SONYPI_WIRELESS_MASK, sonypi_wlessev },
 427	{ SONYPI_DEVICE_MODEL_TYPE3, 0x31, SONYPI_MEMORYSTICK_MASK, sonypi_memorystickev },
 428	{ SONYPI_DEVICE_MODEL_TYPE3, 0x41, SONYPI_BATTERY_MASK, sonypi_batteryev },
 429	{ SONYPI_DEVICE_MODEL_TYPE3, 0x31, SONYPI_PKEY_MASK, sonypi_pkeyev },
 430	{ 0 }
 431};
 432
 433#define SONYPI_BUF_SIZE	128
 434
 435/* Correspondance table between sonypi events and input layer events */
 436static struct {
 437	int sonypiev;
 438	int inputev;
 439} sonypi_inputkeys[] = {
 440	{ SONYPI_EVENT_CAPTURE_PRESSED,	 	KEY_CAMERA },
 441	{ SONYPI_EVENT_FNKEY_ONLY, 		KEY_FN },
 442	{ SONYPI_EVENT_FNKEY_ESC, 		KEY_FN_ESC },
 443	{ SONYPI_EVENT_FNKEY_F1, 		KEY_FN_F1 },
 444	{ SONYPI_EVENT_FNKEY_F2, 		KEY_FN_F2 },
 445	{ SONYPI_EVENT_FNKEY_F3, 		KEY_FN_F3 },
 446	{ SONYPI_EVENT_FNKEY_F4, 		KEY_FN_F4 },
 447	{ SONYPI_EVENT_FNKEY_F5, 		KEY_FN_F5 },
 448	{ SONYPI_EVENT_FNKEY_F6, 		KEY_FN_F6 },
 449	{ SONYPI_EVENT_FNKEY_F7, 		KEY_FN_F7 },
 450	{ SONYPI_EVENT_FNKEY_F8, 		KEY_FN_F8 },
 451	{ SONYPI_EVENT_FNKEY_F9,		KEY_FN_F9 },
 452	{ SONYPI_EVENT_FNKEY_F10,		KEY_FN_F10 },
 453	{ SONYPI_EVENT_FNKEY_F11, 		KEY_FN_F11 },
 454	{ SONYPI_EVENT_FNKEY_F12,		KEY_FN_F12 },
 455	{ SONYPI_EVENT_FNKEY_1, 		KEY_FN_1 },
 456	{ SONYPI_EVENT_FNKEY_2, 		KEY_FN_2 },
 457	{ SONYPI_EVENT_FNKEY_D,			KEY_FN_D },
 458	{ SONYPI_EVENT_FNKEY_E,			KEY_FN_E },
 459	{ SONYPI_EVENT_FNKEY_F,			KEY_FN_F },
 460	{ SONYPI_EVENT_FNKEY_S,			KEY_FN_S },
 461	{ SONYPI_EVENT_FNKEY_B,			KEY_FN_B },
 462	{ SONYPI_EVENT_BLUETOOTH_PRESSED, 	KEY_BLUE },
 463	{ SONYPI_EVENT_BLUETOOTH_ON, 		KEY_BLUE },
 464	{ SONYPI_EVENT_PKEY_P1, 		KEY_PROG1 },
 465	{ SONYPI_EVENT_PKEY_P2, 		KEY_PROG2 },
 466	{ SONYPI_EVENT_PKEY_P3, 		KEY_PROG3 },
 467	{ SONYPI_EVENT_BACK_PRESSED, 		KEY_BACK },
 468	{ SONYPI_EVENT_HELP_PRESSED, 		KEY_HELP },
 469	{ SONYPI_EVENT_ZOOM_PRESSED, 		KEY_ZOOM },
 470	{ SONYPI_EVENT_THUMBPHRASE_PRESSED, 	BTN_THUMB },
 471	{ 0, 0 },
 472};
 473
 474struct sonypi_keypress {
 475	struct input_dev *dev;
 476	int key;
 477};
 478
 479static struct sonypi_device {
 480	struct pci_dev *dev;
 481	u16 irq;
 482	u16 bits;
 483	u16 ioport1;
 484	u16 ioport2;
 485	u16 region_size;
 486	u16 evtype_offset;
 487	int camera_power;
 488	int bluetooth_power;
 489	struct mutex lock;
 490	struct kfifo fifo;
 491	spinlock_t fifo_lock;
 492	wait_queue_head_t fifo_proc_list;
 493	struct fasync_struct *fifo_async;
 494	int open_count;
 495	int model;
 496	struct input_dev *input_jog_dev;
 497	struct input_dev *input_key_dev;
 498	struct work_struct input_work;
 499	struct kfifo input_fifo;
 500	spinlock_t input_fifo_lock;
 501} sonypi_device;
 502
 503#define ITERATIONS_LONG		10000
 504#define ITERATIONS_SHORT	10
 505
 506#define wait_on_command(quiet, command, iterations) { \
 507	unsigned int n = iterations; \
 508	while (--n && (command)) \
 509		udelay(1); \
 510	if (!n && (verbose || !quiet)) \
 511		printk(KERN_WARNING "sonypi command failed at %s : %s (line %d)\n", __FILE__, __func__, __LINE__); \
 512}
 513
 514#ifdef CONFIG_ACPI
 515#define SONYPI_ACPI_ACTIVE (!acpi_disabled)
 516#else
 517#define SONYPI_ACPI_ACTIVE 0
 518#endif				/* CONFIG_ACPI */
 519
 520#ifdef CONFIG_ACPI
 521static struct acpi_device *sonypi_acpi_device;
 522static int acpi_driver_registered;
 523#endif
 524
 525static int sonypi_ec_write(u8 addr, u8 value)
 526{
 527#ifdef CONFIG_ACPI
 528	if (SONYPI_ACPI_ACTIVE)
 529		return ec_write(addr, value);
 530#endif
 531	wait_on_command(1, inb_p(SONYPI_CST_IOPORT) & 3, ITERATIONS_LONG);
 532	outb_p(0x81, SONYPI_CST_IOPORT);
 533	wait_on_command(0, inb_p(SONYPI_CST_IOPORT) & 2, ITERATIONS_LONG);
 534	outb_p(addr, SONYPI_DATA_IOPORT);
 535	wait_on_command(0, inb_p(SONYPI_CST_IOPORT) & 2, ITERATIONS_LONG);
 536	outb_p(value, SONYPI_DATA_IOPORT);
 537	wait_on_command(0, inb_p(SONYPI_CST_IOPORT) & 2, ITERATIONS_LONG);
 538	return 0;
 539}
 540
 541static int sonypi_ec_read(u8 addr, u8 *value)
 542{
 543#ifdef CONFIG_ACPI
 544	if (SONYPI_ACPI_ACTIVE)
 545		return ec_read(addr, value);
 546#endif
 547	wait_on_command(1, inb_p(SONYPI_CST_IOPORT) & 3, ITERATIONS_LONG);
 548	outb_p(0x80, SONYPI_CST_IOPORT);
 549	wait_on_command(0, inb_p(SONYPI_CST_IOPORT) & 2, ITERATIONS_LONG);
 550	outb_p(addr, SONYPI_DATA_IOPORT);
 551	wait_on_command(0, inb_p(SONYPI_CST_IOPORT) & 2, ITERATIONS_LONG);
 552	*value = inb_p(SONYPI_DATA_IOPORT);
 553	return 0;
 554}
 555
 556static int ec_read16(u8 addr, u16 *value)
 557{
 558	u8 val_lb, val_hb;
 559	if (sonypi_ec_read(addr, &val_lb))
 560		return -1;
 561	if (sonypi_ec_read(addr + 1, &val_hb))
 562		return -1;
 563	*value = val_lb | (val_hb << 8);
 564	return 0;
 565}
 566
 567/* Initializes the device - this comes from the AML code in the ACPI bios */
 568static void sonypi_type1_srs(void)
 569{
 570	u32 v;
 571
 572	pci_read_config_dword(sonypi_device.dev, SONYPI_G10A, &v);
 573	v = (v & 0xFFFF0000) | ((u32) sonypi_device.ioport1);
 574	pci_write_config_dword(sonypi_device.dev, SONYPI_G10A, v);
 575
 576	pci_read_config_dword(sonypi_device.dev, SONYPI_G10A, &v);
 577	v = (v & 0xFFF0FFFF) |
 578	    (((u32) sonypi_device.ioport1 ^ sonypi_device.ioport2) << 16);
 579	pci_write_config_dword(sonypi_device.dev, SONYPI_G10A, v);
 580
 581	v = inl(SONYPI_IRQ_PORT);
 582	v &= ~(((u32) 0x3) << SONYPI_IRQ_SHIFT);
 583	v |= (((u32) sonypi_device.bits) << SONYPI_IRQ_SHIFT);
 584	outl(v, SONYPI_IRQ_PORT);
 585
 586	pci_read_config_dword(sonypi_device.dev, SONYPI_G10A, &v);
 587	v = (v & 0xFF1FFFFF) | 0x00C00000;
 588	pci_write_config_dword(sonypi_device.dev, SONYPI_G10A, v);
 589}
 590
 591static void sonypi_type2_srs(void)
 592{
 593	if (sonypi_ec_write(SONYPI_SHIB, (sonypi_device.ioport1 & 0xFF00) >> 8))
 594		printk(KERN_WARNING "ec_write failed\n");
 595	if (sonypi_ec_write(SONYPI_SLOB, sonypi_device.ioport1 & 0x00FF))
 596		printk(KERN_WARNING "ec_write failed\n");
 597	if (sonypi_ec_write(SONYPI_SIRQ, sonypi_device.bits))
 598		printk(KERN_WARNING "ec_write failed\n");
 599	udelay(10);
 600}
 601
 602static void sonypi_type3_srs(void)
 603{
 604	u16 v16;
 605	u8  v8;
 606
 607	/* This model type uses the same initialiazation of
 608	 * the embedded controller as the type2 models. */
 609	sonypi_type2_srs();
 610
 611	/* Initialization of PCI config space of the LPC interface bridge. */
 612	v16 = (sonypi_device.ioport1 & 0xFFF0) | 0x01;
 613	pci_write_config_word(sonypi_device.dev, SONYPI_TYPE3_GID2, v16);
 614	pci_read_config_byte(sonypi_device.dev, SONYPI_TYPE3_MISC, &v8);
 615	v8 = (v8 & 0xCF) | 0x10;
 616	pci_write_config_byte(sonypi_device.dev, SONYPI_TYPE3_MISC, v8);
 617}
 618
 619/* Disables the device - this comes from the AML code in the ACPI bios */
 620static void sonypi_type1_dis(void)
 621{
 622	u32 v;
 623
 624	pci_read_config_dword(sonypi_device.dev, SONYPI_G10A, &v);
 625	v = v & 0xFF3FFFFF;
 626	pci_write_config_dword(sonypi_device.dev, SONYPI_G10A, v);
 627
 628	v = inl(SONYPI_IRQ_PORT);
 629	v |= (0x3 << SONYPI_IRQ_SHIFT);
 630	outl(v, SONYPI_IRQ_PORT);
 631}
 632
 633static void sonypi_type2_dis(void)
 634{
 635	if (sonypi_ec_write(SONYPI_SHIB, 0))
 636		printk(KERN_WARNING "ec_write failed\n");
 637	if (sonypi_ec_write(SONYPI_SLOB, 0))
 638		printk(KERN_WARNING "ec_write failed\n");
 639	if (sonypi_ec_write(SONYPI_SIRQ, 0))
 640		printk(KERN_WARNING "ec_write failed\n");
 641}
 642
 643static void sonypi_type3_dis(void)
 644{
 645	sonypi_type2_dis();
 646	udelay(10);
 647	pci_write_config_word(sonypi_device.dev, SONYPI_TYPE3_GID2, 0);
 648}
 649
 650static u8 sonypi_call1(u8 dev)
 651{
 652	u8 v1, v2;
 653
 654	wait_on_command(0, inb_p(sonypi_device.ioport2) & 2, ITERATIONS_LONG);
 655	outb(dev, sonypi_device.ioport2);
 656	v1 = inb_p(sonypi_device.ioport2);
 657	v2 = inb_p(sonypi_device.ioport1);
 658	return v2;
 659}
 660
 661static u8 sonypi_call2(u8 dev, u8 fn)
 662{
 663	u8 v1;
 664
 665	wait_on_command(0, inb_p(sonypi_device.ioport2) & 2, ITERATIONS_LONG);
 666	outb(dev, sonypi_device.ioport2);
 667	wait_on_command(0, inb_p(sonypi_device.ioport2) & 2, ITERATIONS_LONG);
 668	outb(fn, sonypi_device.ioport1);
 669	v1 = inb_p(sonypi_device.ioport1);
 670	return v1;
 671}
 672
 673static u8 sonypi_call3(u8 dev, u8 fn, u8 v)
 674{
 675	u8 v1;
 676
 677	wait_on_command(0, inb_p(sonypi_device.ioport2) & 2, ITERATIONS_LONG);
 678	outb(dev, sonypi_device.ioport2);
 679	wait_on_command(0, inb_p(sonypi_device.ioport2) & 2, ITERATIONS_LONG);
 680	outb(fn, sonypi_device.ioport1);
 681	wait_on_command(0, inb_p(sonypi_device.ioport2) & 2, ITERATIONS_LONG);
 682	outb(v, sonypi_device.ioport1);
 683	v1 = inb_p(sonypi_device.ioport1);
 684	return v1;
 685}
 686
 687#if 0
 688/* Get brightness, hue etc. Unreliable... */
 689static u8 sonypi_read(u8 fn)
 690{
 691	u8 v1, v2;
 692	int n = 100;
 693
 694	while (n--) {
 695		v1 = sonypi_call2(0x8f, fn);
 696		v2 = sonypi_call2(0x8f, fn);
 697		if (v1 == v2 && v1 != 0xff)
 698			return v1;
 699	}
 700	return 0xff;
 701}
 702#endif
 703
 704/* Set brightness, hue etc */
 705static void sonypi_set(u8 fn, u8 v)
 706{
 707	wait_on_command(0, sonypi_call3(0x90, fn, v), ITERATIONS_SHORT);
 708}
 709
 710/* Tests if the camera is ready */
 711static int sonypi_camera_ready(void)
 712{
 713	u8 v;
 714
 715	v = sonypi_call2(0x8f, SONYPI_CAMERA_STATUS);
 716	return (v != 0xff && (v & SONYPI_CAMERA_STATUS_READY));
 717}
 718
 719/* Turns the camera off */
 720static void sonypi_camera_off(void)
 721{
 722	sonypi_set(SONYPI_CAMERA_PICTURE, SONYPI_CAMERA_MUTE_MASK);
 723
 724	if (!sonypi_device.camera_power)
 725		return;
 726
 727	sonypi_call2(0x91, 0);
 728	sonypi_device.camera_power = 0;
 729}
 730
 731/* Turns the camera on */
 732static void sonypi_camera_on(void)
 733{
 734	int i, j;
 735
 736	if (sonypi_device.camera_power)
 737		return;
 738
 739	for (j = 5; j > 0; j--) {
 740
 741		while (sonypi_call2(0x91, 0x1))
 742			msleep(10);
 743		sonypi_call1(0x93);
 744
 745		for (i = 400; i > 0; i--) {
 746			if (sonypi_camera_ready())
 747				break;
 748			msleep(10);
 749		}
 750		if (i)
 751			break;
 752	}
 753
 754	if (j == 0) {
 755		printk(KERN_WARNING "sonypi: failed to power on camera\n");
 756		return;
 757	}
 758
 759	sonypi_set(0x10, 0x5a);
 760	sonypi_device.camera_power = 1;
 761}
 762
 763/* sets the bluetooth subsystem power state */
 764static void sonypi_setbluetoothpower(u8 state)
 765{
 766	state = !!state;
 767
 768	if (sonypi_device.bluetooth_power == state)
 769		return;
 770
 771	sonypi_call2(0x96, state);
 772	sonypi_call1(0x82);
 773	sonypi_device.bluetooth_power = state;
 774}
 775
 776static void input_keyrelease(struct work_struct *work)
 777{
 778	struct sonypi_keypress kp;
 779
 780	while (kfifo_out_locked(&sonypi_device.input_fifo, (unsigned char *)&kp,
 781			 sizeof(kp), &sonypi_device.input_fifo_lock)
 782			== sizeof(kp)) {
 783		msleep(10);
 784		input_report_key(kp.dev, kp.key, 0);
 785		input_sync(kp.dev);
 786	}
 787}
 788
 789static void sonypi_report_input_event(u8 event)
 790{
 791	struct input_dev *jog_dev = sonypi_device.input_jog_dev;
 792	struct input_dev *key_dev = sonypi_device.input_key_dev;
 793	struct sonypi_keypress kp = { NULL };
 794	int i;
 795
 796	switch (event) {
 797	case SONYPI_EVENT_JOGDIAL_UP:
 798	case SONYPI_EVENT_JOGDIAL_UP_PRESSED:
 799		input_report_rel(jog_dev, REL_WHEEL, 1);
 800		input_sync(jog_dev);
 801		break;
 802
 803	case SONYPI_EVENT_JOGDIAL_DOWN:
 804	case SONYPI_EVENT_JOGDIAL_DOWN_PRESSED:
 805		input_report_rel(jog_dev, REL_WHEEL, -1);
 806		input_sync(jog_dev);
 807		break;
 808
 809	case SONYPI_EVENT_JOGDIAL_PRESSED:
 810		kp.key = BTN_MIDDLE;
 811		kp.dev = jog_dev;
 812		break;
 813
 814	case SONYPI_EVENT_FNKEY_RELEASED:
 815		/* Nothing, not all VAIOs generate this event */
 816		break;
 817
 818	default:
 819		for (i = 0; sonypi_inputkeys[i].sonypiev; i++)
 820			if (event == sonypi_inputkeys[i].sonypiev) {
 821				kp.dev = key_dev;
 822				kp.key = sonypi_inputkeys[i].inputev;
 823				break;
 824			}
 825		break;
 826	}
 827
 828	if (kp.dev) {
 829		input_report_key(kp.dev, kp.key, 1);
 830		input_sync(kp.dev);
 831		kfifo_in_locked(&sonypi_device.input_fifo,
 832			(unsigned char *)&kp, sizeof(kp),
 833			&sonypi_device.input_fifo_lock);
 834		schedule_work(&sonypi_device.input_work);
 835	}
 836}
 837
 838/* Interrupt handler: some event is available */
 839static irqreturn_t sonypi_irq(int irq, void *dev_id)
 840{
 841	u8 v1, v2, event = 0;
 842	int i, j;
 843
 844	v1 = inb_p(sonypi_device.ioport1);
 845	v2 = inb_p(sonypi_device.ioport1 + sonypi_device.evtype_offset);
 846
 847	for (i = 0; sonypi_eventtypes[i].model; i++) {
 848		if (sonypi_device.model != sonypi_eventtypes[i].model)
 849			continue;
 850		if ((v2 & sonypi_eventtypes[i].data) !=
 851		    sonypi_eventtypes[i].data)
 852			continue;
 853		if (!(mask & sonypi_eventtypes[i].mask))
 854			continue;
 855		for (j = 0; sonypi_eventtypes[i].events[j].event; j++) {
 856			if (v1 == sonypi_eventtypes[i].events[j].data) {
 857				event = sonypi_eventtypes[i].events[j].event;
 858				goto found;
 859			}
 860		}
 861	}
 862
 863	if (verbose)
 864		printk(KERN_WARNING
 865		       "sonypi: unknown event port1=0x%02x,port2=0x%02x\n",
 866		       v1, v2);
 867	/* We need to return IRQ_HANDLED here because there *are*
 868	 * events belonging to the sonypi device we don't know about,
 869	 * but we still don't want those to pollute the logs... */
 870	return IRQ_HANDLED;
 871
 872found:
 873	if (verbose > 1)
 874		printk(KERN_INFO
 875		       "sonypi: event port1=0x%02x,port2=0x%02x\n", v1, v2);
 876
 877	if (useinput)
 878		sonypi_report_input_event(event);
 879
 880#ifdef CONFIG_ACPI
 881	if (sonypi_acpi_device)
 882		acpi_bus_generate_proc_event(sonypi_acpi_device, 1, event);
 883#endif
 884
 885	kfifo_in_locked(&sonypi_device.fifo, (unsigned char *)&event,
 886			sizeof(event), &sonypi_device.fifo_lock);
 887	kill_fasync(&sonypi_device.fifo_async, SIGIO, POLL_IN);
 888	wake_up_interruptible(&sonypi_device.fifo_proc_list);
 889
 890	return IRQ_HANDLED;
 891}
 892
 893static int sonypi_misc_fasync(int fd, struct file *filp, int on)
 894{
 895	return fasync_helper(fd, filp, on, &sonypi_device.fifo_async);
 896}
 897
 898static int sonypi_misc_release(struct inode *inode, struct file *file)
 899{
 900	mutex_lock(&sonypi_device.lock);
 901	sonypi_device.open_count--;
 902	mutex_unlock(&sonypi_device.lock);
 903	return 0;
 904}
 905
 906static int sonypi_misc_open(struct inode *inode, struct file *file)
 907{
 908	mutex_lock(&sonypi_device.lock);
 909	/* Flush input queue on first open */
 910	if (!sonypi_device.open_count)
 911		kfifo_reset(&sonypi_device.fifo);
 912	sonypi_device.open_count++;
 913	mutex_unlock(&sonypi_device.lock);
 914
 915	return 0;
 916}
 917
 918static ssize_t sonypi_misc_read(struct file *file, char __user *buf,
 919				size_t count, loff_t *pos)
 920{
 921	ssize_t ret;
 922	unsigned char c;
 923
 924	if ((kfifo_len(&sonypi_device.fifo) == 0) &&
 925	    (file->f_flags & O_NONBLOCK))
 926		return -EAGAIN;
 927
 928	ret = wait_event_interruptible(sonypi_device.fifo_proc_list,
 929				       kfifo_len(&sonypi_device.fifo) != 0);
 930	if (ret)
 931		return ret;
 932
 933	while (ret < count &&
 934	       (kfifo_out_locked(&sonypi_device.fifo, &c, sizeof(c),
 935				 &sonypi_device.fifo_lock) == sizeof(c))) {
 936		if (put_user(c, buf++))
 937			return -EFAULT;
 938		ret++;
 939	}
 940
 941	if (ret > 0) {
 942		struct inode *inode = file->f_path.dentry->d_inode;
 943		inode->i_atime = current_fs_time(inode->i_sb);
 944	}
 945
 946	return ret;
 947}
 948
 949static unsigned int sonypi_misc_poll(struct file *file, poll_table *wait)
 950{
 951	poll_wait(file, &sonypi_device.fifo_proc_list, wait);
 952	if (kfifo_len(&sonypi_device.fifo))
 953		return POLLIN | POLLRDNORM;
 954	return 0;
 955}
 956
 957static long sonypi_misc_ioctl(struct file *fp,
 958			     unsigned int cmd, unsigned long arg)
 959{
 960	long ret = 0;
 961	void __user *argp = (void __user *)arg;
 962	u8 val8;
 963	u16 val16;
 964
 965	mutex_lock(&sonypi_device.lock);
 966	switch (cmd) {
 967	case SONYPI_IOCGBRT:
 968		if (sonypi_ec_read(SONYPI_LCD_LIGHT, &val8)) {
 969			ret = -EIO;
 970			break;
 971		}
 972		if (copy_to_user(argp, &val8, sizeof(val8)))
 973			ret = -EFAULT;
 974		break;
 975	case SONYPI_IOCSBRT:
 976		if (copy_from_user(&val8, argp, sizeof(val8))) {
 977			ret = -EFAULT;
 978			break;
 979		}
 980		if (sonypi_ec_write(SONYPI_LCD_LIGHT, val8))
 981			ret = -EIO;
 982		break;
 983	case SONYPI_IOCGBAT1CAP:
 984		if (ec_read16(SONYPI_BAT1_FULL, &val16)) {
 985			ret = -EIO;
 986			break;
 987		}
 988		if (copy_to_user(argp, &val16, sizeof(val16)))
 989			ret = -EFAULT;
 990		break;
 991	case SONYPI_IOCGBAT1REM:
 992		if (ec_read16(SONYPI_BAT1_LEFT, &val16)) {
 993			ret = -EIO;
 994			break;
 995		}
 996		if (copy_to_user(argp, &val16, sizeof(val16)))
 997			ret = -EFAULT;
 998		break;
 999	case SONYPI_IOCGBAT2CAP:
1000		if (ec_read16(SONYPI_BAT2_FULL, &val16)) {
1001			ret = -EIO;
1002			break;
1003		}
1004		if (copy_to_user(argp, &val16, sizeof(val16)))
1005			ret = -EFAULT;
1006		break;
1007	case SONYPI_IOCGBAT2REM:
1008		if (ec_read16(SONYPI_BAT2_LEFT, &val16)) {
1009			ret = -EIO;
1010			break;
1011		}
1012		if (copy_to_user(argp, &val16, sizeof(val16)))
1013			ret = -EFAULT;
1014		break;
1015	case SONYPI_IOCGBATFLAGS:
1016		if (sonypi_ec_read(SONYPI_BAT_FLAGS, &val8)) {
1017			ret = -EIO;
1018			break;
1019		}
1020		val8 &= 0x07;
1021		if (copy_to_user(argp, &val8, sizeof(val8)))
1022			ret = -EFAULT;
1023		break;
1024	case SONYPI_IOCGBLUE:
1025		val8 = sonypi_device.bluetooth_power;
1026		if (copy_to_user(argp, &val8, sizeof(val8)))
1027			ret = -EFAULT;
1028		break;
1029	case SONYPI_IOCSBLUE:
1030		if (copy_from_user(&val8, argp, sizeof(val8))) {
1031			ret = -EFAULT;
1032			break;
1033		}
1034		sonypi_setbluetoothpower(val8);
1035		break;
1036	/* FAN Controls */
1037	case SONYPI_IOCGFAN:
1038		if (sonypi_ec_read(SONYPI_FAN0_STATUS, &val8)) {
1039			ret = -EIO;
1040			break;
1041		}
1042		if (copy_to_user(argp, &val8, sizeof(val8)))
1043			ret = -EFAULT;
1044		break;
1045	case SONYPI_IOCSFAN:
1046		if (copy_from_user(&val8, argp, sizeof(val8))) {
1047			ret = -EFAULT;
1048			break;
1049		}
1050		if (sonypi_ec_write(SONYPI_FAN0_STATUS, val8))
1051			ret = -EIO;
1052		break;
1053	/* GET Temperature (useful under APM) */
1054	case SONYPI_IOCGTEMP:
1055		if (sonypi_ec_read(SONYPI_TEMP_STATUS, &val8)) {
1056			ret = -EIO;
1057			break;
1058		}
1059		if (copy_to_user(argp, &val8, sizeof(val8)))
1060			ret = -EFAULT;
1061		break;
1062	default:
1063		ret = -EINVAL;
1064	}
1065	mutex_unlock(&sonypi_device.lock);
1066	return ret;
1067}
1068
1069static const struct file_operations sonypi_misc_fops = {
1070	.owner		= THIS_MODULE,
1071	.read		= sonypi_misc_read,
1072	.poll		= sonypi_misc_poll,
1073	.open		= sonypi_misc_open,
1074	.release	= sonypi_misc_release,
1075	.fasync		= sonypi_misc_fasync,
1076	.unlocked_ioctl	= sonypi_misc_ioctl,
1077	.llseek		= no_llseek,
1078};
1079
1080static struct miscdevice sonypi_misc_device = {
1081	.minor		= MISC_DYNAMIC_MINOR,
1082	.name		= "sonypi",
1083	.fops		= &sonypi_misc_fops,
1084};
1085
1086static void sonypi_enable(unsigned int camera_on)
1087{
1088	switch (sonypi_device.model) {
1089	case SONYPI_DEVICE_MODEL_TYPE1:
1090		sonypi_type1_srs();
1091		break;
1092	case SONYPI_DEVICE_MODEL_TYPE2:
1093		sonypi_type2_srs();
1094		break;
1095	case SONYPI_DEVICE_MODEL_TYPE3:
1096		sonypi_type3_srs();
1097		break;
1098	}
1099
1100	sonypi_call1(0x82);
1101	sonypi_call2(0x81, 0xff);
1102	sonypi_call1(compat ? 0x92 : 0x82);
1103
1104	/* Enable ACPI mode to get Fn key events */
1105	if (!SONYPI_ACPI_ACTIVE && fnkeyinit)
1106		outb(0xf0, 0xb2);
1107
1108	if (camera && camera_on)
1109		sonypi_camera_on();
1110}
1111
1112static int sonypi_disable(void)
1113{
1114	sonypi_call2(0x81, 0);	/* make sure we don't get any more events */
1115	if (camera)
1116		sonypi_camera_off();
1117
1118	/* disable ACPI mode */
1119	if (!SONYPI_ACPI_ACTIVE && fnkeyinit)
1120		outb(0xf1, 0xb2);
1121
1122	switch (sonypi_device.model) {
1123	case SONYPI_DEVICE_MODEL_TYPE1:
1124		sonypi_type1_dis();
1125		break;
1126	case SONYPI_DEVICE_MODEL_TYPE2:
1127		sonypi_type2_dis();
1128		break;
1129	case SONYPI_DEVICE_MODEL_TYPE3:
1130		sonypi_type3_dis();
1131		break;
1132	}
1133
1134	return 0;
1135}
1136
1137#ifdef CONFIG_ACPI
1138static int sonypi_acpi_add(struct acpi_device *device)
1139{
1140	sonypi_acpi_device = device;
1141	strcpy(acpi_device_name(device), "Sony laptop hotkeys");
1142	strcpy(acpi_device_class(device), "sony/hotkey");
1143	return 0;
1144}
1145
1146static int sonypi_acpi_remove(struct acpi_device *device, int type)
1147{
1148	sonypi_acpi_device = NULL;
1149	return 0;
1150}
1151
1152static const struct acpi_device_id sonypi_device_ids[] = {
1153	{"SNY6001", 0},
1154	{"", 0},
1155};
1156
1157static struct acpi_driver sonypi_acpi_driver = {
1158	.name           = "sonypi",
1159	.class          = "hkey",
1160	.ids            = sonypi_device_ids,
1161	.ops            = {
1162		           .add = sonypi_acpi_add,
1163			   .remove = sonypi_acpi_remove,
1164	},
1165};
1166#endif
1167
1168static int __devinit sonypi_create_input_devices(struct platform_device *pdev)
1169{
1170	struct input_dev *jog_dev;
1171	struct input_dev *key_dev;
1172	int i;
1173	int error;
1174
1175	sonypi_device.input_jog_dev = jog_dev = input_allocate_device();
1176	if (!jog_dev)
1177		return -ENOMEM;
1178
1179	jog_dev->name = "Sony Vaio Jogdial";
1180	jog_dev->id.bustype = BUS_ISA;
1181	jog_dev->id.vendor = PCI_VENDOR_ID_SONY;
1182	jog_dev->dev.parent = &pdev->dev;
1183
1184	jog_dev->evbit[0] = BIT_MASK(EV_KEY) | BIT_MASK(EV_REL);
1185	jog_dev->keybit[BIT_WORD(BTN_MOUSE)] = BIT_MASK(BTN_MIDDLE);
1186	jog_dev->relbit[0] = BIT_MASK(REL_WHEEL);
1187
1188	sonypi_device.input_key_dev = key_dev = input_allocate_device();
1189	if (!key_dev) {
1190		error = -ENOMEM;
1191		goto err_free_jogdev;
1192	}
1193
1194	key_dev->name = "Sony Vaio Keys";
1195	key_dev->id.bustype = BUS_ISA;
1196	key_dev->id.vendor = PCI_VENDOR_ID_SONY;
1197	key_dev->dev.parent = &pdev->dev;
1198
1199	/* Initialize the Input Drivers: special keys */
1200	key_dev->evbit[0] = BIT_MASK(EV_KEY);
1201	for (i = 0; sonypi_inputkeys[i].sonypiev; i++)
1202		if (sonypi_inputkeys[i].inputev)
1203			set_bit(sonypi_inputkeys[i].inputev, key_dev->keybit);
1204
1205	error = input_register_device(jog_dev);
1206	if (error)
1207		goto err_free_keydev;
1208
1209	error = input_register_device(key_dev);
1210	if (error)
1211		goto err_unregister_jogdev;
1212
1213	return 0;
1214
1215 err_unregister_jogdev:
1216	input_unregister_device(jog_dev);
1217	/* Set to NULL so we don't free it again below */
1218	jog_dev = NULL;
1219 err_free_keydev:
1220	input_free_device(key_dev);
1221	sonypi_device.input_key_dev = NULL;
1222 err_free_jogdev:
1223	input_free_device(jog_dev);
1224	sonypi_device.input_jog_dev = NULL;
1225
1226	return error;
1227}
1228
1229static int __devinit sonypi_setup_ioports(struct sonypi_device *dev,
1230				const struct sonypi_ioport_list *ioport_list)
1231{
1232	/* try to detect if sony-laptop is being used and thus
1233	 * has already requested one of the known ioports.
1234	 * As in the deprecated check_region this is racy has we have
1235	 * multiple ioports available and one of them can be requested
1236	 * between this check and the subsequent request. Anyway, as an
1237	 * attempt to be some more user-friendly as we currently are,
1238	 * this is enough.
1239	 */
1240	const struct sonypi_ioport_list *check = ioport_list;
1241	while (check_ioport && check->port1) {
1242		if (!request_region(check->port1,
1243				   sonypi_device.region_size,
1244				   "Sony Programmable I/O Device Check")) {
1245			printk(KERN_ERR "sonypi: ioport 0x%.4x busy, using sony-laptop? "
1246					"if not use check_ioport=0\n",
1247					check->port1);
1248			return -EBUSY;
1249		}
1250		release_region(check->port1, sonypi_device.region_size);
1251		check++;
1252	}
1253
1254	while (ioport_list->port1) {
1255
1256		if (request_region(ioport_list->port1,
1257				   sonypi_device.region_size,
1258				   "Sony Programmable I/O Device")) {
1259			dev->ioport1 = ioport_list->port1;
1260			dev->ioport2 = ioport_list->port2;
1261			return 0;
1262		}
1263		ioport_list++;
1264	}
1265
1266	return -EBUSY;
1267}
1268
1269static int __devinit sonypi_setup_irq(struct sonypi_device *dev,
1270				      const struct sonypi_irq_list *irq_list)
1271{
1272	while (irq_list->irq) {
1273
1274		if (!request_irq(irq_list->irq, sonypi_irq,
1275				 IRQF_SHARED, "sonypi", sonypi_irq)) {
1276			dev->irq = irq_list->irq;
1277			dev->bits = irq_list->bits;
1278			return 0;
1279		}
1280		irq_list++;
1281	}
1282
1283	return -EBUSY;
1284}
1285
1286static void __devinit sonypi_display_info(void)
1287{
1288	printk(KERN_INFO "sonypi: detected type%d model, "
1289	       "verbose = %d, fnkeyinit = %s, camera = %s, "
1290	       "compat = %s, mask = 0x%08lx, useinput = %s, acpi = %s\n",
1291	       sonypi_device.model,
1292	       verbose,
1293	       fnkeyinit ? "on" : "off",
1294	       camera ? "on" : "off",
1295	       compat ? "on" : "off",
1296	       mask,
1297	       useinput ? "on" : "off",
1298	       SONYPI_ACPI_ACTIVE ? "on" : "off");
1299	printk(KERN_INFO "sonypi: enabled at irq=%d, port1=0x%x, port2=0x%x\n",
1300	       sonypi_device.irq,
1301	       sonypi_device.ioport1, sonypi_device.ioport2);
1302
1303	if (minor == -1)
1304		printk(KERN_INFO "sonypi: device allocated minor is %d\n",
1305		       sonypi_misc_device.minor);
1306}
1307
1308static int __devinit sonypi_probe(struct platform_device *dev)
1309{
1310	const struct sonypi_ioport_list *ioport_list;
1311	const struct sonypi_irq_list *irq_list;
1312	struct pci_dev *pcidev;
1313	int error;
1314
1315	printk(KERN_WARNING "sonypi: please try the sony-laptop module instead "
1316			"and report failures, see also "
1317			"http://www.linux.it/~malattia/wiki/index.php/Sony_drivers\n");
1318
1319	spin_lock_init(&sonypi_device.fifo_lock);
1320	error = kfifo_alloc(&sonypi_device.fifo, SONYPI_BUF_SIZE, GFP_KERNEL);
1321	if (error) {
1322		printk(KERN_ERR "sonypi: kfifo_alloc failed\n");
1323		return error;
1324	}
1325
1326	init_waitqueue_head(&sonypi_device.fifo_proc_list);
1327	mutex_init(&sonypi_device.lock);
1328	sonypi_device.bluetooth_power = -1;
1329
1330	if ((pcidev = pci_get_device(PCI_VENDOR_ID_INTEL,
1331				     PCI_DEVICE_ID_INTEL_82371AB_3, NULL)))
1332		sonypi_device.model = SONYPI_DEVICE_MODEL_TYPE1;
1333	else if ((pcidev = pci_get_device(PCI_VENDOR_ID_INTEL,
1334					  PCI_DEVICE_ID_INTEL_ICH6_1, NULL)))
1335		sonypi_device.model = SONYPI_DEVICE_MODEL_TYPE3;
1336	else if ((pcidev = pci_get_device(PCI_VENDOR_ID_INTEL,
1337					  PCI_DEVICE_ID_INTEL_ICH7_1, NULL)))
1338		sonypi_device.model = SONYPI_DEVICE_MODEL_TYPE3;
1339	else
1340		sonypi_device.model = SONYPI_DEVICE_MODEL_TYPE2;
1341
1342	if (pcidev && pci_enable_device(pcidev)) {
1343		printk(KERN_ERR "sonypi: pci_enable_device failed\n");
1344		error = -EIO;
1345		goto err_put_pcidev;
1346	}
1347
1348	sonypi_device.dev = pcidev;
1349
1350	if (sonypi_device.model == SONYPI_DEVICE_MODEL_TYPE1) {
1351		ioport_list = sonypi_type1_ioport_list;
1352		sonypi_device.region_size = SONYPI_TYPE1_REGION_SIZE;
1353		sonypi_device.evtype_offset = SONYPI_TYPE1_EVTYPE_OFFSET;
1354		irq_list = sonypi_type1_irq_list;
1355	} else if (sonypi_device.model == SONYPI_DEVICE_MODEL_TYPE2) {
1356		ioport_list = sonypi_type2_ioport_list;
1357		sonypi_device.region_size = SONYPI_TYPE2_REGION_SIZE;
1358		sonypi_device.evtype_offset = SONYPI_TYPE2_EVTYPE_OFFSET;
1359		irq_list = sonypi_type2_irq_list;
1360	} else {
1361		ioport_list = sonypi_type3_ioport_list;
1362		sonypi_device.region_size = SONYPI_TYPE3_REGION_SIZE;
1363		sonypi_device.evtype_offset = SONYPI_TYPE3_EVTYPE_OFFSET;
1364		irq_list = sonypi_type3_irq_list;
1365	}
1366
1367	error = sonypi_setup_ioports(&sonypi_device, ioport_list);
1368	if (error) {
1369		printk(KERN_ERR "sonypi: failed to request ioports\n");
1370		goto err_disable_pcidev;
1371	}
1372
1373	error = sonypi_setup_irq(&sonypi_device, irq_list);
1374	if (error) {
1375		printk(KERN_ERR "sonypi: request_irq failed\n");
1376		goto err_free_ioports;
1377	}
1378
1379	if (minor != -1)
1380		sonypi_misc_device.minor = minor;
1381	error = misc_register(&sonypi_misc_device);
1382	if (error) {
1383		printk(KERN_ERR "sonypi: misc_register failed\n");
1384		goto err_free_irq;
1385	}
1386
1387	sonypi_display_info();
1388
1389	if (useinput) {
1390
1391		error = sonypi_create_input_devices(dev);
1392		if (error) {
1393			printk(KERN_ERR
1394				"sonypi: failed to create input devices\n");
1395			goto err_miscdev_unregister;
1396		}
1397
1398		spin_lock_init(&sonypi_device.input_fifo_lock);
1399		error = kfifo_alloc(&sonypi_device.input_fifo, SONYPI_BUF_SIZE,
1400				GFP_KERNEL);
1401		if (error) {
1402			printk(KERN_ERR "sonypi: kfifo_alloc failed\n");
1403			goto err_inpdev_unregister;
1404		}
1405
1406		INIT_WORK(&sonypi_device.input_work, input_keyrelease);
1407	}
1408
1409	sonypi_enable(0);
1410
1411	return 0;
1412
1413 err_inpdev_unregister:
1414	input_unregister_device(sonypi_device.input_key_dev);
1415	input_unregister_device(sonypi_device.input_jog_dev);
1416 err_miscdev_unregister:
1417	misc_deregister(&sonypi_misc_device);
1418 err_free_irq:
1419	free_irq(sonypi_device.irq, sonypi_irq);
1420 err_free_ioports:
1421	release_region(sonypi_device.ioport1, sonypi_device.region_size);
1422 err_disable_pcidev:
1423	if (pcidev)
1424		pci_disable_device(pcidev);
1425 err_put_pcidev:
1426	pci_dev_put(pcidev);
1427	kfifo_free(&sonypi_device.fifo);
1428
1429	return error;
1430}
1431
1432static int __devexit sonypi_remove(struct platform_device *dev)
1433{
1434	sonypi_disable();
1435
1436	synchronize_irq(sonypi_device.irq);
1437	flush_work_sync(&sonypi_device.input_work);
1438
1439	if (useinput) {
1440		input_unregister_device(sonypi_device.input_key_dev);
1441		input_unregister_device(sonypi_device.input_jog_dev);
1442		kfifo_free(&sonypi_device.input_fifo);
1443	}
1444
1445	misc_deregister(&sonypi_misc_device);
1446
1447	free_irq(sonypi_device.irq, sonypi_irq);
1448	release_region(sonypi_device.ioport1, sonypi_device.region_size);
1449
1450	if (sonypi_device.dev) {
1451		pci_disable_device(sonypi_device.dev);
1452		pci_dev_put(sonypi_device.dev);
1453	}
1454
1455	kfifo_free(&sonypi_device.fifo);
1456
1457	return 0;
1458}
1459
1460#ifdef CONFIG_PM
1461static int old_camera_power;
1462
1463static int sonypi_suspend(struct platform_device *dev, pm_message_t state)
1464{
1465	old_camera_power = sonypi_device.camera_power;
1466	sonypi_disable();
1467
1468	return 0;
1469}
1470
1471static int sonypi_resume(struct platform_device *dev)
1472{
1473	sonypi_enable(old_camera_power);
1474	return 0;
1475}
 
 
 
1476#else
1477#define sonypi_suspend	NULL
1478#define sonypi_resume	NULL
1479#endif
1480
1481static void sonypi_shutdown(struct platform_device *dev)
1482{
1483	sonypi_disable();
1484}
1485
1486static struct platform_driver sonypi_driver = {
1487	.driver		= {
1488		.name	= "sonypi",
1489		.owner	= THIS_MODULE,
1490	},
1491	.probe		= sonypi_probe,
1492	.remove		= __devexit_p(sonypi_remove),
1493	.shutdown	= sonypi_shutdown,
1494	.suspend	= sonypi_suspend,
1495	.resume		= sonypi_resume,
1496};
1497
1498static struct platform_device *sonypi_platform_device;
1499
1500static struct dmi_system_id __initdata sonypi_dmi_table[] = {
1501	{
1502		.ident = "Sony Vaio",
1503		.matches = {
1504			DMI_MATCH(DMI_SYS_VENDOR, "Sony Corporation"),
1505			DMI_MATCH(DMI_PRODUCT_NAME, "PCG-"),
1506		},
1507	},
1508	{
1509		.ident = "Sony Vaio",
1510		.matches = {
1511			DMI_MATCH(DMI_SYS_VENDOR, "Sony Corporation"),
1512			DMI_MATCH(DMI_PRODUCT_NAME, "VGN-"),
1513		},
1514	},
1515	{ }
1516};
1517
1518static int __init sonypi_init(void)
1519{
1520	int error;
1521
1522	printk(KERN_INFO
1523		"sonypi: Sony Programmable I/O Controller Driver v%s.\n",
1524		SONYPI_DRIVER_VERSION);
1525
1526	if (!dmi_check_system(sonypi_dmi_table))
1527		return -ENODEV;
1528
1529	error = platform_driver_register(&sonypi_driver);
1530	if (error)
1531		return error;
1532
1533	sonypi_platform_device = platform_device_alloc("sonypi", -1);
1534	if (!sonypi_platform_device) {
1535		error = -ENOMEM;
1536		goto err_driver_unregister;
1537	}
1538
1539	error = platform_device_add(sonypi_platform_device);
1540	if (error)
1541		goto err_free_device;
1542
1543#ifdef CONFIG_ACPI
1544	if (acpi_bus_register_driver(&sonypi_acpi_driver) >= 0)
1545		acpi_driver_registered = 1;
1546#endif
1547
1548	return 0;
1549
1550 err_free_device:
1551	platform_device_put(sonypi_platform_device);
1552 err_driver_unregister:
1553	platform_driver_unregister(&sonypi_driver);
1554	return error;
1555}
1556
1557static void __exit sonypi_exit(void)
1558{
1559#ifdef CONFIG_ACPI
1560	if (acpi_driver_registered)
1561		acpi_bus_unregister_driver(&sonypi_acpi_driver);
1562#endif
1563	platform_device_unregister(sonypi_platform_device);
1564	platform_driver_unregister(&sonypi_driver);
1565	printk(KERN_INFO "sonypi: removed.\n");
1566}
1567
1568module_init(sonypi_init);
1569module_exit(sonypi_exit);
v4.10.11
   1/*
   2 * Sony Programmable I/O Control Device driver for VAIO
   3 *
   4 * Copyright (C) 2007 Mattia Dongili <malattia@linux.it>
   5 *
   6 * Copyright (C) 2001-2005 Stelian Pop <stelian@popies.net>
   7 *
   8 * Copyright (C) 2005 Narayanan R S <nars@kadamba.org>
   9 *
  10 * Copyright (C) 2001-2002 AlcĂ´ve <www.alcove.com>
  11 *
  12 * Copyright (C) 2001 Michael Ashley <m.ashley@unsw.edu.au>
  13 *
  14 * Copyright (C) 2001 Junichi Morita <jun1m@mars.dti.ne.jp>
  15 *
  16 * Copyright (C) 2000 Takaya Kinjo <t-kinjo@tc4.so-net.ne.jp>
  17 *
  18 * Copyright (C) 2000 Andrew Tridgell <tridge@valinux.com>
  19 *
  20 * Earlier work by Werner Almesberger, Paul `Rusty' Russell and Paul Mackerras.
  21 *
  22 * This program is free software; you can redistribute it and/or modify
  23 * it under the terms of the GNU General Public License as published by
  24 * the Free Software Foundation; either version 2 of the License, or
  25 * (at your option) any later version.
  26 *
  27 * This program is distributed in the hope that it will be useful,
  28 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  29 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  30 * GNU General Public License for more details.
  31 *
  32 * You should have received a copy of the GNU General Public License
  33 * along with this program; if not, write to the Free Software
  34 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  35 *
  36 */
  37
  38#include <linux/module.h>
  39#include <linux/sched.h>
  40#include <linux/input.h>
  41#include <linux/pci.h>
  42#include <linux/init.h>
  43#include <linux/interrupt.h>
  44#include <linux/miscdevice.h>
  45#include <linux/poll.h>
  46#include <linux/delay.h>
  47#include <linux/wait.h>
  48#include <linux/acpi.h>
  49#include <linux/dmi.h>
  50#include <linux/err.h>
  51#include <linux/kfifo.h>
  52#include <linux/platform_device.h>
  53#include <linux/gfp.h>
  54
  55#include <linux/uaccess.h>
  56#include <asm/io.h>
 
  57
  58#include <linux/sonypi.h>
  59
  60#define SONYPI_DRIVER_VERSION	 "1.26"
  61
  62MODULE_AUTHOR("Stelian Pop <stelian@popies.net>");
  63MODULE_DESCRIPTION("Sony Programmable I/O Control Device driver");
  64MODULE_LICENSE("GPL");
  65MODULE_VERSION(SONYPI_DRIVER_VERSION);
  66
  67static int minor = -1;
  68module_param(minor, int, 0);
  69MODULE_PARM_DESC(minor,
  70		 "minor number of the misc device, default is -1 (automatic)");
  71
  72static int verbose;		/* = 0 */
  73module_param(verbose, int, 0644);
  74MODULE_PARM_DESC(verbose, "be verbose, default is 0 (no)");
  75
  76static int fnkeyinit;		/* = 0 */
  77module_param(fnkeyinit, int, 0444);
  78MODULE_PARM_DESC(fnkeyinit,
  79		 "set this if your Fn keys do not generate any event");
  80
  81static int camera;		/* = 0 */
  82module_param(camera, int, 0444);
  83MODULE_PARM_DESC(camera,
  84		 "set this if you have a MotionEye camera (PictureBook series)");
  85
  86static int compat;		/* = 0 */
  87module_param(compat, int, 0444);
  88MODULE_PARM_DESC(compat,
  89		 "set this if you want to enable backward compatibility mode");
  90
  91static unsigned long mask = 0xffffffff;
  92module_param(mask, ulong, 0644);
  93MODULE_PARM_DESC(mask,
  94		 "set this to the mask of event you want to enable (see doc)");
  95
  96static int useinput = 1;
  97module_param(useinput, int, 0444);
  98MODULE_PARM_DESC(useinput,
  99		 "set this if you would like sonypi to feed events to the input subsystem");
 100
 101static int check_ioport = 1;
 102module_param(check_ioport, int, 0444);
 103MODULE_PARM_DESC(check_ioport,
 104		 "set this to 0 if you think the automatic ioport check for sony-laptop is wrong");
 105
 106#define SONYPI_DEVICE_MODEL_TYPE1	1
 107#define SONYPI_DEVICE_MODEL_TYPE2	2
 108#define SONYPI_DEVICE_MODEL_TYPE3	3
 109
 110/* type1 models use those */
 111#define SONYPI_IRQ_PORT			0x8034
 112#define SONYPI_IRQ_SHIFT		22
 113#define SONYPI_TYPE1_BASE		0x50
 114#define SONYPI_G10A			(SONYPI_TYPE1_BASE+0x14)
 115#define SONYPI_TYPE1_REGION_SIZE	0x08
 116#define SONYPI_TYPE1_EVTYPE_OFFSET	0x04
 117
 118/* type2 series specifics */
 119#define SONYPI_SIRQ			0x9b
 120#define SONYPI_SLOB			0x9c
 121#define SONYPI_SHIB			0x9d
 122#define SONYPI_TYPE2_REGION_SIZE	0x20
 123#define SONYPI_TYPE2_EVTYPE_OFFSET	0x12
 124
 125/* type3 series specifics */
 126#define SONYPI_TYPE3_BASE		0x40
 127#define SONYPI_TYPE3_GID2		(SONYPI_TYPE3_BASE+0x48) /* 16 bits */
 128#define SONYPI_TYPE3_MISC		(SONYPI_TYPE3_BASE+0x6d) /* 8 bits  */
 129#define SONYPI_TYPE3_REGION_SIZE	0x20
 130#define SONYPI_TYPE3_EVTYPE_OFFSET	0x12
 131
 132/* battery / brightness addresses */
 133#define SONYPI_BAT_FLAGS	0x81
 134#define SONYPI_LCD_LIGHT	0x96
 135#define SONYPI_BAT1_PCTRM	0xa0
 136#define SONYPI_BAT1_LEFT	0xa2
 137#define SONYPI_BAT1_MAXRT	0xa4
 138#define SONYPI_BAT2_PCTRM	0xa8
 139#define SONYPI_BAT2_LEFT	0xaa
 140#define SONYPI_BAT2_MAXRT	0xac
 141#define SONYPI_BAT1_MAXTK	0xb0
 142#define SONYPI_BAT1_FULL	0xb2
 143#define SONYPI_BAT2_MAXTK	0xb8
 144#define SONYPI_BAT2_FULL	0xba
 145
 146/* FAN0 information (reverse engineered from ACPI tables) */
 147#define SONYPI_FAN0_STATUS	0x93
 148#define SONYPI_TEMP_STATUS	0xC1
 149
 150/* ioports used for brightness and type2 events */
 151#define SONYPI_DATA_IOPORT	0x62
 152#define SONYPI_CST_IOPORT	0x66
 153
 154/* The set of possible ioports */
 155struct sonypi_ioport_list {
 156	u16	port1;
 157	u16	port2;
 158};
 159
 160static struct sonypi_ioport_list sonypi_type1_ioport_list[] = {
 161	{ 0x10c0, 0x10c4 },	/* looks like the default on C1Vx */
 162	{ 0x1080, 0x1084 },
 163	{ 0x1090, 0x1094 },
 164	{ 0x10a0, 0x10a4 },
 165	{ 0x10b0, 0x10b4 },
 166	{ 0x0, 0x0 }
 167};
 168
 169static struct sonypi_ioport_list sonypi_type2_ioport_list[] = {
 170	{ 0x1080, 0x1084 },
 171	{ 0x10a0, 0x10a4 },
 172	{ 0x10c0, 0x10c4 },
 173	{ 0x10e0, 0x10e4 },
 174	{ 0x0, 0x0 }
 175};
 176
 177/* same as in type 2 models */
 178static struct sonypi_ioport_list *sonypi_type3_ioport_list =
 179	sonypi_type2_ioport_list;
 180
 181/* The set of possible interrupts */
 182struct sonypi_irq_list {
 183	u16	irq;
 184	u16	bits;
 185};
 186
 187static struct sonypi_irq_list sonypi_type1_irq_list[] = {
 188	{ 11, 0x2 },	/* IRQ 11, GO22=0,GO23=1 in AML */
 189	{ 10, 0x1 },	/* IRQ 10, GO22=1,GO23=0 in AML */
 190	{  5, 0x0 },	/* IRQ  5, GO22=0,GO23=0 in AML */
 191	{  0, 0x3 }	/* no IRQ, GO22=1,GO23=1 in AML */
 192};
 193
 194static struct sonypi_irq_list sonypi_type2_irq_list[] = {
 195	{ 11, 0x80 },	/* IRQ 11, 0x80 in SIRQ in AML */
 196	{ 10, 0x40 },	/* IRQ 10, 0x40 in SIRQ in AML */
 197	{  9, 0x20 },	/* IRQ  9, 0x20 in SIRQ in AML */
 198	{  6, 0x10 },	/* IRQ  6, 0x10 in SIRQ in AML */
 199	{  0, 0x00 }	/* no IRQ, 0x00 in SIRQ in AML */
 200};
 201
 202/* same as in type2 models */
 203static struct sonypi_irq_list *sonypi_type3_irq_list = sonypi_type2_irq_list;
 204
 205#define SONYPI_CAMERA_BRIGHTNESS		0
 206#define SONYPI_CAMERA_CONTRAST			1
 207#define SONYPI_CAMERA_HUE			2
 208#define SONYPI_CAMERA_COLOR			3
 209#define SONYPI_CAMERA_SHARPNESS			4
 210
 211#define SONYPI_CAMERA_PICTURE			5
 212#define SONYPI_CAMERA_EXPOSURE_MASK		0xC
 213#define SONYPI_CAMERA_WHITE_BALANCE_MASK	0x3
 214#define SONYPI_CAMERA_PICTURE_MODE_MASK		0x30
 215#define SONYPI_CAMERA_MUTE_MASK			0x40
 216
 217/* the rest don't need a loop until not 0xff */
 218#define SONYPI_CAMERA_AGC			6
 219#define SONYPI_CAMERA_AGC_MASK			0x30
 220#define SONYPI_CAMERA_SHUTTER_MASK 		0x7
 221
 222#define SONYPI_CAMERA_SHUTDOWN_REQUEST		7
 223#define SONYPI_CAMERA_CONTROL			0x10
 224
 225#define SONYPI_CAMERA_STATUS 			7
 226#define SONYPI_CAMERA_STATUS_READY 		0x2
 227#define SONYPI_CAMERA_STATUS_POSITION		0x4
 228
 229#define SONYPI_DIRECTION_BACKWARDS 		0x4
 230
 231#define SONYPI_CAMERA_REVISION 			8
 232#define SONYPI_CAMERA_ROMVERSION 		9
 233
 234/* Event masks */
 235#define SONYPI_JOGGER_MASK			0x00000001
 236#define SONYPI_CAPTURE_MASK			0x00000002
 237#define SONYPI_FNKEY_MASK			0x00000004
 238#define SONYPI_BLUETOOTH_MASK			0x00000008
 239#define SONYPI_PKEY_MASK			0x00000010
 240#define SONYPI_BACK_MASK			0x00000020
 241#define SONYPI_HELP_MASK			0x00000040
 242#define SONYPI_LID_MASK				0x00000080
 243#define SONYPI_ZOOM_MASK			0x00000100
 244#define SONYPI_THUMBPHRASE_MASK			0x00000200
 245#define SONYPI_MEYE_MASK			0x00000400
 246#define SONYPI_MEMORYSTICK_MASK			0x00000800
 247#define SONYPI_BATTERY_MASK			0x00001000
 248#define SONYPI_WIRELESS_MASK			0x00002000
 249
 250struct sonypi_event {
 251	u8	data;
 252	u8	event;
 253};
 254
 255/* The set of possible button release events */
 256static struct sonypi_event sonypi_releaseev[] = {
 257	{ 0x00, SONYPI_EVENT_ANYBUTTON_RELEASED },
 258	{ 0, 0 }
 259};
 260
 261/* The set of possible jogger events  */
 262static struct sonypi_event sonypi_joggerev[] = {
 263	{ 0x1f, SONYPI_EVENT_JOGDIAL_UP },
 264	{ 0x01, SONYPI_EVENT_JOGDIAL_DOWN },
 265	{ 0x5f, SONYPI_EVENT_JOGDIAL_UP_PRESSED },
 266	{ 0x41, SONYPI_EVENT_JOGDIAL_DOWN_PRESSED },
 267	{ 0x1e, SONYPI_EVENT_JOGDIAL_FAST_UP },
 268	{ 0x02, SONYPI_EVENT_JOGDIAL_FAST_DOWN },
 269	{ 0x5e, SONYPI_EVENT_JOGDIAL_FAST_UP_PRESSED },
 270	{ 0x42, SONYPI_EVENT_JOGDIAL_FAST_DOWN_PRESSED },
 271	{ 0x1d, SONYPI_EVENT_JOGDIAL_VFAST_UP },
 272	{ 0x03, SONYPI_EVENT_JOGDIAL_VFAST_DOWN },
 273	{ 0x5d, SONYPI_EVENT_JOGDIAL_VFAST_UP_PRESSED },
 274	{ 0x43, SONYPI_EVENT_JOGDIAL_VFAST_DOWN_PRESSED },
 275	{ 0x40, SONYPI_EVENT_JOGDIAL_PRESSED },
 276	{ 0, 0 }
 277};
 278
 279/* The set of possible capture button events */
 280static struct sonypi_event sonypi_captureev[] = {
 281	{ 0x05, SONYPI_EVENT_CAPTURE_PARTIALPRESSED },
 282	{ 0x07, SONYPI_EVENT_CAPTURE_PRESSED },
 283	{ 0x01, SONYPI_EVENT_CAPTURE_PARTIALRELEASED },
 284	{ 0, 0 }
 285};
 286
 287/* The set of possible fnkeys events */
 288static struct sonypi_event sonypi_fnkeyev[] = {
 289	{ 0x10, SONYPI_EVENT_FNKEY_ESC },
 290	{ 0x11, SONYPI_EVENT_FNKEY_F1 },
 291	{ 0x12, SONYPI_EVENT_FNKEY_F2 },
 292	{ 0x13, SONYPI_EVENT_FNKEY_F3 },
 293	{ 0x14, SONYPI_EVENT_FNKEY_F4 },
 294	{ 0x15, SONYPI_EVENT_FNKEY_F5 },
 295	{ 0x16, SONYPI_EVENT_FNKEY_F6 },
 296	{ 0x17, SONYPI_EVENT_FNKEY_F7 },
 297	{ 0x18, SONYPI_EVENT_FNKEY_F8 },
 298	{ 0x19, SONYPI_EVENT_FNKEY_F9 },
 299	{ 0x1a, SONYPI_EVENT_FNKEY_F10 },
 300	{ 0x1b, SONYPI_EVENT_FNKEY_F11 },
 301	{ 0x1c, SONYPI_EVENT_FNKEY_F12 },
 302	{ 0x1f, SONYPI_EVENT_FNKEY_RELEASED },
 303	{ 0x21, SONYPI_EVENT_FNKEY_1 },
 304	{ 0x22, SONYPI_EVENT_FNKEY_2 },
 305	{ 0x31, SONYPI_EVENT_FNKEY_D },
 306	{ 0x32, SONYPI_EVENT_FNKEY_E },
 307	{ 0x33, SONYPI_EVENT_FNKEY_F },
 308	{ 0x34, SONYPI_EVENT_FNKEY_S },
 309	{ 0x35, SONYPI_EVENT_FNKEY_B },
 310	{ 0x36, SONYPI_EVENT_FNKEY_ONLY },
 311	{ 0, 0 }
 312};
 313
 314/* The set of possible program key events */
 315static struct sonypi_event sonypi_pkeyev[] = {
 316	{ 0x01, SONYPI_EVENT_PKEY_P1 },
 317	{ 0x02, SONYPI_EVENT_PKEY_P2 },
 318	{ 0x04, SONYPI_EVENT_PKEY_P3 },
 319	{ 0x5c, SONYPI_EVENT_PKEY_P1 },
 320	{ 0, 0 }
 321};
 322
 323/* The set of possible bluetooth events */
 324static struct sonypi_event sonypi_blueev[] = {
 325	{ 0x55, SONYPI_EVENT_BLUETOOTH_PRESSED },
 326	{ 0x59, SONYPI_EVENT_BLUETOOTH_ON },
 327	{ 0x5a, SONYPI_EVENT_BLUETOOTH_OFF },
 328	{ 0, 0 }
 329};
 330
 331/* The set of possible wireless events */
 332static struct sonypi_event sonypi_wlessev[] = {
 333	{ 0x59, SONYPI_EVENT_WIRELESS_ON },
 334	{ 0x5a, SONYPI_EVENT_WIRELESS_OFF },
 335	{ 0, 0 }
 336};
 337
 338/* The set of possible back button events */
 339static struct sonypi_event sonypi_backev[] = {
 340	{ 0x20, SONYPI_EVENT_BACK_PRESSED },
 341	{ 0, 0 }
 342};
 343
 344/* The set of possible help button events */
 345static struct sonypi_event sonypi_helpev[] = {
 346	{ 0x3b, SONYPI_EVENT_HELP_PRESSED },
 347	{ 0, 0 }
 348};
 349
 350
 351/* The set of possible lid events */
 352static struct sonypi_event sonypi_lidev[] = {
 353	{ 0x51, SONYPI_EVENT_LID_CLOSED },
 354	{ 0x50, SONYPI_EVENT_LID_OPENED },
 355	{ 0, 0 }
 356};
 357
 358/* The set of possible zoom events */
 359static struct sonypi_event sonypi_zoomev[] = {
 360	{ 0x39, SONYPI_EVENT_ZOOM_PRESSED },
 361	{ 0, 0 }
 362};
 363
 364/* The set of possible thumbphrase events */
 365static struct sonypi_event sonypi_thumbphraseev[] = {
 366	{ 0x3a, SONYPI_EVENT_THUMBPHRASE_PRESSED },
 367	{ 0, 0 }
 368};
 369
 370/* The set of possible motioneye camera events */
 371static struct sonypi_event sonypi_meyeev[] = {
 372	{ 0x00, SONYPI_EVENT_MEYE_FACE },
 373	{ 0x01, SONYPI_EVENT_MEYE_OPPOSITE },
 374	{ 0, 0 }
 375};
 376
 377/* The set of possible memorystick events */
 378static struct sonypi_event sonypi_memorystickev[] = {
 379	{ 0x53, SONYPI_EVENT_MEMORYSTICK_INSERT },
 380	{ 0x54, SONYPI_EVENT_MEMORYSTICK_EJECT },
 381	{ 0, 0 }
 382};
 383
 384/* The set of possible battery events */
 385static struct sonypi_event sonypi_batteryev[] = {
 386	{ 0x20, SONYPI_EVENT_BATTERY_INSERT },
 387	{ 0x30, SONYPI_EVENT_BATTERY_REMOVE },
 388	{ 0, 0 }
 389};
 390
 391static struct sonypi_eventtypes {
 392	int			model;
 393	u8			data;
 394	unsigned long		mask;
 395	struct sonypi_event *	events;
 396} sonypi_eventtypes[] = {
 397	{ SONYPI_DEVICE_MODEL_TYPE1, 0, 0xffffffff, sonypi_releaseev },
 398	{ SONYPI_DEVICE_MODEL_TYPE1, 0x70, SONYPI_MEYE_MASK, sonypi_meyeev },
 399	{ SONYPI_DEVICE_MODEL_TYPE1, 0x30, SONYPI_LID_MASK, sonypi_lidev },
 400	{ SONYPI_DEVICE_MODEL_TYPE1, 0x60, SONYPI_CAPTURE_MASK, sonypi_captureev },
 401	{ SONYPI_DEVICE_MODEL_TYPE1, 0x10, SONYPI_JOGGER_MASK, sonypi_joggerev },
 402	{ SONYPI_DEVICE_MODEL_TYPE1, 0x20, SONYPI_FNKEY_MASK, sonypi_fnkeyev },
 403	{ SONYPI_DEVICE_MODEL_TYPE1, 0x30, SONYPI_BLUETOOTH_MASK, sonypi_blueev },
 404	{ SONYPI_DEVICE_MODEL_TYPE1, 0x40, SONYPI_PKEY_MASK, sonypi_pkeyev },
 405	{ SONYPI_DEVICE_MODEL_TYPE1, 0x30, SONYPI_MEMORYSTICK_MASK, sonypi_memorystickev },
 406	{ SONYPI_DEVICE_MODEL_TYPE1, 0x40, SONYPI_BATTERY_MASK, sonypi_batteryev },
 407
 408	{ SONYPI_DEVICE_MODEL_TYPE2, 0, 0xffffffff, sonypi_releaseev },
 409	{ SONYPI_DEVICE_MODEL_TYPE2, 0x38, SONYPI_LID_MASK, sonypi_lidev },
 410	{ SONYPI_DEVICE_MODEL_TYPE2, 0x11, SONYPI_JOGGER_MASK, sonypi_joggerev },
 411	{ SONYPI_DEVICE_MODEL_TYPE2, 0x61, SONYPI_CAPTURE_MASK, sonypi_captureev },
 412	{ SONYPI_DEVICE_MODEL_TYPE2, 0x21, SONYPI_FNKEY_MASK, sonypi_fnkeyev },
 413	{ SONYPI_DEVICE_MODEL_TYPE2, 0x31, SONYPI_BLUETOOTH_MASK, sonypi_blueev },
 414	{ SONYPI_DEVICE_MODEL_TYPE2, 0x08, SONYPI_PKEY_MASK, sonypi_pkeyev },
 415	{ SONYPI_DEVICE_MODEL_TYPE2, 0x11, SONYPI_BACK_MASK, sonypi_backev },
 416	{ SONYPI_DEVICE_MODEL_TYPE2, 0x21, SONYPI_HELP_MASK, sonypi_helpev },
 417	{ SONYPI_DEVICE_MODEL_TYPE2, 0x21, SONYPI_ZOOM_MASK, sonypi_zoomev },
 418	{ SONYPI_DEVICE_MODEL_TYPE2, 0x20, SONYPI_THUMBPHRASE_MASK, sonypi_thumbphraseev },
 419	{ SONYPI_DEVICE_MODEL_TYPE2, 0x31, SONYPI_MEMORYSTICK_MASK, sonypi_memorystickev },
 420	{ SONYPI_DEVICE_MODEL_TYPE2, 0x41, SONYPI_BATTERY_MASK, sonypi_batteryev },
 421	{ SONYPI_DEVICE_MODEL_TYPE2, 0x31, SONYPI_PKEY_MASK, sonypi_pkeyev },
 422
 423	{ SONYPI_DEVICE_MODEL_TYPE3, 0, 0xffffffff, sonypi_releaseev },
 424	{ SONYPI_DEVICE_MODEL_TYPE3, 0x21, SONYPI_FNKEY_MASK, sonypi_fnkeyev },
 425	{ SONYPI_DEVICE_MODEL_TYPE3, 0x31, SONYPI_WIRELESS_MASK, sonypi_wlessev },
 426	{ SONYPI_DEVICE_MODEL_TYPE3, 0x31, SONYPI_MEMORYSTICK_MASK, sonypi_memorystickev },
 427	{ SONYPI_DEVICE_MODEL_TYPE3, 0x41, SONYPI_BATTERY_MASK, sonypi_batteryev },
 428	{ SONYPI_DEVICE_MODEL_TYPE3, 0x31, SONYPI_PKEY_MASK, sonypi_pkeyev },
 429	{ 0 }
 430};
 431
 432#define SONYPI_BUF_SIZE	128
 433
 434/* Correspondance table between sonypi events and input layer events */
 435static struct {
 436	int sonypiev;
 437	int inputev;
 438} sonypi_inputkeys[] = {
 439	{ SONYPI_EVENT_CAPTURE_PRESSED,	 	KEY_CAMERA },
 440	{ SONYPI_EVENT_FNKEY_ONLY, 		KEY_FN },
 441	{ SONYPI_EVENT_FNKEY_ESC, 		KEY_FN_ESC },
 442	{ SONYPI_EVENT_FNKEY_F1, 		KEY_FN_F1 },
 443	{ SONYPI_EVENT_FNKEY_F2, 		KEY_FN_F2 },
 444	{ SONYPI_EVENT_FNKEY_F3, 		KEY_FN_F3 },
 445	{ SONYPI_EVENT_FNKEY_F4, 		KEY_FN_F4 },
 446	{ SONYPI_EVENT_FNKEY_F5, 		KEY_FN_F5 },
 447	{ SONYPI_EVENT_FNKEY_F6, 		KEY_FN_F6 },
 448	{ SONYPI_EVENT_FNKEY_F7, 		KEY_FN_F7 },
 449	{ SONYPI_EVENT_FNKEY_F8, 		KEY_FN_F8 },
 450	{ SONYPI_EVENT_FNKEY_F9,		KEY_FN_F9 },
 451	{ SONYPI_EVENT_FNKEY_F10,		KEY_FN_F10 },
 452	{ SONYPI_EVENT_FNKEY_F11, 		KEY_FN_F11 },
 453	{ SONYPI_EVENT_FNKEY_F12,		KEY_FN_F12 },
 454	{ SONYPI_EVENT_FNKEY_1, 		KEY_FN_1 },
 455	{ SONYPI_EVENT_FNKEY_2, 		KEY_FN_2 },
 456	{ SONYPI_EVENT_FNKEY_D,			KEY_FN_D },
 457	{ SONYPI_EVENT_FNKEY_E,			KEY_FN_E },
 458	{ SONYPI_EVENT_FNKEY_F,			KEY_FN_F },
 459	{ SONYPI_EVENT_FNKEY_S,			KEY_FN_S },
 460	{ SONYPI_EVENT_FNKEY_B,			KEY_FN_B },
 461	{ SONYPI_EVENT_BLUETOOTH_PRESSED, 	KEY_BLUE },
 462	{ SONYPI_EVENT_BLUETOOTH_ON, 		KEY_BLUE },
 463	{ SONYPI_EVENT_PKEY_P1, 		KEY_PROG1 },
 464	{ SONYPI_EVENT_PKEY_P2, 		KEY_PROG2 },
 465	{ SONYPI_EVENT_PKEY_P3, 		KEY_PROG3 },
 466	{ SONYPI_EVENT_BACK_PRESSED, 		KEY_BACK },
 467	{ SONYPI_EVENT_HELP_PRESSED, 		KEY_HELP },
 468	{ SONYPI_EVENT_ZOOM_PRESSED, 		KEY_ZOOM },
 469	{ SONYPI_EVENT_THUMBPHRASE_PRESSED, 	BTN_THUMB },
 470	{ 0, 0 },
 471};
 472
 473struct sonypi_keypress {
 474	struct input_dev *dev;
 475	int key;
 476};
 477
 478static struct sonypi_device {
 479	struct pci_dev *dev;
 480	u16 irq;
 481	u16 bits;
 482	u16 ioport1;
 483	u16 ioport2;
 484	u16 region_size;
 485	u16 evtype_offset;
 486	int camera_power;
 487	int bluetooth_power;
 488	struct mutex lock;
 489	struct kfifo fifo;
 490	spinlock_t fifo_lock;
 491	wait_queue_head_t fifo_proc_list;
 492	struct fasync_struct *fifo_async;
 493	int open_count;
 494	int model;
 495	struct input_dev *input_jog_dev;
 496	struct input_dev *input_key_dev;
 497	struct work_struct input_work;
 498	struct kfifo input_fifo;
 499	spinlock_t input_fifo_lock;
 500} sonypi_device;
 501
 502#define ITERATIONS_LONG		10000
 503#define ITERATIONS_SHORT	10
 504
 505#define wait_on_command(quiet, command, iterations) { \
 506	unsigned int n = iterations; \
 507	while (--n && (command)) \
 508		udelay(1); \
 509	if (!n && (verbose || !quiet)) \
 510		printk(KERN_WARNING "sonypi command failed at %s : %s (line %d)\n", __FILE__, __func__, __LINE__); \
 511}
 512
 513#ifdef CONFIG_ACPI
 514#define SONYPI_ACPI_ACTIVE (!acpi_disabled)
 515#else
 516#define SONYPI_ACPI_ACTIVE 0
 517#endif				/* CONFIG_ACPI */
 518
 519#ifdef CONFIG_ACPI
 520static struct acpi_device *sonypi_acpi_device;
 521static int acpi_driver_registered;
 522#endif
 523
 524static int sonypi_ec_write(u8 addr, u8 value)
 525{
 526#ifdef CONFIG_ACPI
 527	if (SONYPI_ACPI_ACTIVE)
 528		return ec_write(addr, value);
 529#endif
 530	wait_on_command(1, inb_p(SONYPI_CST_IOPORT) & 3, ITERATIONS_LONG);
 531	outb_p(0x81, SONYPI_CST_IOPORT);
 532	wait_on_command(0, inb_p(SONYPI_CST_IOPORT) & 2, ITERATIONS_LONG);
 533	outb_p(addr, SONYPI_DATA_IOPORT);
 534	wait_on_command(0, inb_p(SONYPI_CST_IOPORT) & 2, ITERATIONS_LONG);
 535	outb_p(value, SONYPI_DATA_IOPORT);
 536	wait_on_command(0, inb_p(SONYPI_CST_IOPORT) & 2, ITERATIONS_LONG);
 537	return 0;
 538}
 539
 540static int sonypi_ec_read(u8 addr, u8 *value)
 541{
 542#ifdef CONFIG_ACPI
 543	if (SONYPI_ACPI_ACTIVE)
 544		return ec_read(addr, value);
 545#endif
 546	wait_on_command(1, inb_p(SONYPI_CST_IOPORT) & 3, ITERATIONS_LONG);
 547	outb_p(0x80, SONYPI_CST_IOPORT);
 548	wait_on_command(0, inb_p(SONYPI_CST_IOPORT) & 2, ITERATIONS_LONG);
 549	outb_p(addr, SONYPI_DATA_IOPORT);
 550	wait_on_command(0, inb_p(SONYPI_CST_IOPORT) & 2, ITERATIONS_LONG);
 551	*value = inb_p(SONYPI_DATA_IOPORT);
 552	return 0;
 553}
 554
 555static int ec_read16(u8 addr, u16 *value)
 556{
 557	u8 val_lb, val_hb;
 558	if (sonypi_ec_read(addr, &val_lb))
 559		return -1;
 560	if (sonypi_ec_read(addr + 1, &val_hb))
 561		return -1;
 562	*value = val_lb | (val_hb << 8);
 563	return 0;
 564}
 565
 566/* Initializes the device - this comes from the AML code in the ACPI bios */
 567static void sonypi_type1_srs(void)
 568{
 569	u32 v;
 570
 571	pci_read_config_dword(sonypi_device.dev, SONYPI_G10A, &v);
 572	v = (v & 0xFFFF0000) | ((u32) sonypi_device.ioport1);
 573	pci_write_config_dword(sonypi_device.dev, SONYPI_G10A, v);
 574
 575	pci_read_config_dword(sonypi_device.dev, SONYPI_G10A, &v);
 576	v = (v & 0xFFF0FFFF) |
 577	    (((u32) sonypi_device.ioport1 ^ sonypi_device.ioport2) << 16);
 578	pci_write_config_dword(sonypi_device.dev, SONYPI_G10A, v);
 579
 580	v = inl(SONYPI_IRQ_PORT);
 581	v &= ~(((u32) 0x3) << SONYPI_IRQ_SHIFT);
 582	v |= (((u32) sonypi_device.bits) << SONYPI_IRQ_SHIFT);
 583	outl(v, SONYPI_IRQ_PORT);
 584
 585	pci_read_config_dword(sonypi_device.dev, SONYPI_G10A, &v);
 586	v = (v & 0xFF1FFFFF) | 0x00C00000;
 587	pci_write_config_dword(sonypi_device.dev, SONYPI_G10A, v);
 588}
 589
 590static void sonypi_type2_srs(void)
 591{
 592	if (sonypi_ec_write(SONYPI_SHIB, (sonypi_device.ioport1 & 0xFF00) >> 8))
 593		printk(KERN_WARNING "ec_write failed\n");
 594	if (sonypi_ec_write(SONYPI_SLOB, sonypi_device.ioport1 & 0x00FF))
 595		printk(KERN_WARNING "ec_write failed\n");
 596	if (sonypi_ec_write(SONYPI_SIRQ, sonypi_device.bits))
 597		printk(KERN_WARNING "ec_write failed\n");
 598	udelay(10);
 599}
 600
 601static void sonypi_type3_srs(void)
 602{
 603	u16 v16;
 604	u8  v8;
 605
 606	/* This model type uses the same initialiazation of
 607	 * the embedded controller as the type2 models. */
 608	sonypi_type2_srs();
 609
 610	/* Initialization of PCI config space of the LPC interface bridge. */
 611	v16 = (sonypi_device.ioport1 & 0xFFF0) | 0x01;
 612	pci_write_config_word(sonypi_device.dev, SONYPI_TYPE3_GID2, v16);
 613	pci_read_config_byte(sonypi_device.dev, SONYPI_TYPE3_MISC, &v8);
 614	v8 = (v8 & 0xCF) | 0x10;
 615	pci_write_config_byte(sonypi_device.dev, SONYPI_TYPE3_MISC, v8);
 616}
 617
 618/* Disables the device - this comes from the AML code in the ACPI bios */
 619static void sonypi_type1_dis(void)
 620{
 621	u32 v;
 622
 623	pci_read_config_dword(sonypi_device.dev, SONYPI_G10A, &v);
 624	v = v & 0xFF3FFFFF;
 625	pci_write_config_dword(sonypi_device.dev, SONYPI_G10A, v);
 626
 627	v = inl(SONYPI_IRQ_PORT);
 628	v |= (0x3 << SONYPI_IRQ_SHIFT);
 629	outl(v, SONYPI_IRQ_PORT);
 630}
 631
 632static void sonypi_type2_dis(void)
 633{
 634	if (sonypi_ec_write(SONYPI_SHIB, 0))
 635		printk(KERN_WARNING "ec_write failed\n");
 636	if (sonypi_ec_write(SONYPI_SLOB, 0))
 637		printk(KERN_WARNING "ec_write failed\n");
 638	if (sonypi_ec_write(SONYPI_SIRQ, 0))
 639		printk(KERN_WARNING "ec_write failed\n");
 640}
 641
 642static void sonypi_type3_dis(void)
 643{
 644	sonypi_type2_dis();
 645	udelay(10);
 646	pci_write_config_word(sonypi_device.dev, SONYPI_TYPE3_GID2, 0);
 647}
 648
 649static u8 sonypi_call1(u8 dev)
 650{
 651	u8 v1, v2;
 652
 653	wait_on_command(0, inb_p(sonypi_device.ioport2) & 2, ITERATIONS_LONG);
 654	outb(dev, sonypi_device.ioport2);
 655	v1 = inb_p(sonypi_device.ioport2);
 656	v2 = inb_p(sonypi_device.ioport1);
 657	return v2;
 658}
 659
 660static u8 sonypi_call2(u8 dev, u8 fn)
 661{
 662	u8 v1;
 663
 664	wait_on_command(0, inb_p(sonypi_device.ioport2) & 2, ITERATIONS_LONG);
 665	outb(dev, sonypi_device.ioport2);
 666	wait_on_command(0, inb_p(sonypi_device.ioport2) & 2, ITERATIONS_LONG);
 667	outb(fn, sonypi_device.ioport1);
 668	v1 = inb_p(sonypi_device.ioport1);
 669	return v1;
 670}
 671
 672static u8 sonypi_call3(u8 dev, u8 fn, u8 v)
 673{
 674	u8 v1;
 675
 676	wait_on_command(0, inb_p(sonypi_device.ioport2) & 2, ITERATIONS_LONG);
 677	outb(dev, sonypi_device.ioport2);
 678	wait_on_command(0, inb_p(sonypi_device.ioport2) & 2, ITERATIONS_LONG);
 679	outb(fn, sonypi_device.ioport1);
 680	wait_on_command(0, inb_p(sonypi_device.ioport2) & 2, ITERATIONS_LONG);
 681	outb(v, sonypi_device.ioport1);
 682	v1 = inb_p(sonypi_device.ioport1);
 683	return v1;
 684}
 685
 686#if 0
 687/* Get brightness, hue etc. Unreliable... */
 688static u8 sonypi_read(u8 fn)
 689{
 690	u8 v1, v2;
 691	int n = 100;
 692
 693	while (n--) {
 694		v1 = sonypi_call2(0x8f, fn);
 695		v2 = sonypi_call2(0x8f, fn);
 696		if (v1 == v2 && v1 != 0xff)
 697			return v1;
 698	}
 699	return 0xff;
 700}
 701#endif
 702
 703/* Set brightness, hue etc */
 704static void sonypi_set(u8 fn, u8 v)
 705{
 706	wait_on_command(0, sonypi_call3(0x90, fn, v), ITERATIONS_SHORT);
 707}
 708
 709/* Tests if the camera is ready */
 710static int sonypi_camera_ready(void)
 711{
 712	u8 v;
 713
 714	v = sonypi_call2(0x8f, SONYPI_CAMERA_STATUS);
 715	return (v != 0xff && (v & SONYPI_CAMERA_STATUS_READY));
 716}
 717
 718/* Turns the camera off */
 719static void sonypi_camera_off(void)
 720{
 721	sonypi_set(SONYPI_CAMERA_PICTURE, SONYPI_CAMERA_MUTE_MASK);
 722
 723	if (!sonypi_device.camera_power)
 724		return;
 725
 726	sonypi_call2(0x91, 0);
 727	sonypi_device.camera_power = 0;
 728}
 729
 730/* Turns the camera on */
 731static void sonypi_camera_on(void)
 732{
 733	int i, j;
 734
 735	if (sonypi_device.camera_power)
 736		return;
 737
 738	for (j = 5; j > 0; j--) {
 739
 740		while (sonypi_call2(0x91, 0x1))
 741			msleep(10);
 742		sonypi_call1(0x93);
 743
 744		for (i = 400; i > 0; i--) {
 745			if (sonypi_camera_ready())
 746				break;
 747			msleep(10);
 748		}
 749		if (i)
 750			break;
 751	}
 752
 753	if (j == 0) {
 754		printk(KERN_WARNING "sonypi: failed to power on camera\n");
 755		return;
 756	}
 757
 758	sonypi_set(0x10, 0x5a);
 759	sonypi_device.camera_power = 1;
 760}
 761
 762/* sets the bluetooth subsystem power state */
 763static void sonypi_setbluetoothpower(u8 state)
 764{
 765	state = !!state;
 766
 767	if (sonypi_device.bluetooth_power == state)
 768		return;
 769
 770	sonypi_call2(0x96, state);
 771	sonypi_call1(0x82);
 772	sonypi_device.bluetooth_power = state;
 773}
 774
 775static void input_keyrelease(struct work_struct *work)
 776{
 777	struct sonypi_keypress kp;
 778
 779	while (kfifo_out_locked(&sonypi_device.input_fifo, (unsigned char *)&kp,
 780			 sizeof(kp), &sonypi_device.input_fifo_lock)
 781			== sizeof(kp)) {
 782		msleep(10);
 783		input_report_key(kp.dev, kp.key, 0);
 784		input_sync(kp.dev);
 785	}
 786}
 787
 788static void sonypi_report_input_event(u8 event)
 789{
 790	struct input_dev *jog_dev = sonypi_device.input_jog_dev;
 791	struct input_dev *key_dev = sonypi_device.input_key_dev;
 792	struct sonypi_keypress kp = { NULL };
 793	int i;
 794
 795	switch (event) {
 796	case SONYPI_EVENT_JOGDIAL_UP:
 797	case SONYPI_EVENT_JOGDIAL_UP_PRESSED:
 798		input_report_rel(jog_dev, REL_WHEEL, 1);
 799		input_sync(jog_dev);
 800		break;
 801
 802	case SONYPI_EVENT_JOGDIAL_DOWN:
 803	case SONYPI_EVENT_JOGDIAL_DOWN_PRESSED:
 804		input_report_rel(jog_dev, REL_WHEEL, -1);
 805		input_sync(jog_dev);
 806		break;
 807
 808	case SONYPI_EVENT_JOGDIAL_PRESSED:
 809		kp.key = BTN_MIDDLE;
 810		kp.dev = jog_dev;
 811		break;
 812
 813	case SONYPI_EVENT_FNKEY_RELEASED:
 814		/* Nothing, not all VAIOs generate this event */
 815		break;
 816
 817	default:
 818		for (i = 0; sonypi_inputkeys[i].sonypiev; i++)
 819			if (event == sonypi_inputkeys[i].sonypiev) {
 820				kp.dev = key_dev;
 821				kp.key = sonypi_inputkeys[i].inputev;
 822				break;
 823			}
 824		break;
 825	}
 826
 827	if (kp.dev) {
 828		input_report_key(kp.dev, kp.key, 1);
 829		input_sync(kp.dev);
 830		kfifo_in_locked(&sonypi_device.input_fifo,
 831			(unsigned char *)&kp, sizeof(kp),
 832			&sonypi_device.input_fifo_lock);
 833		schedule_work(&sonypi_device.input_work);
 834	}
 835}
 836
 837/* Interrupt handler: some event is available */
 838static irqreturn_t sonypi_irq(int irq, void *dev_id)
 839{
 840	u8 v1, v2, event = 0;
 841	int i, j;
 842
 843	v1 = inb_p(sonypi_device.ioport1);
 844	v2 = inb_p(sonypi_device.ioport1 + sonypi_device.evtype_offset);
 845
 846	for (i = 0; sonypi_eventtypes[i].model; i++) {
 847		if (sonypi_device.model != sonypi_eventtypes[i].model)
 848			continue;
 849		if ((v2 & sonypi_eventtypes[i].data) !=
 850		    sonypi_eventtypes[i].data)
 851			continue;
 852		if (!(mask & sonypi_eventtypes[i].mask))
 853			continue;
 854		for (j = 0; sonypi_eventtypes[i].events[j].event; j++) {
 855			if (v1 == sonypi_eventtypes[i].events[j].data) {
 856				event = sonypi_eventtypes[i].events[j].event;
 857				goto found;
 858			}
 859		}
 860	}
 861
 862	if (verbose)
 863		printk(KERN_WARNING
 864		       "sonypi: unknown event port1=0x%02x,port2=0x%02x\n",
 865		       v1, v2);
 866	/* We need to return IRQ_HANDLED here because there *are*
 867	 * events belonging to the sonypi device we don't know about,
 868	 * but we still don't want those to pollute the logs... */
 869	return IRQ_HANDLED;
 870
 871found:
 872	if (verbose > 1)
 873		printk(KERN_INFO
 874		       "sonypi: event port1=0x%02x,port2=0x%02x\n", v1, v2);
 875
 876	if (useinput)
 877		sonypi_report_input_event(event);
 878
 
 
 
 
 
 879	kfifo_in_locked(&sonypi_device.fifo, (unsigned char *)&event,
 880			sizeof(event), &sonypi_device.fifo_lock);
 881	kill_fasync(&sonypi_device.fifo_async, SIGIO, POLL_IN);
 882	wake_up_interruptible(&sonypi_device.fifo_proc_list);
 883
 884	return IRQ_HANDLED;
 885}
 886
 887static int sonypi_misc_fasync(int fd, struct file *filp, int on)
 888{
 889	return fasync_helper(fd, filp, on, &sonypi_device.fifo_async);
 890}
 891
 892static int sonypi_misc_release(struct inode *inode, struct file *file)
 893{
 894	mutex_lock(&sonypi_device.lock);
 895	sonypi_device.open_count--;
 896	mutex_unlock(&sonypi_device.lock);
 897	return 0;
 898}
 899
 900static int sonypi_misc_open(struct inode *inode, struct file *file)
 901{
 902	mutex_lock(&sonypi_device.lock);
 903	/* Flush input queue on first open */
 904	if (!sonypi_device.open_count)
 905		kfifo_reset(&sonypi_device.fifo);
 906	sonypi_device.open_count++;
 907	mutex_unlock(&sonypi_device.lock);
 908
 909	return 0;
 910}
 911
 912static ssize_t sonypi_misc_read(struct file *file, char __user *buf,
 913				size_t count, loff_t *pos)
 914{
 915	ssize_t ret;
 916	unsigned char c;
 917
 918	if ((kfifo_len(&sonypi_device.fifo) == 0) &&
 919	    (file->f_flags & O_NONBLOCK))
 920		return -EAGAIN;
 921
 922	ret = wait_event_interruptible(sonypi_device.fifo_proc_list,
 923				       kfifo_len(&sonypi_device.fifo) != 0);
 924	if (ret)
 925		return ret;
 926
 927	while (ret < count &&
 928	       (kfifo_out_locked(&sonypi_device.fifo, &c, sizeof(c),
 929				 &sonypi_device.fifo_lock) == sizeof(c))) {
 930		if (put_user(c, buf++))
 931			return -EFAULT;
 932		ret++;
 933	}
 934
 935	if (ret > 0) {
 936		struct inode *inode = file_inode(file);
 937		inode->i_atime = current_time(inode);
 938	}
 939
 940	return ret;
 941}
 942
 943static unsigned int sonypi_misc_poll(struct file *file, poll_table *wait)
 944{
 945	poll_wait(file, &sonypi_device.fifo_proc_list, wait);
 946	if (kfifo_len(&sonypi_device.fifo))
 947		return POLLIN | POLLRDNORM;
 948	return 0;
 949}
 950
 951static long sonypi_misc_ioctl(struct file *fp,
 952			     unsigned int cmd, unsigned long arg)
 953{
 954	long ret = 0;
 955	void __user *argp = (void __user *)arg;
 956	u8 val8;
 957	u16 val16;
 958
 959	mutex_lock(&sonypi_device.lock);
 960	switch (cmd) {
 961	case SONYPI_IOCGBRT:
 962		if (sonypi_ec_read(SONYPI_LCD_LIGHT, &val8)) {
 963			ret = -EIO;
 964			break;
 965		}
 966		if (copy_to_user(argp, &val8, sizeof(val8)))
 967			ret = -EFAULT;
 968		break;
 969	case SONYPI_IOCSBRT:
 970		if (copy_from_user(&val8, argp, sizeof(val8))) {
 971			ret = -EFAULT;
 972			break;
 973		}
 974		if (sonypi_ec_write(SONYPI_LCD_LIGHT, val8))
 975			ret = -EIO;
 976		break;
 977	case SONYPI_IOCGBAT1CAP:
 978		if (ec_read16(SONYPI_BAT1_FULL, &val16)) {
 979			ret = -EIO;
 980			break;
 981		}
 982		if (copy_to_user(argp, &val16, sizeof(val16)))
 983			ret = -EFAULT;
 984		break;
 985	case SONYPI_IOCGBAT1REM:
 986		if (ec_read16(SONYPI_BAT1_LEFT, &val16)) {
 987			ret = -EIO;
 988			break;
 989		}
 990		if (copy_to_user(argp, &val16, sizeof(val16)))
 991			ret = -EFAULT;
 992		break;
 993	case SONYPI_IOCGBAT2CAP:
 994		if (ec_read16(SONYPI_BAT2_FULL, &val16)) {
 995			ret = -EIO;
 996			break;
 997		}
 998		if (copy_to_user(argp, &val16, sizeof(val16)))
 999			ret = -EFAULT;
1000		break;
1001	case SONYPI_IOCGBAT2REM:
1002		if (ec_read16(SONYPI_BAT2_LEFT, &val16)) {
1003			ret = -EIO;
1004			break;
1005		}
1006		if (copy_to_user(argp, &val16, sizeof(val16)))
1007			ret = -EFAULT;
1008		break;
1009	case SONYPI_IOCGBATFLAGS:
1010		if (sonypi_ec_read(SONYPI_BAT_FLAGS, &val8)) {
1011			ret = -EIO;
1012			break;
1013		}
1014		val8 &= 0x07;
1015		if (copy_to_user(argp, &val8, sizeof(val8)))
1016			ret = -EFAULT;
1017		break;
1018	case SONYPI_IOCGBLUE:
1019		val8 = sonypi_device.bluetooth_power;
1020		if (copy_to_user(argp, &val8, sizeof(val8)))
1021			ret = -EFAULT;
1022		break;
1023	case SONYPI_IOCSBLUE:
1024		if (copy_from_user(&val8, argp, sizeof(val8))) {
1025			ret = -EFAULT;
1026			break;
1027		}
1028		sonypi_setbluetoothpower(val8);
1029		break;
1030	/* FAN Controls */
1031	case SONYPI_IOCGFAN:
1032		if (sonypi_ec_read(SONYPI_FAN0_STATUS, &val8)) {
1033			ret = -EIO;
1034			break;
1035		}
1036		if (copy_to_user(argp, &val8, sizeof(val8)))
1037			ret = -EFAULT;
1038		break;
1039	case SONYPI_IOCSFAN:
1040		if (copy_from_user(&val8, argp, sizeof(val8))) {
1041			ret = -EFAULT;
1042			break;
1043		}
1044		if (sonypi_ec_write(SONYPI_FAN0_STATUS, val8))
1045			ret = -EIO;
1046		break;
1047	/* GET Temperature (useful under APM) */
1048	case SONYPI_IOCGTEMP:
1049		if (sonypi_ec_read(SONYPI_TEMP_STATUS, &val8)) {
1050			ret = -EIO;
1051			break;
1052		}
1053		if (copy_to_user(argp, &val8, sizeof(val8)))
1054			ret = -EFAULT;
1055		break;
1056	default:
1057		ret = -EINVAL;
1058	}
1059	mutex_unlock(&sonypi_device.lock);
1060	return ret;
1061}
1062
1063static const struct file_operations sonypi_misc_fops = {
1064	.owner		= THIS_MODULE,
1065	.read		= sonypi_misc_read,
1066	.poll		= sonypi_misc_poll,
1067	.open		= sonypi_misc_open,
1068	.release	= sonypi_misc_release,
1069	.fasync		= sonypi_misc_fasync,
1070	.unlocked_ioctl	= sonypi_misc_ioctl,
1071	.llseek		= no_llseek,
1072};
1073
1074static struct miscdevice sonypi_misc_device = {
1075	.minor		= MISC_DYNAMIC_MINOR,
1076	.name		= "sonypi",
1077	.fops		= &sonypi_misc_fops,
1078};
1079
1080static void sonypi_enable(unsigned int camera_on)
1081{
1082	switch (sonypi_device.model) {
1083	case SONYPI_DEVICE_MODEL_TYPE1:
1084		sonypi_type1_srs();
1085		break;
1086	case SONYPI_DEVICE_MODEL_TYPE2:
1087		sonypi_type2_srs();
1088		break;
1089	case SONYPI_DEVICE_MODEL_TYPE3:
1090		sonypi_type3_srs();
1091		break;
1092	}
1093
1094	sonypi_call1(0x82);
1095	sonypi_call2(0x81, 0xff);
1096	sonypi_call1(compat ? 0x92 : 0x82);
1097
1098	/* Enable ACPI mode to get Fn key events */
1099	if (!SONYPI_ACPI_ACTIVE && fnkeyinit)
1100		outb(0xf0, 0xb2);
1101
1102	if (camera && camera_on)
1103		sonypi_camera_on();
1104}
1105
1106static int sonypi_disable(void)
1107{
1108	sonypi_call2(0x81, 0);	/* make sure we don't get any more events */
1109	if (camera)
1110		sonypi_camera_off();
1111
1112	/* disable ACPI mode */
1113	if (!SONYPI_ACPI_ACTIVE && fnkeyinit)
1114		outb(0xf1, 0xb2);
1115
1116	switch (sonypi_device.model) {
1117	case SONYPI_DEVICE_MODEL_TYPE1:
1118		sonypi_type1_dis();
1119		break;
1120	case SONYPI_DEVICE_MODEL_TYPE2:
1121		sonypi_type2_dis();
1122		break;
1123	case SONYPI_DEVICE_MODEL_TYPE3:
1124		sonypi_type3_dis();
1125		break;
1126	}
1127
1128	return 0;
1129}
1130
1131#ifdef CONFIG_ACPI
1132static int sonypi_acpi_add(struct acpi_device *device)
1133{
1134	sonypi_acpi_device = device;
1135	strcpy(acpi_device_name(device), "Sony laptop hotkeys");
1136	strcpy(acpi_device_class(device), "sony/hotkey");
1137	return 0;
1138}
1139
1140static int sonypi_acpi_remove(struct acpi_device *device)
1141{
1142	sonypi_acpi_device = NULL;
1143	return 0;
1144}
1145
1146static const struct acpi_device_id sonypi_device_ids[] = {
1147	{"SNY6001", 0},
1148	{"", 0},
1149};
1150
1151static struct acpi_driver sonypi_acpi_driver = {
1152	.name           = "sonypi",
1153	.class          = "hkey",
1154	.ids            = sonypi_device_ids,
1155	.ops            = {
1156		           .add = sonypi_acpi_add,
1157			   .remove = sonypi_acpi_remove,
1158	},
1159};
1160#endif
1161
1162static int sonypi_create_input_devices(struct platform_device *pdev)
1163{
1164	struct input_dev *jog_dev;
1165	struct input_dev *key_dev;
1166	int i;
1167	int error;
1168
1169	sonypi_device.input_jog_dev = jog_dev = input_allocate_device();
1170	if (!jog_dev)
1171		return -ENOMEM;
1172
1173	jog_dev->name = "Sony Vaio Jogdial";
1174	jog_dev->id.bustype = BUS_ISA;
1175	jog_dev->id.vendor = PCI_VENDOR_ID_SONY;
1176	jog_dev->dev.parent = &pdev->dev;
1177
1178	jog_dev->evbit[0] = BIT_MASK(EV_KEY) | BIT_MASK(EV_REL);
1179	jog_dev->keybit[BIT_WORD(BTN_MOUSE)] = BIT_MASK(BTN_MIDDLE);
1180	jog_dev->relbit[0] = BIT_MASK(REL_WHEEL);
1181
1182	sonypi_device.input_key_dev = key_dev = input_allocate_device();
1183	if (!key_dev) {
1184		error = -ENOMEM;
1185		goto err_free_jogdev;
1186	}
1187
1188	key_dev->name = "Sony Vaio Keys";
1189	key_dev->id.bustype = BUS_ISA;
1190	key_dev->id.vendor = PCI_VENDOR_ID_SONY;
1191	key_dev->dev.parent = &pdev->dev;
1192
1193	/* Initialize the Input Drivers: special keys */
1194	key_dev->evbit[0] = BIT_MASK(EV_KEY);
1195	for (i = 0; sonypi_inputkeys[i].sonypiev; i++)
1196		if (sonypi_inputkeys[i].inputev)
1197			set_bit(sonypi_inputkeys[i].inputev, key_dev->keybit);
1198
1199	error = input_register_device(jog_dev);
1200	if (error)
1201		goto err_free_keydev;
1202
1203	error = input_register_device(key_dev);
1204	if (error)
1205		goto err_unregister_jogdev;
1206
1207	return 0;
1208
1209 err_unregister_jogdev:
1210	input_unregister_device(jog_dev);
1211	/* Set to NULL so we don't free it again below */
1212	jog_dev = NULL;
1213 err_free_keydev:
1214	input_free_device(key_dev);
1215	sonypi_device.input_key_dev = NULL;
1216 err_free_jogdev:
1217	input_free_device(jog_dev);
1218	sonypi_device.input_jog_dev = NULL;
1219
1220	return error;
1221}
1222
1223static int sonypi_setup_ioports(struct sonypi_device *dev,
1224				const struct sonypi_ioport_list *ioport_list)
1225{
1226	/* try to detect if sony-laptop is being used and thus
1227	 * has already requested one of the known ioports.
1228	 * As in the deprecated check_region this is racy has we have
1229	 * multiple ioports available and one of them can be requested
1230	 * between this check and the subsequent request. Anyway, as an
1231	 * attempt to be some more user-friendly as we currently are,
1232	 * this is enough.
1233	 */
1234	const struct sonypi_ioport_list *check = ioport_list;
1235	while (check_ioport && check->port1) {
1236		if (!request_region(check->port1,
1237				   sonypi_device.region_size,
1238				   "Sony Programmable I/O Device Check")) {
1239			printk(KERN_ERR "sonypi: ioport 0x%.4x busy, using sony-laptop? "
1240					"if not use check_ioport=0\n",
1241					check->port1);
1242			return -EBUSY;
1243		}
1244		release_region(check->port1, sonypi_device.region_size);
1245		check++;
1246	}
1247
1248	while (ioport_list->port1) {
1249
1250		if (request_region(ioport_list->port1,
1251				   sonypi_device.region_size,
1252				   "Sony Programmable I/O Device")) {
1253			dev->ioport1 = ioport_list->port1;
1254			dev->ioport2 = ioport_list->port2;
1255			return 0;
1256		}
1257		ioport_list++;
1258	}
1259
1260	return -EBUSY;
1261}
1262
1263static int sonypi_setup_irq(struct sonypi_device *dev,
1264				      const struct sonypi_irq_list *irq_list)
1265{
1266	while (irq_list->irq) {
1267
1268		if (!request_irq(irq_list->irq, sonypi_irq,
1269				 IRQF_SHARED, "sonypi", sonypi_irq)) {
1270			dev->irq = irq_list->irq;
1271			dev->bits = irq_list->bits;
1272			return 0;
1273		}
1274		irq_list++;
1275	}
1276
1277	return -EBUSY;
1278}
1279
1280static void sonypi_display_info(void)
1281{
1282	printk(KERN_INFO "sonypi: detected type%d model, "
1283	       "verbose = %d, fnkeyinit = %s, camera = %s, "
1284	       "compat = %s, mask = 0x%08lx, useinput = %s, acpi = %s\n",
1285	       sonypi_device.model,
1286	       verbose,
1287	       fnkeyinit ? "on" : "off",
1288	       camera ? "on" : "off",
1289	       compat ? "on" : "off",
1290	       mask,
1291	       useinput ? "on" : "off",
1292	       SONYPI_ACPI_ACTIVE ? "on" : "off");
1293	printk(KERN_INFO "sonypi: enabled at irq=%d, port1=0x%x, port2=0x%x\n",
1294	       sonypi_device.irq,
1295	       sonypi_device.ioport1, sonypi_device.ioport2);
1296
1297	if (minor == -1)
1298		printk(KERN_INFO "sonypi: device allocated minor is %d\n",
1299		       sonypi_misc_device.minor);
1300}
1301
1302static int sonypi_probe(struct platform_device *dev)
1303{
1304	const struct sonypi_ioport_list *ioport_list;
1305	const struct sonypi_irq_list *irq_list;
1306	struct pci_dev *pcidev;
1307	int error;
1308
1309	printk(KERN_WARNING "sonypi: please try the sony-laptop module instead "
1310			"and report failures, see also "
1311			"http://www.linux.it/~malattia/wiki/index.php/Sony_drivers\n");
1312
1313	spin_lock_init(&sonypi_device.fifo_lock);
1314	error = kfifo_alloc(&sonypi_device.fifo, SONYPI_BUF_SIZE, GFP_KERNEL);
1315	if (error) {
1316		printk(KERN_ERR "sonypi: kfifo_alloc failed\n");
1317		return error;
1318	}
1319
1320	init_waitqueue_head(&sonypi_device.fifo_proc_list);
1321	mutex_init(&sonypi_device.lock);
1322	sonypi_device.bluetooth_power = -1;
1323
1324	if ((pcidev = pci_get_device(PCI_VENDOR_ID_INTEL,
1325				     PCI_DEVICE_ID_INTEL_82371AB_3, NULL)))
1326		sonypi_device.model = SONYPI_DEVICE_MODEL_TYPE1;
1327	else if ((pcidev = pci_get_device(PCI_VENDOR_ID_INTEL,
1328					  PCI_DEVICE_ID_INTEL_ICH6_1, NULL)))
1329		sonypi_device.model = SONYPI_DEVICE_MODEL_TYPE3;
1330	else if ((pcidev = pci_get_device(PCI_VENDOR_ID_INTEL,
1331					  PCI_DEVICE_ID_INTEL_ICH7_1, NULL)))
1332		sonypi_device.model = SONYPI_DEVICE_MODEL_TYPE3;
1333	else
1334		sonypi_device.model = SONYPI_DEVICE_MODEL_TYPE2;
1335
1336	if (pcidev && pci_enable_device(pcidev)) {
1337		printk(KERN_ERR "sonypi: pci_enable_device failed\n");
1338		error = -EIO;
1339		goto err_put_pcidev;
1340	}
1341
1342	sonypi_device.dev = pcidev;
1343
1344	if (sonypi_device.model == SONYPI_DEVICE_MODEL_TYPE1) {
1345		ioport_list = sonypi_type1_ioport_list;
1346		sonypi_device.region_size = SONYPI_TYPE1_REGION_SIZE;
1347		sonypi_device.evtype_offset = SONYPI_TYPE1_EVTYPE_OFFSET;
1348		irq_list = sonypi_type1_irq_list;
1349	} else if (sonypi_device.model == SONYPI_DEVICE_MODEL_TYPE2) {
1350		ioport_list = sonypi_type2_ioport_list;
1351		sonypi_device.region_size = SONYPI_TYPE2_REGION_SIZE;
1352		sonypi_device.evtype_offset = SONYPI_TYPE2_EVTYPE_OFFSET;
1353		irq_list = sonypi_type2_irq_list;
1354	} else {
1355		ioport_list = sonypi_type3_ioport_list;
1356		sonypi_device.region_size = SONYPI_TYPE3_REGION_SIZE;
1357		sonypi_device.evtype_offset = SONYPI_TYPE3_EVTYPE_OFFSET;
1358		irq_list = sonypi_type3_irq_list;
1359	}
1360
1361	error = sonypi_setup_ioports(&sonypi_device, ioport_list);
1362	if (error) {
1363		printk(KERN_ERR "sonypi: failed to request ioports\n");
1364		goto err_disable_pcidev;
1365	}
1366
1367	error = sonypi_setup_irq(&sonypi_device, irq_list);
1368	if (error) {
1369		printk(KERN_ERR "sonypi: request_irq failed\n");
1370		goto err_free_ioports;
1371	}
1372
1373	if (minor != -1)
1374		sonypi_misc_device.minor = minor;
1375	error = misc_register(&sonypi_misc_device);
1376	if (error) {
1377		printk(KERN_ERR "sonypi: misc_register failed\n");
1378		goto err_free_irq;
1379	}
1380
1381	sonypi_display_info();
1382
1383	if (useinput) {
1384
1385		error = sonypi_create_input_devices(dev);
1386		if (error) {
1387			printk(KERN_ERR
1388				"sonypi: failed to create input devices\n");
1389			goto err_miscdev_unregister;
1390		}
1391
1392		spin_lock_init(&sonypi_device.input_fifo_lock);
1393		error = kfifo_alloc(&sonypi_device.input_fifo, SONYPI_BUF_SIZE,
1394				GFP_KERNEL);
1395		if (error) {
1396			printk(KERN_ERR "sonypi: kfifo_alloc failed\n");
1397			goto err_inpdev_unregister;
1398		}
1399
1400		INIT_WORK(&sonypi_device.input_work, input_keyrelease);
1401	}
1402
1403	sonypi_enable(0);
1404
1405	return 0;
1406
1407 err_inpdev_unregister:
1408	input_unregister_device(sonypi_device.input_key_dev);
1409	input_unregister_device(sonypi_device.input_jog_dev);
1410 err_miscdev_unregister:
1411	misc_deregister(&sonypi_misc_device);
1412 err_free_irq:
1413	free_irq(sonypi_device.irq, sonypi_irq);
1414 err_free_ioports:
1415	release_region(sonypi_device.ioport1, sonypi_device.region_size);
1416 err_disable_pcidev:
1417	if (pcidev)
1418		pci_disable_device(pcidev);
1419 err_put_pcidev:
1420	pci_dev_put(pcidev);
1421	kfifo_free(&sonypi_device.fifo);
1422
1423	return error;
1424}
1425
1426static int sonypi_remove(struct platform_device *dev)
1427{
1428	sonypi_disable();
1429
1430	synchronize_irq(sonypi_device.irq);
1431	flush_work(&sonypi_device.input_work);
1432
1433	if (useinput) {
1434		input_unregister_device(sonypi_device.input_key_dev);
1435		input_unregister_device(sonypi_device.input_jog_dev);
1436		kfifo_free(&sonypi_device.input_fifo);
1437	}
1438
1439	misc_deregister(&sonypi_misc_device);
1440
1441	free_irq(sonypi_device.irq, sonypi_irq);
1442	release_region(sonypi_device.ioport1, sonypi_device.region_size);
1443
1444	if (sonypi_device.dev) {
1445		pci_disable_device(sonypi_device.dev);
1446		pci_dev_put(sonypi_device.dev);
1447	}
1448
1449	kfifo_free(&sonypi_device.fifo);
1450
1451	return 0;
1452}
1453
1454#ifdef CONFIG_PM_SLEEP
1455static int old_camera_power;
1456
1457static int sonypi_suspend(struct device *dev)
1458{
1459	old_camera_power = sonypi_device.camera_power;
1460	sonypi_disable();
1461
1462	return 0;
1463}
1464
1465static int sonypi_resume(struct device *dev)
1466{
1467	sonypi_enable(old_camera_power);
1468	return 0;
1469}
1470
1471static SIMPLE_DEV_PM_OPS(sonypi_pm, sonypi_suspend, sonypi_resume);
1472#define SONYPI_PM	(&sonypi_pm)
1473#else
1474#define SONYPI_PM	NULL
 
1475#endif
1476
1477static void sonypi_shutdown(struct platform_device *dev)
1478{
1479	sonypi_disable();
1480}
1481
1482static struct platform_driver sonypi_driver = {
1483	.driver		= {
1484		.name	= "sonypi",
1485		.pm	= SONYPI_PM,
1486	},
1487	.probe		= sonypi_probe,
1488	.remove		= sonypi_remove,
1489	.shutdown	= sonypi_shutdown,
 
 
1490};
1491
1492static struct platform_device *sonypi_platform_device;
1493
1494static struct dmi_system_id __initdata sonypi_dmi_table[] = {
1495	{
1496		.ident = "Sony Vaio",
1497		.matches = {
1498			DMI_MATCH(DMI_SYS_VENDOR, "Sony Corporation"),
1499			DMI_MATCH(DMI_PRODUCT_NAME, "PCG-"),
1500		},
1501	},
1502	{
1503		.ident = "Sony Vaio",
1504		.matches = {
1505			DMI_MATCH(DMI_SYS_VENDOR, "Sony Corporation"),
1506			DMI_MATCH(DMI_PRODUCT_NAME, "VGN-"),
1507		},
1508	},
1509	{ }
1510};
1511
1512static int __init sonypi_init(void)
1513{
1514	int error;
1515
1516	printk(KERN_INFO
1517		"sonypi: Sony Programmable I/O Controller Driver v%s.\n",
1518		SONYPI_DRIVER_VERSION);
1519
1520	if (!dmi_check_system(sonypi_dmi_table))
1521		return -ENODEV;
1522
1523	error = platform_driver_register(&sonypi_driver);
1524	if (error)
1525		return error;
1526
1527	sonypi_platform_device = platform_device_alloc("sonypi", -1);
1528	if (!sonypi_platform_device) {
1529		error = -ENOMEM;
1530		goto err_driver_unregister;
1531	}
1532
1533	error = platform_device_add(sonypi_platform_device);
1534	if (error)
1535		goto err_free_device;
1536
1537#ifdef CONFIG_ACPI
1538	if (acpi_bus_register_driver(&sonypi_acpi_driver) >= 0)
1539		acpi_driver_registered = 1;
1540#endif
1541
1542	return 0;
1543
1544 err_free_device:
1545	platform_device_put(sonypi_platform_device);
1546 err_driver_unregister:
1547	platform_driver_unregister(&sonypi_driver);
1548	return error;
1549}
1550
1551static void __exit sonypi_exit(void)
1552{
1553#ifdef CONFIG_ACPI
1554	if (acpi_driver_registered)
1555		acpi_bus_unregister_driver(&sonypi_acpi_driver);
1556#endif
1557	platform_device_unregister(sonypi_platform_device);
1558	platform_driver_unregister(&sonypi_driver);
1559	printk(KERN_INFO "sonypi: removed.\n");
1560}
1561
1562module_init(sonypi_init);
1563module_exit(sonypi_exit);