1 /*
2  * CDDL HEADER START
3  *
4  * The contents of this file are subject to the terms of the
5  * Common Development and Distribution License, Version 1.0 only
6  * (the "License").  You may not use this file except in compliance
7  * with the License.
8  *
9  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10  * or http://www.opensolaris.org/os/licensing.
11  * See the License for the specific language governing permissions
12  * and limitations under the License.
13  *
14  * When distributing Covered Code, include this CDDL HEADER in each
15  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16  * If applicable, add the following below this CDDL HEADER, with the
17  * fields enclosed by brackets "[]" replaced with your own identifying
18  * information: Portions Copyright [yyyy] [name of copyright owner]
19  *
20  * CDDL HEADER END
21  */
22 /*
23  * Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
24  * Use is subject to license terms.
25  */
26 
27 #ifndef _SYS_USB_HIDVAR_H
28 #define	_SYS_USB_HIDVAR_H
29 
30 #pragma ident	"%Z%%M%	%I%	%E% SMI"
31 
32 #ifdef	__cplusplus
33 extern "C" {
34 #endif
35 
36 #include <sys/usb/usba/usbai_private.h>
37 
38 /*
39  * HID : This header file contains the internal structures
40  * and variable definitions used in hid driver.
41  */
42 
43 /*
44  * HID USB device state management :
45  *
46  *	ONLINE-----1--->SUSPENDED----2---->ONLINE
47  *	  |
48  *	  +-----3--->DISCONNECTED----4----->ONLINE
49  *	  |
50  *	  +-----7--->POWERED DOWN----8----->POWER CHANGE---9--->ONLINE
51  *						|
52  *						+---3--->DISCONNECTED
53  *
54  *	POWERED DOWN----1--->SUSPENDED------2----->POWERED DOWN
55  *	  |		      |     ^
56  *	  |		      5     |
57  *	  |		      |     6
58  *	  |		      v     |
59  *	  +---------3----->DISCONNECTED-------4----->POWERED DOWN
60  *
61  *	1 = CPR SUSPEND
62  *	2 = CPR RESUME (with original device)
63  *	3 = Device Unplug
64  *	4 = Original Device Plugged in
65  *	5 = CPR RESUME (with device disconnected or with a wrong device)
66  *	6 = CPR SUSPEND on a disconnected device
67  *	7 = Device idles for time T & transitions to low power state
68  *	8 = Remote wakeup by device OR Application kicking off IO to device
69  *          This results in a Transistion state till PM calls the power
70  *	    entry point to raise the power level of the device
71  *	9 = Device entry point called to raise power level of the device
72  *
73  */
74 
75 
76 /* Boot protocol values for keyboard and mouse */
77 #define	KEYBOARD_PROTOCOL	0x01		/* legacy keyboard */
78 #define	MOUSE_PROTOCOL		0x02		/* legacy mouse */
79 
80 /*
81  * If the hid descriptor is not valid, the following values are
82  * used.
83  */
84 #define	USBKPSZ 		8	/* keyboard packet size */
85 #define	USBMSSZ 		3	/* mouse packet size */
86 #define	USB_KB_HID_DESCR_LENGTH 0x3f 	/* keyboard Report descr length */
87 #define	USB_MS_HID_DESCR_LENGTH 0x32 	/* mouse Report descr length */
88 
89 /*
90  * Flags for the default pipe.
91  */
92 #define	HID_DEFAULT_PIPE_BUSY	0x01
93 
94 /*
95  * Hid interrupt pipe states. Interrupt pipe
96  * can be in only one of these states :
97  *
98  *	open--1-->data_transferring--1-->open
99  *	 |
100  *	 |----2---->closed
101  *
102  *	1 = interrupt pipe callback
103  *	2 = hid_close
104  */
105 #define	HID_INTERRUPT_PIPE_CLOSED 0x00 /* Int. pipe is closed */
106 #define	HID_INTERRUPT_PIPE_OPEN	0x01 /* Int. pipe is opened */
107 
108 /* HID mctl processing return codes */
109 #define	HID_SUCCESS	0	/* mctl processed successfully */
110 #define	HID_INPROGRESS	1	/* mctl queued/deferred for execution */
111 #define	HID_ENQUEUE	2	/* mctl queued/deferred for execution */
112 #define	HID_FAILURE	-1	/* mctl processing failed */
113 
114 /* Data is being sent up */
115 #define	HID_INTERRUPT_PIPE_DATA_TRANSFERRING	0x03
116 
117 /* Attach/detach states */
118 #define	HID_LOCK_INIT		0x01	/* Initial attach state */
119 #define	HID_MINOR_NODES		0x02 	/* Set after minor node is created */
120 
121 /* HID Protocol Requests */
122 #define	SET_IDLE 		0x0a 	/* bRequest value to set idle request */
123 #define	DURATION 		(0<<8) 	/* no. of repeat reports (HID 7.2.4) */
124 #define	SET_PROTOCOL 		0x0b 	/* bRequest value for boot protocol */
125 
126 /* Hid PM scheme */
127 typedef enum {
128 	HID_PM_ACTIVITY,	/* device is power managed by idleness */
129 	HID_PM_OPEN_CLOSE,	/* device is busy on open, idle on close */
130 	HID_PM_APPLICATION	/* device is power managed by application */
131 } hid_pm_scheme_t;
132 
133 typedef struct hid_power {
134 
135 	void			*hid_state;	/* points back to hid_state */
136 
137 	int			hid_pm_busy;	/* device busy accounting */
138 
139 	hid_pm_scheme_t		hid_pm_strategy;	/* device PM */
140 
141 	uint8_t			hid_wakeup_enabled;
142 
143 	/* this is the bit mask of the power states that device has */
144 	uint8_t			hid_pwr_states;
145 
146 	/* wakeup and power transistion capabilites of an interface */
147 	uint8_t			hid_pm_capabilities;
148 
149 	/* flag to indicate if driver is about to raise power level */
150 	boolean_t		hid_raise_power;
151 
152 	/* current power level the device is in */
153 	uint8_t			hid_current_power;
154 
155 	/* mblk indicating that the device has powered up */
156 	mblk_t			*hid_pm_pwrup;
157 } hid_power_t;
158 
159 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_power_t::hid_state))
160 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_power_t::hid_pm_strategy))
161 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_power_t::hid_wakeup_enabled))
162 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_power_t::hid_pwr_states))
163 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_power_t::hid_pm_capabilities))
164 
165 typedef struct hid_state {
166 	dev_info_t		*hid_dip;	/* per-device info handle */
167 	kmutex_t		hid_mutex;	/* for general locking */
168 	int			hid_instance;	/* instance number */
169 
170 	minor_t			hid_minor;
171 	boolean_t		hid_km;		/* for virtual keyboard/mouse */
172 
173 	/* Attach/detach flags */
174 	int			hid_attach_flags;
175 
176 	/* device state flag */
177 	int			hid_dev_state;
178 
179 	/* outstanding requests on the default pipe */
180 	int			hid_default_pipe_req;
181 
182 	queue_t			*hid_rq_ptr;	/* pointer to read queue */
183 	queue_t			*hid_wq_ptr;	/* pointer to write queue */
184 
185 	hid_power_t		*hid_pm;	/* ptr to power struct */
186 
187 	usb_client_dev_data_t	*hid_dev_data;	/* ptr to usb reg struct */
188 
189 	usb_dev_descr_t		*hid_dev_descr;	/* device descriptor. */
190 
191 	/* hid driver is attached to this interface */
192 	int			hid_interfaceno;
193 
194 	usb_if_descr_t		hid_if_descr;		/* interface descr */
195 	usb_hid_descr_t		hid_hid_descr;		/* hid descriptor */
196 	usb_ep_descr_t		hid_ep_intr_descr;
197 	hidparser_handle_t	hid_report_descr;	/* report descr */
198 
199 	usb_pipe_handle_t	hid_default_pipe;	/* default pipe */
200 	usb_pipe_handle_t	hid_interrupt_pipe;	/* intr pipe handle */
201 
202 	int			hid_streams_flags;	/* see below */
203 	int			hid_packet_size;	/* data packet size */
204 
205 	/* Pipe policy for the interrupt pipe is saved here */
206 	usb_pipe_policy_t	hid_intr_pipe_policy;
207 
208 	/*
209 	 * This field is only used if the device provides polled input
210 	 * This is state information for the usba layer.
211 	 */
212 	usb_console_info_t	hid_polled_console_info;
213 
214 	/*
215 	 * This is the buffer that the raw characters are stored in.
216 	 * for polled mode.
217 	 */
218 	uchar_t			*hid_polled_raw_buf;
219 
220 	/* handle for outputting messages */
221 	usb_log_handle_t	hid_log_handle;
222 } hid_state_t;
223 
224 /* warlock directives, stable data */
225 _NOTE(MUTEX_PROTECTS_DATA(hid_state_t::hid_mutex, hid_state_t))
226 _NOTE(MUTEX_PROTECTS_DATA(hid_state_t::hid_mutex, hid_power_t))
227 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_dip))
228 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_pm))
229 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_dev_data))
230 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_instance))
231 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_km))
232 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_minor))
233 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_interrupt_pipe))
234 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_ep_intr_descr))
235 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_default_pipe))
236 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_log_handle))
237 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_if_descr))
238 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_dev_data))
239 _NOTE(DATA_READABLE_WITHOUT_LOCK(hid_state_t::hid_dev_descr))
240 _NOTE(SCHEME_PROTECTS_DATA("stable data", hid_state_t::hid_rq_ptr))
241 _NOTE(SCHEME_PROTECTS_DATA("stable data", hid_state_t::hid_wq_ptr))
242 
243 _NOTE(SCHEME_PROTECTS_DATA("stable data", usb_ep_descr))
244 
245 
246 /*
247  * The hid_polled_console_info field is a handle from usba.  The
248  * handle is used when the kernel is in the single thread mode
249  * so the field is tagged with this note.
250  */
251 _NOTE(SCHEME_PROTECTS_DATA("unique per call",
252 				hid_state_t::hid_polled_console_info))
253 
254 /*
255  * structure for argument for callback routine for async
256  * data transfer through default pipe.
257  */
258 typedef struct hid_default_pipe_argument {
259 
260 	/* Message to be sent up to the stream */
261 	struct iocblk	hid_default_pipe_arg_mctlmsg;
262 
263 	/* Pointer to hid_state structure */
264 	hid_state_t	*hid_default_pipe_arg_hidp;
265 
266 	/* Pointer to the original mblk_t received from hid_wput() */
267 	mblk_t		*hid_default_pipe_arg_mblk;
268 
269 	/* Request that caused this callback to happen */
270 	uchar_t		hid_default_pipe_arg_bRequest;
271 
272 } hid_default_pipe_arg_t;
273 
274 /*
275  * An instance of this structure is created per command down to the
276  * device.  The control callback is not executed until the call is
277  * made into usba, so there is no danger of a callback happening when
278  * the fields of the structure are being set.
279  */
280 _NOTE(SCHEME_PROTECTS_DATA("unique per call", hid_default_pipe_arg_t))
281 
282 /*
283  * An instance of this structure is created per command down to the
284  * device.  The callback is not executed until the call is
285  * made into usba, so there is no danger of a callback happening when
286  * the fields of the structure are being set.
287  */
288 
289 /* Value for hid_streams_flags */
290 #define	HID_STREAMS_OPEN	0x00000001	/* Streams are open */
291 #define	HID_STREAMS_DISMANTLING	0x00000002	/* In hid_close() */
292 
293 #define	HID_BAD_DESCR		0x01		/* Bad hid report descriptor */
294 
295 #define	HID_MINOR_NAME_LEN	20	/* Max length of minor_name string */
296 
297 /* hid_close will wait 60 secons for callbacks to be over */
298 #define	HID_CLOSE_WAIT_TIMEOUT	10
299 
300 /* define a timeout for draining requests on the default control pipe */
301 #define	HID_DEFAULT_PIPE_DRAIN_TIMEOUT	5
302 
303 /* To support PM on SUN mice of later revisions */
304 #define	HID_SUN_MOUSE_VENDOR_ID	0x0430
305 #define	HID_SUN_MOUSE_PROD_ID	0x0100
306 #define	HID_SUN_MOUSE_BCDDEVICE	0x0105	/* and later revisions */
307 
308 
309 /*
310  * Debug message Masks
311  */
312 #define	PRINT_MASK_ATTA		0x00000001
313 #define	PRINT_MASK_OPEN 	0x00000002
314 #define	PRINT_MASK_CLOSE	0x00000004
315 #define	PRINT_MASK_EVENTS	0x00000008
316 #define	PRINT_MASK_PM		0x00000010
317 #define	PRINT_MASK_ALL		0xFFFFFFFF
318 
319 /*
320  * Define states local to hid driver
321  */
322 #define	USB_DEV_HID_POWER_CHANGE 0x80
323 
324 /* define for retrying control requests */
325 #define	HID_RETRY	10
326 
327 #ifdef __cplusplus
328 }
329 #endif
330 
331 #endif	/* _SYS_USB_HIDVAR_H */
332