xref: /illumos-gate/usr/src/uts/common/io/usb/hcd/openhci/ohci_polled.c (revision f808c858fa61e7769218966759510a8b1190dfcf)
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 (the "License").
6  * You may not use this file except in compliance with the License.
7  *
8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9  * or http://www.opensolaris.org/os/licensing.
10  * See the License for the specific language governing permissions
11  * and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL HEADER in each
14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15  * If applicable, add the following below this CDDL HEADER, with the
16  * fields enclosed by brackets "[]" replaced with your own identifying
17  * information: Portions Copyright [yyyy] [name of copyright owner]
18  *
19  * CDDL HEADER END
20  */
21 /*
22  * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
23  * Use is subject to license terms.
24  */
25 #pragma ident	"%Z%%M%	%I%	%E% SMI"
26 
27 /*
28  * Open Host Controller Driver (OHCI)
29  *
30  * The USB Open Host Controller driver is a software driver which interfaces
31  * to the Universal Serial Bus layer (USBA) and the USB Open Host Controller.
32  * The interface to USB Open Host Controller is defined by the OpenHCI	Host
33  * Controller Interface.
34  *
35  * This module contains the specific ohci code used in POLLED mode and this
36  * code is in a separate file since it will never become part of ohci driver.
37  */
38 #include <sys/usb/hcd/openhci/ohcid.h>
39 #include <sys/usb/hcd/openhci/ohci_polled.h>
40 
41 /*
42  * Internal Function Prototypes
43  */
44 
45 /* Polled initialization routines */
46 static int	ohci_polled_init(
47 				usba_pipe_handle_data_t	*ph,
48 				ohci_state_t		*ohcip,
49 				usb_console_info_impl_t	*console_input_info);
50 
51 /* Polled deinitialization routines */
52 static int	ohci_polled_fini(ohci_polled_t		*ohci_polledp);
53 
54 /* Polled save state routines */
55 static void	ohci_polled_save_state(ohci_polled_t	*ohci_polledp);
56 static void	ohci_polled_stop_processing(
57 				ohci_polled_t		*ohci_polledp);
58 
59 /* Polled restore state routines */
60 static void	ohci_polled_restore_state(ohci_polled_t	*ohci_polledp);
61 static void	ohci_polled_start_processing(
62 				ohci_polled_t		*ohci_polledp);
63 
64 /* Polled read routines */
65 static ohci_td_t *ohci_polled_pickup_done_list(
66 				ohci_polled_t		*ohci_polledp,
67 				ohci_td_t		*done_head);
68 static int	ohci_polled_check_done_list(
69 				ohci_polled_t		*ohci_polledp);
70 static void	ohci_polled_create_input_list(
71 				ohci_polled_t		*ohci_polledp,
72 				ohci_td_t		*head_done_list);
73 static int	ohci_polled_process_input_list(
74 				ohci_polled_t		*ohci_polledp);
75 static int	ohci_polled_handle_normal_td(
76 				ohci_polled_t		*ohci_polledp,
77 				ohci_td_t		*td);
78 static void	ohci_polled_insert_td(ohci_state_t	*ohcip,
79 				ohci_td_t		*td);
80 static void	ohci_polled_fill_in_td(ohci_state_t	*ohcip,
81 				ohci_td_t		*td,
82 				ohci_td_t		*new_dummy,
83 				uint_t			hctd_ctrl,
84 				uint32_t		hctd_iommu_cbp,
85 				size_t			hctd_length,
86 				ohci_trans_wrapper_t	*tw);
87 static void	ohci_polled_insert_td_on_tw(
88 				ohci_state_t		*ohcip,
89 				ohci_trans_wrapper_t	*tw,
90 				ohci_td_t		*td);
91 static void	ohci_polled_handle_frame_number_overflow(
92 				ohci_state_t		*ohcip);
93 static void	ohci_polled_finish_interrupt(
94 				ohci_state_t		*ohcip,
95 				uint_t			intr);
96 /*
97  * POLLED entry points
98  *
99  * These functions are entry points into the POLLED code.
100  */
101 
102 /*
103  * ohci_hcdi_polled_input_init:
104  *
105  * This is the initialization routine for handling the USB keyboard
106  * in POLLED mode.  This routine is not called from POLLED mode, so
107  * it is OK to acquire mutexes.
108  */
109 int
110 ohci_hcdi_polled_input_init(
111 	usba_pipe_handle_data_t	*ph,
112 	uchar_t			**polled_buf,
113 	usb_console_info_impl_t	*console_input_info)
114 {
115 	ohci_polled_t		*ohci_polledp;
116 	ohci_state_t		*ohcip;
117 	int			ret;
118 
119 	ohcip = ohci_obtain_state(ph->p_usba_device->usb_root_hub_dip);
120 
121 	/*
122 	 * Grab the ohci_int_mutex so that things don't change on us
123 	 * if an interrupt comes in.
124 	 */
125 	mutex_enter(&ohcip->ohci_int_mutex);
126 
127 	ret = ohci_polled_init(ph, ohcip, console_input_info);
128 
129 	if (ret != USB_SUCCESS) {
130 
131 		/* Allow interrupts to continue */
132 		mutex_exit(&ohcip->ohci_int_mutex);
133 
134 		return (ret);
135 	}
136 
137 	ohci_polledp = (ohci_polled_t *)console_input_info->uci_private;
138 
139 	/*
140 	 * Mark the structure so that if we are using it, we don't free
141 	 * the structures if one of them is unplugged.
142 	 */
143 	ohci_polledp->ohci_polled_flags |= POLLED_INPUT_MODE;
144 
145 	/* increase the polled kbd counter for keyboard connected */
146 	ohcip->ohci_polled_kbd_count ++;
147 
148 	/*
149 	 * This is the buffer we will copy characters into. It will be
150 	 * copied into at this layer, so we need to keep track of it.
151 	 */
152 	ohci_polledp->ohci_polled_buf =
153 		(uchar_t *)kmem_zalloc(POLLED_RAW_BUF_SIZE, KM_SLEEP);
154 
155 	*polled_buf = ohci_polledp->ohci_polled_buf;
156 
157 	/*
158 	 * This is a software workaround to fix schizo hardware bug.
159 	 * Existence of "no-prom-cdma-sync"  property means consistent
160 	 * dma sync should not be done while in prom or polled mode.
161 	 */
162 	if (ddi_prop_exists(DDI_DEV_T_ANY, ohcip->ohci_dip,
163 	    DDI_PROP_NOTPROM, "no-prom-cdma-sync")) {
164 		ohci_polledp->ohci_polled_no_sync_flag = B_TRUE;
165 	}
166 
167 	/* Allow interrupts to continue */
168 	mutex_exit(&ohcip->ohci_int_mutex);
169 
170 	return (USB_SUCCESS);
171 }
172 
173 
174 /*
175  * ohci_hcdi_polled_input_fini:
176  */
177 int
178 ohci_hcdi_polled_input_fini(usb_console_info_impl_t *info)
179 {
180 	ohci_polled_t		*ohci_polledp;
181 	ohci_state_t		*ohcip;
182 	int			ret;
183 
184 	ohci_polledp = (ohci_polled_t *)info->uci_private;
185 
186 	ohcip = ohci_polledp->ohci_polled_ohcip;
187 
188 	mutex_enter(&ohcip->ohci_int_mutex);
189 
190 	/*
191 	 * Reset the POLLED_INPUT_MODE flag so that we can tell if
192 	 * this structure is in use in the ohci_polled_fini routine.
193 	 */
194 	ohci_polledp->ohci_polled_flags &= ~POLLED_INPUT_MODE;
195 
196 	/* Decrease the polled kbd counter for keyboard disconnected */
197 	ohcip->ohci_polled_kbd_count --;
198 
199 	/* Free the buffer that we copied data into */
200 	kmem_free(ohci_polledp->ohci_polled_buf, POLLED_RAW_BUF_SIZE);
201 
202 	ret = ohci_polled_fini(ohci_polledp);
203 
204 	mutex_exit(&ohcip->ohci_int_mutex);
205 
206 	return (ret);
207 }
208 
209 
210 /*
211  * ohci_hcdi_polled_input_enter:
212  *
213  * This is where we enter into POLLED mode.  This routine sets up
214  * everything so that calls to	ohci_hcdi_polled_read will return
215  * characters.
216  */
217 int
218 ohci_hcdi_polled_input_enter(usb_console_info_impl_t *info)
219 {
220 	ohci_polled_t		*ohci_polledp;
221 
222 	ohci_polledp = (ohci_polled_t *)info->uci_private;
223 	ohci_polledp->ohci_polled_entry++;
224 	/*
225 	 * If the controller is already switched over, just return
226 	 */
227 	if (ohci_polledp->ohci_polled_entry > 1) {
228 
229 		return (USB_SUCCESS);
230 	}
231 	ohci_polled_save_state(ohci_polledp);
232 
233 	ohci_polledp->ohci_polled_flags |= POLLED_INPUT_MODE_INUSE;
234 
235 	return (USB_SUCCESS);
236 }
237 
238 
239 /*
240  * ohci_hcdi_polled_input_exit:
241  *
242  * This is where we exit POLLED mode. This routine restores
243  * everything that is needed to continue operation.
244  */
245 int
246 ohci_hcdi_polled_input_exit(usb_console_info_impl_t *info)
247 {
248 	ohci_polled_t		*ohci_polledp;
249 
250 	ohci_polledp = (ohci_polled_t *)info->uci_private;
251 
252 	ohci_polledp->ohci_polled_entry--;
253 
254 	/*
255 	 * If there are still outstanding "enters", just return
256 	 */
257 	if (ohci_polledp->ohci_polled_entry > 0)
258 		return (USB_SUCCESS);
259 
260 	ohci_polledp->ohci_polled_flags &= ~POLLED_INPUT_MODE_INUSE;
261 	ohci_polled_restore_state(ohci_polledp);
262 
263 	return (USB_SUCCESS);
264 }
265 
266 
267 /*
268  * ohci_hcdi_polled_read:
269  *
270  * Get a key character
271  */
272 int
273 ohci_hcdi_polled_read(
274 	usb_console_info_impl_t	*info,
275 	uint_t			*num_characters)
276 {
277 	ohci_state_t		*ohcip;
278 	ohci_polled_t		*ohci_polledp;
279 	uint_t			intr;
280 	ohci_polledp = (ohci_polled_t *)info->uci_private;
281 
282 	ohcip = ohci_polledp->ohci_polled_ohcip;
283 
284 #ifndef lint
285 	_NOTE(NO_COMPETING_THREADS_NOW);
286 #endif
287 	*num_characters = 0;
288 	intr = (Get_OpReg(hcr_intr_status) & Get_OpReg(hcr_intr_enable));
289 
290 	/*
291 	 * Check whether any Frame Number Overflow interrupt is pending
292 	 * and if it is pending, process this interrupt.
293 	 */
294 
295 	if (intr & HCR_INTR_FNO) {
296 		ohci_handle_frame_number_overflow(ohcip);
297 
298 		/* Acknowledge the FNO interrupt */
299 		ohci_polled_finish_interrupt(ohcip, HCR_INTR_FNO);
300 	}
301 	if (intr & HCR_INTR_WDH) {
302 
303 		/* Check to see if there are any TD's for this input device */
304 		if (ohci_polled_check_done_list(ohci_polledp) == USB_SUCCESS) {
305 
306 			/* Process any TD's on the input done list */
307 			*num_characters =
308 			    ohci_polled_process_input_list(ohci_polledp);
309 		}
310 
311 		/*
312 		 * To make sure after we get the done list from DoneHead,
313 		 * every input device get his own TD's in the
314 		 * ohci_polled_done_list and then clear the interrupt status.
315 		 */
316 		if (ohcip->ohci_polled_done_list == NULL) {
317 
318 			/* Acknowledge the WDH interrupt */
319 			ohci_polled_finish_interrupt(ohcip, HCR_INTR_WDH);
320 		}
321 	}
322 #ifndef lint
323 	_NOTE(COMPETING_THREADS_NOW);
324 #endif
325 
326 	return (USB_SUCCESS);
327 }
328 
329 
330 /*
331  * Internal Functions
332  */
333 
334 /*
335  * Polled initialization routines
336  */
337 
338 
339 /*
340  * ohci_polled_init:
341  *
342  * Initialize generic information Uthat is needed to provide USB/POLLED
343  * support.
344  */
345 static int
346 ohci_polled_init(
347 	usba_pipe_handle_data_t	*ph,
348 	ohci_state_t		*ohcip,
349 	usb_console_info_impl_t	*console_info)
350 {
351 	ohci_polled_t		*ohci_polledp;
352 	ohci_pipe_private_t	*pp;
353 
354 	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
355 
356 	/*
357 	 * We have already initialized this structure. If the structure
358 	 * has already been initialized, then we don't need to redo it.
359 	 */
360 	if (console_info->uci_private) {
361 
362 		return (USB_SUCCESS);
363 	}
364 
365 	/* Allocate and intitialize a state structure */
366 	ohci_polledp = (ohci_polled_t *)
367 	    kmem_zalloc(sizeof (ohci_polled_t), KM_SLEEP);
368 
369 	console_info->uci_private = (usb_console_info_private_t)ohci_polledp;
370 
371 	/*
372 	 * Store away the ohcip so that we can get to it when we are in
373 	 * POLLED mode. We don't want to have to call ohci_obtain_state
374 	 * every time we want to access this structure. Also save ohci
375 	 * polled state information in ohcip.
376 	 */
377 	ohci_polledp->ohci_polled_ohcip = ohcip;
378 
379 	/*
380 	 * Save usb device and endpoint number information from the usb
381 	 * pipe handle.
382 	 */
383 	mutex_enter(&ph->p_mutex);
384 	ohci_polledp->ohci_polled_usb_dev = ph->p_usba_device;
385 	ohci_polledp->ohci_polled_ep_addr = ph->p_ep.bEndpointAddress;
386 	mutex_exit(&ph->p_mutex);
387 
388 	/*
389 	 * Allocate memory to make duplicate of original usb pipe handle.
390 	 */
391 	ohci_polledp->ohci_polled_input_pipe_handle =
392 	    kmem_zalloc(sizeof (usba_pipe_handle_data_t), KM_SLEEP);
393 
394 	/*
395 	 * Copy the USB handle into the new pipe handle. Also
396 	 * create new lock for the new pipe handle.
397 	 */
398 	bcopy((void *)ph,
399 	    (void *)ohci_polledp->ohci_polled_input_pipe_handle,
400 	    sizeof (usba_pipe_handle_data_t));
401 
402 	/*
403 	 * uint64_t typecast to make sure amd64 can compile
404 	 */
405 	mutex_init(&ohci_polledp->ohci_polled_input_pipe_handle->p_mutex,
406 	    NULL, MUTEX_DRIVER, DDI_INTR_PRI(ohcip->ohci_intr_pri));
407 
408 	/* Create a new ohci pipe private structure */
409 	pp = (ohci_pipe_private_t *)
410 	    kmem_zalloc(sizeof (ohci_pipe_private_t), KM_SLEEP);
411 
412 	/*
413 	 * Store the pointer in the pipe handle. This structure was also
414 	 * just allocated.
415 	 */
416 	mutex_enter(&ohci_polledp->ohci_polled_input_pipe_handle->p_mutex);
417 
418 	ohci_polledp->ohci_polled_input_pipe_handle->
419 	    p_hcd_private = (usb_opaque_t)pp;
420 
421 	mutex_exit(&ohci_polledp->ohci_polled_input_pipe_handle->p_mutex);
422 
423 	/*
424 	 * Store a pointer to the pipe handle. This structure was  just
425 	 * allocated and it is not in use yet.	The locking is there to
426 	 * satisfy warlock.
427 	 */
428 	mutex_enter(&ph->p_mutex);
429 
430 	bcopy(&ph->p_policy, &pp->pp_policy, sizeof (usb_pipe_policy_t));
431 
432 	mutex_exit(&ph->p_mutex);
433 
434 	pp->pp_pipe_handle = ohci_polledp->ohci_polled_input_pipe_handle;
435 
436 	/*
437 	 * Allocate a dummy for the interrupt table. This dummy will be
438 	 * put into the action when we	switch interrupt  tables during
439 	 * ohci_hcdi_polled_enter. Dummy is placed on the unused lattice
440 	 * entries. When the ED is allocated we will replace dummy ED by
441 	 * valid interrupt ED in one or more locations in the interrupt
442 	 * lattice depending on the requested polling interval. Also we
443 	 * will hang a dummy TD to the ED & dummy TD is used to indicate
444 	 * the end of the TD chain.
445 	 */
446 	ohci_polledp->ohci_polled_dummy_ed = ohci_alloc_hc_ed(ohcip, NULL);
447 
448 	if (ohci_polledp->ohci_polled_dummy_ed == NULL) {
449 
450 		return (USB_NO_RESOURCES);
451 	}
452 
453 	/*
454 	 * Allocate the interrupt endpoint. This ED will be inserted in
455 	 * to the lattice chain for the  keyboard device. This endpoint
456 	 * will have the TDs hanging off of it for the processing.
457 	 */
458 	ohci_polledp->ohci_polled_ed = ohci_alloc_hc_ed(ohcip,
459 	    ohci_polledp->ohci_polled_input_pipe_handle);
460 
461 	if (ohci_polledp->ohci_polled_ed == NULL) {
462 
463 		return (USB_NO_RESOURCES);
464 	}
465 
466 	/* Set the state of pipe as idle */
467 	pp->pp_state = OHCI_PIPE_STATE_IDLE;
468 
469 	/* Insert the endpoint onto the pipe handle */
470 	pp->pp_ept = ohci_polledp->ohci_polled_ed;
471 
472 	/*
473 	 * Set soft interrupt handler flag in the normal mode usb
474 	 * pipe handle.
475 	 */
476 	mutex_enter(&ph->p_mutex);
477 	ph->p_spec_flag |= USBA_PH_FLAG_USE_SOFT_INTR;
478 	mutex_exit(&ph->p_mutex);
479 
480 	/*
481 	 * Insert a Interrupt polling request onto the endpoint.
482 	 *
483 	 * There will now be two TDs on the ED, one is the dummy TD that
484 	 * was allocated above in the  ohci_alloc_hc_ed and this new one.
485 	 */
486 	if ((ohci_start_periodic_pipe_polling(ohcip,
487 	    ohci_polledp->ohci_polled_input_pipe_handle,
488 	    NULL, USB_FLAGS_SLEEP)) != USB_SUCCESS) {
489 
490 		return (USB_NO_RESOURCES);
491 	}
492 
493 	return (USB_SUCCESS);
494 }
495 
496 
497 /*
498  * Polled deinitialization routines
499  */
500 
501 
502 /*
503  * ohci_polled_fini:
504  */
505 static int
506 ohci_polled_fini(ohci_polled_t	*ohci_polledp)
507 {
508 	ohci_state_t		*ohcip = ohci_polledp->ohci_polled_ohcip;
509 	ohci_pipe_private_t	*pp;
510 	ohci_td_t		*curr_td, *next_td;
511 	ohci_trans_wrapper_t	*curr_tw, *next_tw;
512 	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
513 
514 	/*
515 	 * If the structure is already in use, then don't free it.
516 	 */
517 	if (ohci_polledp->ohci_polled_flags & POLLED_INPUT_MODE) {
518 
519 		return (USB_SUCCESS);
520 	}
521 
522 	pp = (ohci_pipe_private_t *)
523 	    ohci_polledp->ohci_polled_input_pipe_handle->p_hcd_private;
524 
525 	/*
526 	 * Deallocate all the pre-allocated interrupt requests
527 	 */
528 	ohci_handle_outstanding_requests(ohcip, pp);
529 
530 	/*
531 	 * Traverse the list of TD's on this endpoint and these TD's
532 	 * have outstanding transfer requests. Since list processing
533 	 * is stopped, these TDs can be deallocated.
534 	 */
535 	ohci_traverse_tds(ohcip, pp->pp_pipe_handle);
536 
537 	/*
538 	 * For each transfer wrapper on this pipe, free the TD and
539 	 * free the TW.  We don't free the last TD in the chain
540 	 * because it will be freed by ohci_deallocate_ed.  All TD's
541 	 * on this TW are also on the end point associated with this
542 	 * pipe.
543 	 */
544 	next_tw = pp->pp_tw_head;
545 
546 	while (next_tw) {
547 		next_td = (ohci_td_t *)next_tw->tw_hctd_head;
548 
549 		/*
550 		 * Walk through each TD for this transfer
551 		 * wrapper and free that TD.
552 		 */
553 		while (next_td) {
554 			curr_td = next_td;
555 
556 			next_td = ohci_td_iommu_to_cpu(ohcip,
557 			    Get_TD(next_td->hctd_tw_next_td));
558 
559 			ohci_deallocate_td(ohcip, curr_td);
560 		}
561 
562 		curr_tw = next_tw;
563 		next_tw = curr_tw->tw_next;
564 
565 		/* Free the transfer wrapper */
566 		ohci_deallocate_tw_resources(ohcip, pp, curr_tw);
567 	}
568 
569 	/*
570 	 * Deallocate the endpoint descriptors that we allocated
571 	 * with ohci_alloc_hc_ed.
572 	 */
573 	if (ohci_polledp->ohci_polled_dummy_ed) {
574 		ohci_deallocate_ed(ohcip, ohci_polledp->ohci_polled_dummy_ed);
575 	}
576 
577 	if (ohci_polledp->ohci_polled_ed) {
578 		ohci_deallocate_ed(ohcip, ohci_polledp->ohci_polled_ed);
579 	}
580 
581 	mutex_destroy(&ohci_polledp->ohci_polled_input_pipe_handle->p_mutex);
582 
583 	/*
584 	 * Destroy everything about the pipe that we allocated in
585 	 * ohci_polled_duplicate_pipe_handle
586 	 */
587 	kmem_free(pp, sizeof (ohci_pipe_private_t));
588 
589 	kmem_free(ohci_polledp->ohci_polled_input_pipe_handle,
590 	    sizeof (usba_pipe_handle_data_t));
591 
592 	/*
593 	 * We use this field to determine if a TD is for input or not,
594 	 * so NULL the pointer so we don't check deallocated data.
595 	 */
596 	ohci_polledp->ohci_polled_input_pipe_handle = NULL;
597 
598 	/*
599 	 * Finally, free off the structure that we use to keep track
600 	 * of all this.
601 	 */
602 	kmem_free(ohci_polledp, sizeof (ohci_polled_t));
603 
604 	return (USB_SUCCESS);
605 }
606 
607 
608 /*
609  * Polled save state routines
610  */
611 
612 
613 /*
614  * ohci_polled_save_state:
615  */
616 static void
617 ohci_polled_save_state(ohci_polled_t	*ohci_polledp)
618 {
619 	ohci_state_t		*ohcip;
620 	int			i;
621 	uint_t			polled_toggle;
622 	uint_t			real_toggle;
623 	ohci_pipe_private_t	*pp = NULL;	/* Normal mode Pipe */
624 	ohci_pipe_private_t	*polled_pp;	/* Polled mode Pipe */
625 	usba_pipe_handle_data_t	*ph;
626 	uint8_t			ep_addr;
627 	ohci_save_intr_sts_t	*ohci_intr_sts;
628 	ohci_regs_t		*ohci_polled_regsp;
629 	ohci_td_t		*td, *prev_td;
630 	ohci_td_t		*done_head, **done_list;
631 
632 #ifndef lint
633 	_NOTE(NO_COMPETING_THREADS_NOW);
634 #endif
635 
636 	/*
637 	 * If either of these two flags are set, then we have already
638 	 * saved off the state information and setup the controller.
639 	 */
640 	if (ohci_polledp->ohci_polled_flags & POLLED_INPUT_MODE_INUSE) {
641 #ifndef lint
642 		_NOTE(COMPETING_THREADS_NOW);
643 #endif
644 		return;
645 	}
646 
647 	ohcip = ohci_polledp->ohci_polled_ohcip;
648 
649 	/*
650 	 * Check if the number of keyboard reach the max number we can
651 	 * support in polled mode
652 	 */
653 	if (++ ohcip->ohci_polled_enter_count > MAX_NUM_FOR_KEYBOARD) {
654 #ifndef lint
655 		_NOTE(COMPETING_THREADS_NOW);
656 #endif
657 		return;
658 	}
659 	/* Get the endpoint addr. */
660 	ep_addr = ohci_polledp->ohci_polled_ep_addr;
661 
662 	/* Get the normal mode usb pipe handle */
663 	ph = usba_hcdi_get_ph_data(ohci_polledp->ohci_polled_usb_dev, ep_addr);
664 	ohci_intr_sts = &ohcip->ohci_save_intr_sts;
665 	ohci_polled_regsp = &ohcip->ohci_polled_save_regs;
666 
667 	/*
668 	 * Only the first enter keyboard entry disable the interrupt, save the
669 	 * information of normal mode, stop the processing, initialize the
670 	 * frame list table.
671 	 */
672 	if (ohcip->ohci_polled_enter_count == 1) {
673 		/*
674 		 * Prevent the ohci interrupt handler from handling interrupt.
675 		 * We will turn off interrupts. This  keeps us from generating
676 		 * a hardware interrupt.This is the useful for testing because
677 		 * in POLLED  mode we can't get interrupts anyway. We can test
678 		 * this code by shutting off hardware interrupt generation and
679 		 * polling  for the interrupts.
680 		 */
681 		Set_OpReg(hcr_intr_disable, HCR_INTR_MIE);
682 		/*
683 		 * Save the current normal mode ohci registers	and later this
684 		 * saved register copy is used to replace some of required ohci
685 		 * registers before switching from polled mode to normal mode.
686 		 */
687 		bzero((void *)ohci_polled_regsp, sizeof (ohci_regs_t));
688 
689 		ohci_polled_regsp->hcr_control = Get_OpReg(hcr_control);
690 		ohci_polled_regsp->hcr_cmd_status = Get_OpReg(hcr_cmd_status);
691 		ohci_polled_regsp->hcr_intr_enable = Get_OpReg(hcr_intr_enable);
692 		ohci_polled_regsp->hcr_HCCA = Get_OpReg(hcr_HCCA);
693 		ohci_polled_regsp->hcr_done_head = Get_OpReg(hcr_done_head);
694 		ohci_polled_regsp->hcr_bulk_head = Get_OpReg(hcr_bulk_head);
695 		ohci_polled_regsp->hcr_ctrl_head = Get_OpReg(hcr_ctrl_head);
696 
697 		/*
698 		 * The functionality &	importance of critical code section in
699 		 * the normal mode ohci interrupt handler and its usage in the
700 		 * polled mode is explained below.
701 		 *
702 		 * (a) Normal mode:
703 		 *
704 		 *	- Set the flag indicating that processing critical code
705 		 *	  in ohci interrupt handler.
706 		 *
707 		 *	- Process the missed ohci interrupts by copying missed
708 		 *	  interrupt events & done head list fields information
709 		 *	  to the critical interrupt events & done list fields.
710 		 *
711 		 *	- Reset the missed ohci interrupt events and done head
712 		 *	  list fields so that the new missed  interrupt events
713 		 *	  and done head list information can be saved.
714 		 *
715 		 *	- All above steps will be executed within the critical
716 		 *	  section of the  interrupt handler.  Then ohci missed
717 		 *	  interrupt handler will be called to service the ohci
718 		 *	  missed interrupts.
719 		 *
720 		 * (b) Polled mode:
721 		 *
722 		 *	- On entering the polled code, checks for the critical
723 		 *	  section code execution within normal	mode interrupt
724 		 *	  handler.
725 		 *
726 		 *	- If critical section code is  executing in the normal
727 		 *	  mode ohci interrupt handler & if copying of the ohci
728 		 *	  missed interrupt events and done head list fields to
729 		 *	  the critical fields is finished then, save the  "any
730 		 *	  missed interrupt events and done head list"  because
731 		 *	  of current polled mode switch into "critical	missed
732 		 *	  interrupt events & done list fields" instead	actual
733 		 *	  missed events and done list fields.
734 		 *
735 		 *	- Otherwise save "any missed interrupt events and done
736 		 *	  list" because of this  current polled mode switch in
737 		 *	  the actual missed  interrupt events & done head list
738 		 *	  fields.
739 		 */
740 
741 		/*
742 		 * Check and save the pending SOF interrupt  condition for the
743 		 * ohci normal mode. This information will be  saved either in
744 		 * the critical missed event fields or in actual  missed event
745 		 * fields depending on the whether the critical code section's
746 		 * execution flag was set or not when switched to  polled mode
747 		 * from normal mode.
748 		 */
749 		if ((ohci_intr_sts->ohci_intr_flag & OHCI_INTR_CRITICAL) &&
750 		    (ohci_intr_sts->ohci_critical_intr_sts != 0)) {
751 
752 			ohci_intr_sts->ohci_critical_intr_sts |=
753 			    ((Get_OpReg(hcr_intr_status) &
754 			    Get_OpReg(hcr_intr_enable)) & HCR_INTR_SOF);
755 		} else {
756 			ohci_intr_sts->ohci_missed_intr_sts |=
757 			    ((Get_OpReg(hcr_intr_status) &
758 			    Get_OpReg(hcr_intr_enable)) & HCR_INTR_SOF);
759 		}
760 		ohci_polled_stop_processing(ohci_polledp);
761 
762 		/* Process any missed Frame Number Overflow (FNO) interrupt */
763 		ohci_polled_handle_frame_number_overflow(ohcip);
764 
765 		/*
766 		 * By this time all list processing has been stopped.Now check
767 		 * and save the information about the pending HCCA done  list,
768 		 * done head ohci register and WDH bit in the interrupt status
769 		 * register. This information will be saved either in critical
770 		 * missed event fields or in actual missed event fields depend
771 		 * on the whether the  critical code section's	execution flag
772 		 * was set or not when switched to polled mode from the normal
773 		 * mode.
774 		 */
775 
776 		/* Read and Save the HCCA DoneHead value */
777 		done_head = (ohci_td_t *)(uintptr_t)(Get_HCCA(
778 		    ohcip->ohci_hccap->HccaDoneHead) & HCCA_DONE_HEAD_MASK);
779 
780 		if ((done_head) &&
781 		    (done_head != ohci_intr_sts->ohci_curr_done_lst)) {
782 
783 			if ((ohci_intr_sts->ohci_intr_flag &
784 			    OHCI_INTR_CRITICAL) &&
785 			    ((ohci_intr_sts->ohci_critical_done_lst) ||
786 			    (ohci_intr_sts->ohci_missed_done_lst == NULL))) {
787 
788 				done_list =
789 				    &ohci_intr_sts->ohci_critical_done_lst;
790 				ohci_intr_sts->ohci_critical_intr_sts |=
791 				    HCR_INTR_WDH;
792 			} else {
793 				done_list =
794 				    &ohci_intr_sts->ohci_missed_done_lst;
795 				ohci_intr_sts->ohci_missed_intr_sts |=
796 				    HCR_INTR_WDH;
797 			}
798 
799 			if (*done_list) {
800 				td = (ohci_td_t *)
801 				    ohci_td_iommu_to_cpu(ohcip,
802 				    (uintptr_t)done_head);
803 
804 				while (td) {
805 					prev_td = td;
806 					td = ohci_td_iommu_to_cpu(ohcip,
807 					    Get_TD(td->hctd_next_td));
808 				}
809 
810 				Set_TD(prev_td->hctd_next_td, *done_list);
811 
812 				*done_list = done_head;
813 			} else {
814 				*done_list = (ohci_td_t *)done_head;
815 			}
816 		}
817 
818 		/*
819 		 * Save the latest hcr_done_head ohci register value,  so that
820 		 * this value can be replaced  when exit from the POLLED mode.
821 		 */
822 		ohci_polled_regsp->hcr_done_head = Get_OpReg(hcr_done_head);
823 		/*
824 		 * Reset the HCCA done head and ohci done head register.
825 		 */
826 		Set_HCCA(ohcip->ohci_hccap->HccaDoneHead, NULL);
827 		Set_OpReg(hcr_done_head, (uint32_t)0x0);
828 
829 		/*
830 		 * Clear the  WriteDoneHead interrupt bit in the ohci interrupt
831 		 * status register.
832 		 */
833 		Set_OpReg(hcr_intr_status, HCR_INTR_WDH);
834 
835 		/*
836 		 * Save the current interrupt lattice and  replace this lattice
837 		 * with an lattice used in POLLED mode. We will restore lattice
838 		 * back when we exit from the POLLED mode.
839 		 */
840 		for (i = 0; i < NUM_INTR_ED_LISTS; i++) {
841 			ohcip->ohci_polled_save_IntTble[i] =
842 			    (ohci_ed_t *)(uintptr_t)Get_HCCA(
843 			    ohcip->ohci_hccap->HccaIntTble[i]);
844 		}
845 		/*
846 		 * Fill in the lattice with dummy EDs. These EDs are used so the
847 		 * controller can tell that it is at the end of the ED list.
848 		 */
849 		for (i = 0; i < NUM_INTR_ED_LISTS; i++) {
850 			Set_HCCA(ohcip->ohci_hccap->HccaIntTble[i],
851 			    ohci_ed_cpu_to_iommu(ohcip,
852 			    ohci_polledp->ohci_polled_dummy_ed));
853 		}
854 	}
855 	/* Get the polled mode ohci pipe private structure */
856 	polled_pp = (ohci_pipe_private_t *)
857 	    ohci_polledp->ohci_polled_input_pipe_handle->p_hcd_private;
858 
859 	/*
860 	 * Before replacing the lattice, adjust the data togggle on the
861 	 * on the ohci's interrupt ed
862 	 */
863 	polled_toggle = (Get_ED(polled_pp->pp_ept->hced_headp) &
864 					HC_EPT_Carry) ? DATA1:DATA0;
865 
866 	/*
867 	 * If normal mode interrupt pipe endpoint is active, get the data
868 	 * toggle from the this interrupt endpoint through the corresponding
869 	 * interrupt pipe handle. Else get the data toggle information from
870 	 * the usb device structure and this information is saved during the
871 	 * normal mode interrupt pipe close. Use this data toggle information
872 	 * to fix the data toggle of polled mode interrupt endpoint.
873 	 */
874 	if (ph) {
875 		/* Get the normal mode ohci pipe private structure */
876 		pp = (ohci_pipe_private_t *)ph->p_hcd_private;
877 
878 		real_toggle = (Get_ED(pp->pp_ept->hced_headp) &
879 		    HC_EPT_Carry) ? DATA1:DATA0;
880 	} else {
881 		real_toggle = usba_hcdi_get_data_toggle(
882 		    ohci_polledp->ohci_polled_usb_dev, ep_addr);
883 	}
884 
885 	if (polled_toggle != real_toggle) {
886 		if (real_toggle == DATA0) {
887 			Set_ED(polled_pp->pp_ept->hced_headp,
888 			    Get_ED(polled_pp->pp_ept->hced_headp) &
889 			    ~HC_EPT_Carry);
890 		} else {
891 			Set_ED(polled_pp->pp_ept->hced_headp,
892 			    Get_ED(polled_pp->pp_ept->hced_headp) |
893 			    HC_EPT_Carry);
894 		}
895 	}
896 
897 	/*
898 	 * Check whether Halt bit is set in the ED and if so  clear the
899 	 * halt bit.
900 	 */
901 	if (polled_pp->pp_ept->hced_headp & HC_EPT_Halt) {
902 
903 		/* Clear the halt bit */
904 		Set_ED(polled_pp->pp_ept->hced_headp,
905 		    (Get_ED(polled_pp->pp_ept->hced_headp) & ~HC_EPT_Halt));
906 	}
907 
908 	/*
909 	 * Now, add the endpoint to the lattice that we will  hang  our
910 	 * TD's off of.  We need to poll this device at  every 8 ms and
911 	 * hence add this ED needs 4 entries in interrupt lattice.
912 	 */
913 	for (i = (ohcip->ohci_polled_enter_count -1); i < NUM_INTR_ED_LISTS;
914 		i = i + MIN_LOW_SPEED_POLL_INTERVAL) {
915 		Set_HCCA(ohcip->ohci_hccap->HccaIntTble[i],
916 		    ohci_ed_cpu_to_iommu(ohcip,
917 		    ohci_polledp->ohci_polled_ed));
918 	}
919 	/*
920 	 * Only the first enter keyboard entry clear the contents of
921 	 * periodic ED register and enable the WDH interrupt and
922 	 * start process the periodic list.
923 	 */
924 	if (ohcip->ohci_polled_enter_count == 1) {
925 		/*
926 		 * Clear the contents of current ohci periodic ED register that
927 		 * is physical address of current Isochronous or Interrupt ED.
928 		 */
929 
930 		Set_OpReg(hcr_periodic_curr, (uint32_t)0x0);
931 
932 		/* Make sure WriteDoneHead interrupt is enabled */
933 		Set_OpReg(hcr_intr_enable, HCR_INTR_WDH);
934 
935 		/*
936 		 * Enable the periodic list. We will now start processing EDs &
937 		 * TDs again.
938 		 */
939 		Set_OpReg(hcr_control,
940 		    (Get_OpReg(hcr_control) | HCR_CONTROL_PLE));
941 	}
942 #ifndef lint
943 	_NOTE(COMPETING_THREADS_NOW);
944 #endif
945 }
946 
947 
948 /*
949  * ohci_polled_stop_processing:
950  */
951 static void
952 ohci_polled_stop_processing(ohci_polled_t	*ohci_polledp)
953 {
954 	ohci_state_t		*ohcip;
955 	uint_t			count;
956 	ohci_regs_t		*ohci_polled_regsp;
957 
958 	ohcip = ohci_polledp->ohci_polled_ohcip;
959 	ohci_polled_regsp = &ohcip->ohci_polled_save_regs;
960 
961 	/*
962 	 * Turn off all list processing. This will take place starting
963 	 * at the next frame.
964 	 */
965 	Set_OpReg(hcr_control,
966 	    (ohci_polled_regsp->hcr_control) & ~(HCR_CONTROL_CLE|
967 	    HCR_CONTROL_PLE| HCR_CONTROL_BLE|HCR_CONTROL_IE));
968 
969 	/*
970 	 * Make sure that the  SOF interrupt bit is cleared in the ohci
971 	 * interrupt status register.
972 	 */
973 	Set_OpReg(hcr_intr_status, HCR_INTR_SOF);
974 
975 	/* Enable SOF interrupt */
976 	Set_OpReg(hcr_intr_enable, HCR_INTR_SOF);
977 
978 	/*
979 	 * According to  OHCI Specification,  we have to wait for eight
980 	 * start of frames to make sure that the Host Controller writes
981 	 * contents of done head register to done head filed of HCCA.
982 	 */
983 	for (count = 0; count <= DONE_QUEUE_INTR_COUNTER; count++) {
984 		while (!((Get_OpReg(hcr_intr_status)) & HCR_INTR_SOF)) {
985 			continue;
986 		}
987 
988 		/* Acknowledge the SOF interrupt */
989 		ohci_polled_finish_interrupt(ohcip, HCR_INTR_SOF);
990 	}
991 
992 	Set_OpReg(hcr_intr_disable, HCR_INTR_SOF);
993 }
994 
995 
996 /*
997  * Polled restore state routines
998  */
999 
1000 /*
1001  * ohci_polled_restore_state:
1002  */
1003 static void
1004 ohci_polled_restore_state(ohci_polled_t	*ohci_polledp)
1005 {
1006 	ohci_state_t		*ohcip;
1007 	int			i;
1008 	uint_t			polled_toggle;
1009 	uint_t			real_toggle;
1010 	ohci_pipe_private_t	*pp = NULL;	/* Normal mode Pipe */
1011 	ohci_pipe_private_t	*polled_pp;	/* Polled mode Pipe */
1012 	ohci_td_t		*td;
1013 	ohci_td_t		*next_td;	/* TD pointers */
1014 	uint_t			count;
1015 	ohci_save_intr_sts_t	*ohci_intr_sts;
1016 	ohci_regs_t		*ohci_polled_regsp;
1017 	uint32_t		mask;
1018 	usba_pipe_handle_data_t	*ph;
1019 	uint8_t			ep_addr;
1020 
1021 #ifndef lint
1022 	_NOTE(NO_COMPETING_THREADS_NOW);
1023 #endif
1024 
1025 	/*
1026 	 * If this flag is set, then we are still using this structure,
1027 	 * so don't restore any controller state information yet.
1028 	 */
1029 	if (ohci_polledp->ohci_polled_flags & POLLED_INPUT_MODE_INUSE) {
1030 
1031 #ifndef lint
1032 		_NOTE(COMPETING_THREADS_NOW);
1033 #endif
1034 
1035 		return;
1036 	}
1037 
1038 	ohcip = ohci_polledp->ohci_polled_ohcip;
1039 	ohci_intr_sts = &ohcip->ohci_save_intr_sts;
1040 	ohci_polled_regsp = &ohcip->ohci_polled_save_regs;
1041 	ohcip->ohci_polled_enter_count --;
1042 
1043 	/* Get the endpoint addr. */
1044 	ep_addr = ohci_polledp->ohci_polled_ep_addr;
1045 	/* Get the normal mode usb pipe handle */
1046 	ph = usba_hcdi_get_ph_data(ohci_polledp->ohci_polled_usb_dev, ep_addr);
1047 
1048 	/*
1049 	 * Only the first leave keyboard entry turn off all list processing.
1050 	 * This will take place starting at the next frame.
1051 	 */
1052 	if (Get_OpReg(hcr_control) & HCR_CONTROL_PLE) {
1053 		Set_OpReg(hcr_control,
1054 		    (Get_OpReg(hcr_control) & ~HCR_CONTROL_PLE));
1055 	}
1056 
1057 	/*
1058 	 * Only the last leave keyboard entry restore the info for
1059 	 * normal mode.
1060 	 */
1061 	if (ohcip->ohci_polled_enter_count == 0) {
1062 		Set_OpReg(hcr_intr_enable, HCR_INTR_SOF);
1063 
1064 		/*
1065 		 * According to  OHCI Specification,  we have to wait for eight
1066 		 * start of frames to make sure that the Host Controller writes
1067 		 * contents of done head register to done head filed of HCCA.
1068 		 */
1069 		for (count = 0; count <= DONE_QUEUE_INTR_COUNTER; count++) {
1070 			while (!((Get_OpReg(hcr_intr_status)) & HCR_INTR_SOF)) {
1071 				continue;
1072 			}
1073 			/* Acknowledge the SOF interrupt */
1074 			ohci_polled_finish_interrupt(ohcip, HCR_INTR_SOF);
1075 		}
1076 
1077 		/*
1078 		 * Check any Frame Number Overflow interrupt (FNO) is pending.
1079 		 */
1080 		ohci_polled_handle_frame_number_overflow(ohcip);
1081 
1082 		/*
1083 		 * Before switching back, we have to process last TD in the
1084 		 * POLLED mode. It may be in the hcr_done_head register or
1085 		 * in done list or in the lattice. If it is either on the
1086 		 * hcr_done_head register or in the done list, just re-inserted
1087 		 * into the ED's TD list.
1088 		 *
1089 		 * First look up at the TD's that are in the hcr_done_head
1090 		 * register and re-insert them back into the ED's TD list.
1091 		 */
1092 		td = ohci_td_iommu_to_cpu(ohcip,
1093 		    (uintptr_t)Get_OpReg(hcr_done_head));
1094 
1095 		while (td) {
1096 
1097 		next_td = ohci_td_iommu_to_cpu(ohcip, Get_TD(td->hctd_next_td));
1098 
1099 			/*
1100 			 * Insert valid interrupt TD back into ED's
1101 			 * TD list. No periodic TD's will be processed
1102 			 * since all processing has been stopped.
1103 			 */
1104 			ohci_polled_insert_td(ohcip, td);
1105 
1106 			td = next_td;
1107 		}
1108 
1109 		/*
1110 		 * Now look up at the TD's that are in the HCCA done head list &
1111 		 * re-insert them back into the ED's TD list.
1112 		 */
1113 		td = ohci_td_iommu_to_cpu(ohcip, (Get_HCCA(
1114 		    ohcip->ohci_hccap->HccaDoneHead) & HCCA_DONE_HEAD_MASK));
1115 
1116 		while (td) {
1117 
1118 			next_td = ohci_td_iommu_to_cpu(ohcip,
1119 			    Get_TD(td->hctd_next_td));
1120 
1121 			/*
1122 			 * Insert valid interrupt TD back into ED's
1123 			 * TD list. No periodic TD's will be processed
1124 			 * since all processing has been stopped.
1125 			 */
1126 			ohci_polled_insert_td(ohcip, td);
1127 
1128 			td = next_td;
1129 		}
1130 		/* Reset the HCCA done head list to NULL */
1131 		Set_HCCA(ohcip->ohci_hccap->HccaDoneHead, NULL);
1132 
1133 		/*
1134 		 * Replace the hcr_done_head register field with the saved copy
1135 		 * of current normal mode hcr_done_head register contents.
1136 		 */
1137 		Set_OpReg(hcr_done_head,
1138 		    (uint32_t)ohci_polled_regsp->hcr_done_head);
1139 
1140 		/*
1141 		 * Clear the WriteDoneHead and SOF interrupt bits in the ohci
1142 		 * interrupt status register.
1143 		 */
1144 		Set_OpReg(hcr_intr_status, (HCR_INTR_WDH | HCR_INTR_SOF));
1145 	}
1146 
1147 	/* Get the polled mode ohci pipe private structure */
1148 	polled_pp = (ohci_pipe_private_t *)
1149 	    ohci_polledp->ohci_polled_input_pipe_handle->p_hcd_private;
1150 
1151 	/*
1152 	 * Before replacing the lattice, adjust the data togggle
1153 	 * on the on the ohci's interrupt ed
1154 	 */
1155 	polled_toggle = (Get_ED(polled_pp->pp_ept->hced_headp) &
1156 					HC_EPT_Carry) ? DATA1:DATA0;
1157 
1158 	/*
1159 	 * If normal mode interrupt pipe endpoint is active, fix the
1160 	 * data toggle for this interrupt endpoint by getting the data
1161 	 * toggle information from the polled interrupt endpoint. Else
1162 	 * save the data toggle information in usb device structure.
1163 	 */
1164 	if (ph) {
1165 		/* Get the normal mode ohci pipe private structure */
1166 		pp = (ohci_pipe_private_t *)ph->p_hcd_private;
1167 
1168 		real_toggle = (Get_ED(pp->pp_ept->hced_headp) &
1169 		    HC_EPT_Carry) ? DATA1:DATA0;
1170 
1171 		if (polled_toggle != real_toggle) {
1172 			if (polled_toggle == DATA0) {
1173 				Set_ED(pp->pp_ept->hced_headp,
1174 				    Get_ED(pp->pp_ept->hced_headp) &
1175 				    ~HC_EPT_Carry);
1176 			} else {
1177 				Set_ED(pp->pp_ept->hced_headp,
1178 				    Get_ED(pp->pp_ept->hced_headp) |
1179 				    HC_EPT_Carry);
1180 			}
1181 		}
1182 	} else {
1183 		usba_hcdi_set_data_toggle(ohci_polledp->ohci_polled_usb_dev,
1184 		    ep_addr, polled_toggle);
1185 	}
1186 	/*
1187 	 * Only the last leave keyboard entry restore the Interrupt table,
1188 	 * start processing and enable the interrupt.
1189 	 */
1190 	if (ohcip->ohci_polled_enter_count == 0) {
1191 		/* Replace the lattice */
1192 		for (i = 0; i < NUM_INTR_ED_LISTS; i++) {
1193 			Set_HCCA(ohcip->ohci_hccap->HccaIntTble[i],
1194 			    (uintptr_t)ohcip->ohci_polled_save_IntTble[i]);
1195 		}
1196 
1197 		/*
1198 		 * Clear the contents of current ohci periodic ED register that
1199 		 * is physical address of current Isochronous or Interrupt ED.
1200 		 */
1201 		Set_OpReg(hcr_periodic_curr, (uint32_t)0x0);
1202 
1203 		ohci_polled_start_processing(ohci_polledp);
1204 
1205 		/*
1206 		 * Check and enable required ohci  interrupts before switching
1207 		 * back to normal mode from the POLLED mode.
1208 		 */
1209 		mask = (uint32_t)ohci_polled_regsp->hcr_intr_enable &
1210 		    (HCR_INTR_SOF | HCR_INTR_WDH);
1211 
1212 		if (ohci_intr_sts->ohci_intr_flag & OHCI_INTR_HANDLING) {
1213 			Set_OpReg(hcr_intr_enable, mask);
1214 		} else {
1215 			Set_OpReg(hcr_intr_enable, mask | HCR_INTR_MIE);
1216 		}
1217 	}
1218 
1219 #ifndef lint
1220 	_NOTE(COMPETING_THREADS_NOW);
1221 #endif
1222 }
1223 
1224 /*
1225  * ohci_polled_start_processing:
1226  */
1227 static void
1228 ohci_polled_start_processing(ohci_polled_t	*ohci_polledp)
1229 {
1230 	ohci_state_t		*ohcip;
1231 	uint32_t		control;
1232 	uint32_t		mask;
1233 	ohci_regs_t		*ohci_polled_regsp;
1234 
1235 	ohcip = ohci_polledp->ohci_polled_ohcip;
1236 	ohci_polled_regsp = &ohcip->ohci_polled_save_regs;
1237 
1238 	mask = ((uint32_t)ohci_polled_regsp->hcr_control) & (HCR_CONTROL_CLE |
1239 	    HCR_CONTROL_PLE | HCR_CONTROL_BLE | HCR_CONTROL_IE);
1240 
1241 	control = Get_OpReg(hcr_control) & ~(HCR_CONTROL_CLE |
1242 	    HCR_CONTROL_PLE | HCR_CONTROL_BLE | HCR_CONTROL_IE);
1243 
1244 	Set_OpReg(hcr_control, (control | mask));
1245 }
1246 
1247 
1248 /*
1249  * Polled read routines
1250  */
1251 
1252 
1253 /*
1254  * ohci_polled_check_done_list:
1255  *
1256  * Check to see it there are any TD's on the done head.  If there are
1257  * then reverse the done list and put the TD's on the appropriated list.
1258  */
1259 static int
1260 ohci_polled_check_done_list(ohci_polled_t	*ohci_polledp)
1261 {
1262 	ohci_state_t	*ohcip = ohci_polledp->ohci_polled_ohcip;
1263 	ohci_td_t	*done_head, *done_list;
1264 
1265 	/* Sync HCCA area */
1266 	if (ohci_polledp->ohci_polled_no_sync_flag == B_FALSE) {
1267 		Sync_HCCA(ohcip);
1268 	}
1269 
1270 	/* Read and Save the HCCA DoneHead value */
1271 	done_head = (ohci_td_t *)(uintptr_t)
1272 	    (Get_HCCA(ohcip->ohci_hccap->HccaDoneHead) & HCCA_DONE_HEAD_MASK);
1273 
1274 	/*
1275 	 * Look at the Done Head and if it is NULL and ohci done list is NULL,
1276 	 * just return; else if ohci done list is not NULL, should check it.
1277 	 */
1278 	if (done_head == NULL) {
1279 		if (ohcip->ohci_polled_done_list) {
1280 			done_head = ohcip->ohci_polled_done_list;
1281 		} else {
1282 
1283 			return (USB_FAILURE);
1284 		}
1285 	} else {
1286 		/* Reset the done head to NULL */
1287 		Set_HCCA(ohcip->ohci_hccap->HccaDoneHead, NULL);
1288 		ohcip->ohci_polled_done_list = NULL;
1289 	}
1290 
1291 	/* Sync ED and TD pool */
1292 	if (ohci_polledp->ohci_polled_no_sync_flag == B_FALSE) {
1293 		Sync_ED_TD_Pool(ohcip);
1294 	}
1295 
1296 	/* Pickup own tds in the done head */
1297 	done_list = ohci_polled_pickup_done_list(ohci_polledp, done_head);
1298 
1299 	/*
1300 	 * Look at the own done list which is pickup'ed
1301 	 * and if it is NULL, just return.
1302 	 */
1303 	if (done_list == NULL) {
1304 
1305 		return (USB_FAILURE);
1306 	}
1307 	/* Create the input done list */
1308 	ohci_polled_create_input_list(ohci_polledp, done_list);
1309 
1310 	return (USB_SUCCESS);
1311 }
1312 
1313 /*
1314  * ohci_polled_pickup_done_list:
1315  *
1316  * Pickup the TDs of own in the Done Head List
1317  */
1318 static ohci_td_t *
1319 ohci_polled_pickup_done_list(
1320 	ohci_polled_t	*ohci_polledp,
1321 	ohci_td_t	*done_head)
1322 {
1323 	ohci_state_t	*ohcip = ohci_polledp->ohci_polled_ohcip;
1324 	ohci_td_t	*reserve_head = NULL, *reserve_tail = NULL;
1325 	ohci_td_t	*create_head = NULL, *current_td, *td;
1326 	ohci_trans_wrapper_t	*tw;
1327 	ohci_pipe_private_t	*pp;
1328 
1329 	/*
1330 	 * Current_td pointers point to the done head.
1331 	 */
1332 	current_td = (ohci_td_t *)
1333 	    ohci_td_iommu_to_cpu(ohcip, (uintptr_t)done_head);
1334 	while (current_td) {
1335 		td = (ohci_td_t *)ohci_td_iommu_to_cpu(ohcip,
1336 		    Get_TD(current_td->hctd_next_td));
1337 
1338 		Set_TD(current_td->hctd_next_td, NULL);
1339 
1340 		/* Obtain the transfer wrapper from the TD */
1341 		tw = (ohci_trans_wrapper_t *)OHCI_LOOKUP_ID(
1342 		    (uint32_t)Get_TD(current_td->hctd_trans_wrapper));
1343 
1344 		/* Get the pipe handle for this transfer wrapper. */
1345 		pp = tw->tw_pipe_private;
1346 
1347 		/*
1348 		 * Figure  out  which  done list to put this TD on and put it
1349 		 * there.   If  the  pipe handle  of the TD matches the pipe
1350 		 * handle  we  are  using for the input device, then this must
1351 		 * be an input TD, reverse the order and link to the list for
1352 		 * this input device. Else put the TD to the reserve done list
1353 		 * for other input devices.
1354 		 */
1355 
1356 		if (pp->pp_pipe_handle ==
1357 		    ohci_polledp->ohci_polled_input_pipe_handle) {
1358 			if (create_head == NULL) {
1359 				create_head = current_td;
1360 			} else {
1361 				Set_TD(current_td->hctd_next_td,
1362 				    ohci_td_cpu_to_iommu(ohcip, create_head));
1363 				create_head = current_td;
1364 			}
1365 		} else {
1366 			if (reserve_head == NULL) {
1367 				reserve_head = reserve_tail = current_td;
1368 			} else {
1369 				Set_TD(reserve_tail->hctd_next_td,
1370 				    ohci_td_cpu_to_iommu(ohcip, current_td));
1371 				reserve_tail = current_td;
1372 			}
1373 		}
1374 		current_td = td;
1375 	}
1376 
1377 	/* Check if there is other TDs left for other input devices */
1378 	if (reserve_head) {
1379 		ohcip->ohci_polled_done_list = (ohci_td_t *)(uintptr_t)
1380 		    ohci_td_cpu_to_iommu(ohcip, reserve_head);
1381 
1382 	} else {
1383 		ohcip->ohci_polled_done_list = NULL;
1384 	}
1385 
1386 	return (create_head);
1387 }
1388 
1389 /*
1390  * ohci_polled_create_input_list:
1391  *
1392  * Create the input done list from the actual done head list.
1393  */
1394 static void
1395 ohci_polled_create_input_list(
1396 	ohci_polled_t		*ohci_polledp,
1397 	ohci_td_t		*head_done_list)
1398 {
1399 	ohci_state_t		*ohcip = ohci_polledp->ohci_polled_ohcip;
1400 	ohci_td_t		*cpu_save, *td;
1401 
1402 	ASSERT(head_done_list != NULL);
1403 
1404 	/* Get the done head list */
1405 	td = (ohci_td_t *)head_done_list;
1406 
1407 	/*
1408 	 * Traverse the done list and create the input done list.
1409 	 */
1410 	while (td) {
1411 
1412 		/*
1413 		 * Convert the iommu pointer to a cpu pointer. No point
1414 		 * in doing this over and over, might as well do it once.
1415 		 */
1416 		cpu_save = ohci_td_iommu_to_cpu(ohcip,
1417 		    Get_TD(td->hctd_next_td));
1418 
1419 		/*
1420 		 * Terminate this TD by setting its next pointer to NULL.
1421 		 */
1422 		Set_TD(td->hctd_next_td, NULL);
1423 
1424 		/* This is an input TD, so put it on the input done list */
1425 		if (ohci_polledp->ohci_polled_input_done_head == NULL) {
1426 
1427 			/*
1428 			 * There is nothing on the input done list,
1429 			 * so put this TD on the head.
1430 			 */
1431 			ohci_polledp->ohci_polled_input_done_head = td;
1432 		} else {
1433 			Set_TD(ohci_polledp->
1434 			    ohci_polled_input_done_tail->hctd_next_td,
1435 			    ohci_td_cpu_to_iommu(ohcip, td));
1436 		}
1437 
1438 		/* The tail points to the new TD */
1439 		ohci_polledp->ohci_polled_input_done_tail = td;
1440 		td = cpu_save;
1441 	}
1442 }
1443 
1444 
1445 /*
1446  * ohci_polled_process_input_list:
1447  *
1448  * This routine takes the TD's off of the input done head and processes
1449  * them.  It returns the number of characters that have been copied for
1450  * input.
1451  */
1452 static int
1453 ohci_polled_process_input_list(ohci_polled_t	*ohci_polledp)
1454 {
1455 	ohci_state_t		*ohcip = ohci_polledp->ohci_polled_ohcip;
1456 	ohci_td_t		*td, *next_td;
1457 	uint_t			ctrl;
1458 	uint_t			num_characters;
1459 	ohci_trans_wrapper_t	*tw;
1460 	ohci_pipe_private_t	*pp;
1461 
1462 	/*
1463 	 * Get the first TD on the input done head.
1464 	 */
1465 	td = ohci_polledp->ohci_polled_input_done_head;
1466 
1467 	ohci_polledp->ohci_polled_input_done_head = NULL;
1468 
1469 	num_characters = 0;
1470 
1471 	/*
1472 	 * Traverse the list of transfer descriptors. We can't destroy
1473 	 * hctd_next_td pointers of these  TDs because we are using it
1474 	 * to traverse the done list.  Therefore, we can not put these
1475 	 * TDs back on the ED until we are done processing all of them.
1476 	 */
1477 	while (td) {
1478 
1479 		/* Get the next TD from the input done list */
1480 		next_td = (ohci_td_t *)
1481 		    ohci_td_iommu_to_cpu(ohcip, Get_TD(td->hctd_next_td));
1482 
1483 		/* Look at the status */
1484 		ctrl = (uint_t)Get_TD(td->hctd_ctrl) & (uint32_t)HC_TD_CC;
1485 
1486 		/*
1487 		 * Check to see if there is an error. If there is error
1488 		 * clear the halt condition in the Endpoint  Descriptor
1489 		 * (ED) associated with this Transfer  Descriptor (TD).
1490 		 */
1491 		if (ctrl != HC_TD_CC_NO_E) {
1492 			/* Obtain the transfer wrapper from the TD */
1493 			tw = (ohci_trans_wrapper_t *)OHCI_LOOKUP_ID(
1494 			    (uint32_t)Get_TD(td->hctd_trans_wrapper));
1495 
1496 			/* Get the pipe handle for this transfer wrapper */
1497 			pp = tw->tw_pipe_private;
1498 
1499 			/* Clear the halt bit */
1500 			Set_ED(pp->pp_ept->hced_headp,
1501 			    (Get_ED(pp->pp_ept->hced_headp) & ~HC_EPT_Halt));
1502 		} else {
1503 			num_characters +=
1504 			    ohci_polled_handle_normal_td(ohci_polledp, td);
1505 		}
1506 
1507 		/* Insert this interrupt TD back onto the ED's TD list */
1508 		ohci_polled_insert_td(ohcip, td);
1509 
1510 		td = next_td;
1511 	}
1512 
1513 	return (num_characters);
1514 }
1515 
1516 
1517 /*
1518  * ohci_polled_handle_normal_td:
1519  */
1520 static int
1521 ohci_polled_handle_normal_td(
1522 	ohci_polled_t		*ohci_polledp,
1523 	ohci_td_t		*td)
1524 {
1525 	ohci_state_t		*ohcip = ohci_polledp->ohci_polled_ohcip;
1526 	uchar_t			*buf;
1527 	ohci_trans_wrapper_t	*tw;
1528 	size_t			length, residue;
1529 
1530 	/* Obtain the transfer wrapper from the TD */
1531 	tw = (ohci_trans_wrapper_t *)OHCI_LOOKUP_ID((uint32_t)
1532 	    Get_TD(td->hctd_trans_wrapper));
1533 
1534 	ASSERT(tw != NULL);
1535 
1536 	buf = (uchar_t *)tw->tw_buf;
1537 
1538 	length = tw->tw_length;
1539 
1540 	/*
1541 	 * If "CurrentBufferPointer" of Transfer Descriptor (TD) is
1542 	 * not equal to zero, then we  received less data  from the
1543 	 * device than requested by us. In that  case, get the actual
1544 	 * received data size.
1545 	 */
1546 	if (Get_TD(td->hctd_cbp)) {
1547 
1548 		residue = ohci_get_td_residue(ohcip, td);
1549 		length = Get_TD(td->hctd_xfer_offs) +
1550 		    Get_TD(td->hctd_xfer_len) - residue;
1551 	}
1552 
1553 	/* Sync IO buffer */
1554 	if (ohci_polledp->ohci_polled_no_sync_flag == B_FALSE) {
1555 		Sync_IO_Buffer(tw->tw_dmahandle, length);
1556 	}
1557 
1558 	/* Copy the data into the message */
1559 	ddi_rep_get8(tw->tw_accesshandle,
1560 	    (uint8_t *)ohci_polledp->ohci_polled_buf,
1561 	    (uint8_t *)buf, length, DDI_DEV_AUTOINCR);
1562 
1563 	return (length);
1564 }
1565 
1566 
1567 /*
1568  * ohci_polled_insert_td:
1569  *
1570  * Insert a Transfer Descriptor (TD) on an Endpoint Descriptor (ED).
1571  */
1572 static void
1573 ohci_polled_insert_td(
1574 	ohci_state_t		*ohcip,
1575 	ohci_td_t		*td)
1576 {
1577 	ohci_pipe_private_t	*pp;
1578 	ohci_ed_t		*ept;
1579 	uint_t			td_control;
1580 	ohci_trans_wrapper_t	*tw;
1581 	ohci_td_t		*cpu_current_dummy;
1582 	usb_intr_req_t		*intr_req;
1583 
1584 	/* Obtain the transfer wrapper from the TD */
1585 	tw = (ohci_trans_wrapper_t *)OHCI_LOOKUP_ID(
1586 	    (uint32_t)Get_TD(td->hctd_trans_wrapper));
1587 
1588 	/* Ensure the DMA cookie is valid for reuse */
1589 	ASSERT((tw->tw_cookie_idx == 0) && (tw->tw_dma_offs == 0));
1590 
1591 	/*
1592 	 * Take this TD off the transfer wrapper's list since
1593 	 * the pipe is FIFO, this must be the first TD on the
1594 	 * list.
1595 	 */
1596 	ASSERT((ohci_td_t *)tw->tw_hctd_head == td);
1597 
1598 	tw->tw_hctd_head = (ohci_td_t *)
1599 	    ohci_td_iommu_to_cpu(ohcip, Get_TD(td->hctd_tw_next_td));
1600 
1601 	/*
1602 	 * If the head becomes NULL, then there are no more
1603 	 * active TD's for this transfer wrapper. Also	set
1604 	 * the tail to NULL.
1605 	 */
1606 	if (tw->tw_hctd_head == NULL) {
1607 		tw->tw_hctd_tail = NULL;
1608 	}
1609 
1610 	/* Convert current valid TD as new dummy TD */
1611 	bzero((char *)td, sizeof (ohci_td_t));
1612 	Set_TD(td->hctd_state, HC_TD_DUMMY);
1613 
1614 	pp = tw->tw_pipe_private;
1615 
1616 	/* Obtain the endpoint and interrupt request */
1617 	ept = pp->pp_ept;
1618 
1619 	intr_req = (usb_intr_req_t *)tw->tw_curr_xfer_reqp;
1620 
1621 	if (intr_req->intr_attributes & USB_ATTRS_SHORT_XFER_OK) {
1622 		td_control = HC_TD_IN|HC_TD_1I|HC_TD_R;
1623 	} else {
1624 		td_control = HC_TD_IN|HC_TD_1I;
1625 	}
1626 
1627 	/* Get the current dummy */
1628 	cpu_current_dummy = (ohci_td_t *)
1629 	    (ohci_td_iommu_to_cpu(ohcip, Get_ED(ept->hced_tailp)));
1630 
1631 	/*
1632 	 * Fill in the current dummy td and
1633 	 * add the new dummy to the end.
1634 	 */
1635 	ohci_polled_fill_in_td(ohcip, cpu_current_dummy, td,
1636 	    td_control, 0, tw->tw_length, tw);
1637 
1638 	/* Insert this td onto the tw */
1639 	ohci_polled_insert_td_on_tw(ohcip, tw, cpu_current_dummy);
1640 
1641 	/*
1642 	 * Add the new dummy to the ED's list.	When this occurs,
1643 	 * the Host Controller will see the newly filled in dummy
1644 	 * TD.
1645 	 */
1646 	Set_ED(ept->hced_tailp, (ohci_td_cpu_to_iommu(ohcip, td)));
1647 }
1648 
1649 
1650 /*
1651  * ohci_polled_fill_in_td:
1652  *
1653  * Fill in the fields of a Transfer Descriptor (TD).
1654  */
1655 static void
1656 ohci_polled_fill_in_td(
1657 	ohci_state_t		*ohcip,
1658 	ohci_td_t		*td,
1659 	ohci_td_t		*new_dummy,
1660 	uint_t			hctd_ctrl,
1661 	uint32_t		hctd_dma_offs,
1662 	size_t			hctd_length,
1663 	ohci_trans_wrapper_t	*tw)
1664 {
1665 	/* Assert that the td to be filled in is a dummy */
1666 	ASSERT(Get_TD(td->hctd_state) == HC_TD_DUMMY);
1667 
1668 	/* Clear the TD */
1669 	bzero((char *)td, sizeof (ohci_td_t));
1670 
1671 	/* Update the dummy with control information */
1672 	Set_TD(td->hctd_ctrl, (hctd_ctrl | HC_TD_CC_NA));
1673 
1674 	/* Update the beginning and end of the buffer */
1675 	ohci_init_td(ohcip, tw, hctd_dma_offs, hctd_length, td);
1676 
1677 	/* The current dummy now points to the new dummy */
1678 	Set_TD(td->hctd_next_td, (ohci_td_cpu_to_iommu(ohcip, new_dummy)));
1679 
1680 	/* Fill in the wrapper portion of the TD */
1681 	Set_TD(td->hctd_trans_wrapper, (uint32_t)tw->tw_id);
1682 	Set_TD(td->hctd_tw_next_td, NULL);
1683 }
1684 
1685 
1686 /*
1687  * ohci_polled_insert_td_on_tw:
1688  *
1689  * The transfer wrapper keeps a list of all Transfer Descriptors (TD) that
1690  * are allocated for this transfer. Insert a TD  onto this list. The  list
1691  * of TD's does not include the dummy TD that is at the end of the list of
1692  * TD's for the endpoint.
1693  */
1694 static void
1695 ohci_polled_insert_td_on_tw(
1696 	ohci_state_t		*ohcip,
1697 	ohci_trans_wrapper_t	*tw,
1698 	ohci_td_t		*td)
1699 {
1700 
1701 	/*
1702 	 * Set the next pointer to NULL because
1703 	 * this is the last TD on list.
1704 	 */
1705 	Set_TD(td->hctd_tw_next_td, NULL);
1706 
1707 	if (tw->tw_hctd_head == NULL) {
1708 		ASSERT(tw->tw_hctd_tail == NULL);
1709 		tw->tw_hctd_head = td;
1710 		tw->tw_hctd_tail = td;
1711 	} else {
1712 		ohci_td_t *dummy = (ohci_td_t *)tw->tw_hctd_tail;
1713 
1714 		ASSERT(dummy != NULL);
1715 		ASSERT(dummy != td);
1716 		ASSERT(Get_TD(td->hctd_state) == HC_TD_DUMMY);
1717 
1718 		/* Add the td to the end of the list */
1719 		Set_TD(dummy->hctd_tw_next_td, ohci_td_cpu_to_iommu(ohcip, td));
1720 		tw->tw_hctd_tail = td;
1721 
1722 		ASSERT(Get_TD(td->hctd_tw_next_td) == NULL);
1723 	}
1724 }
1725 
1726 
1727 /*
1728  * ohci_polled_handle_frame_number_overflow:
1729  *
1730  * Process Frame Number Overflow (FNO) interrupt in polled mode.
1731  */
1732 static void
1733 ohci_polled_handle_frame_number_overflow(ohci_state_t	*ohcip)
1734 {
1735 	uint_t			intr;
1736 
1737 	/* Read the Interrupt Status & Interrupt enable register */
1738 	intr = (Get_OpReg(hcr_intr_status) & Get_OpReg(hcr_intr_enable));
1739 
1740 	/*
1741 	 * Check whether any Frame Number Overflow interrupt is pending
1742 	 * and if it is pending, process this interrupt.
1743 	 */
1744 	if (intr & HCR_INTR_FNO) {
1745 		ohci_handle_frame_number_overflow(ohcip);
1746 
1747 		/* Acknowledge the FNO interrupt */
1748 		ohci_polled_finish_interrupt(ohcip, HCR_INTR_FNO);
1749 	}
1750 }
1751 
1752 
1753 /*
1754  * ohci_polled_finish_interrupt:
1755  */
1756 static void
1757 ohci_polled_finish_interrupt(
1758 	ohci_state_t	*ohcip,
1759 	uint_t		intr)
1760 {
1761 	/* Acknowledge the interrupt */
1762 	Set_OpReg(hcr_intr_status, intr);
1763 
1764 	/*
1765 	 * Read interrupt status register to make sure that any PIO
1766 	 * store to clear the ISR has made it on the PCI bus before
1767 	 * returning from its interrupt handler.
1768 	 */
1769 	(void) Get_OpReg(hcr_intr_status);
1770 }
1771