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 2009 Sun Microsystems, Inc.  All rights reserved.
23 * Use is subject to license terms.
24 */
25
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 * NOTE:
36 *
37 * Currently OHCI driver does not support the following features
38 *
39 * - Handle request with multiple TDs under short xfer conditions except for
40 *   bulk transfers.
41 */
42#include <sys/usb/hcd/openhci/ohcid.h>
43
44#include <sys/disp.h>
45#include <sys/strsun.h>
46
47/* Pointer to the state structure */
48static void *ohci_statep;
49
50int force_ohci_off = 1;
51
52/* Number of instances */
53#define	OHCI_INSTS	1
54
55/* Adjustable variables for the size of the pools */
56int ohci_ed_pool_size = OHCI_ED_POOL_SIZE;
57int ohci_td_pool_size = OHCI_TD_POOL_SIZE;
58
59/*
60 * Initialize the values which are used for setting up head pointers for
61 * the 32ms scheduling lists which starts from the HCCA.
62 */
63static uchar_t ohci_index[NUM_INTR_ED_LISTS / 2] = {0x0, 0x8, 0x4, 0xc,
64						0x2, 0xa, 0x6, 0xe,
65						0x1, 0x9, 0x5, 0xd,
66						0x3, 0xb, 0x7, 0xf};
67/* Debugging information */
68uint_t ohci_errmask	= (uint_t)PRINT_MASK_ALL;
69uint_t ohci_errlevel	= USB_LOG_L2;
70uint_t ohci_instance_debug = (uint_t)-1;
71
72/*
73 * OHCI MSI tunable:
74 *
75 * By default MSI is enabled on all supported platforms.
76 */
77boolean_t ohci_enable_msi = B_TRUE;
78
79/*
80 * HCDI entry points
81 *
82 * The Host Controller Driver Interfaces (HCDI) are the software interfaces
83 * between the Universal Serial Bus Driver (USBA) and the Host	Controller
84 * Driver (HCD). The HCDI interfaces or entry points are subject to change.
85 */
86static int	ohci_hcdi_pipe_open(
87				usba_pipe_handle_data_t	*ph,
88				usb_flags_t		usb_flags);
89static int	ohci_hcdi_pipe_close(
90				usba_pipe_handle_data_t	*ph,
91				usb_flags_t		usb_flags);
92static int	ohci_hcdi_pipe_reset(
93				usba_pipe_handle_data_t	*ph,
94				usb_flags_t		usb_flags);
95static void	ohci_hcdi_pipe_reset_data_toggle(
96				usba_pipe_handle_data_t	*ph);
97static int	ohci_hcdi_pipe_ctrl_xfer(
98				usba_pipe_handle_data_t	*ph,
99				usb_ctrl_req_t		*ctrl_reqp,
100				usb_flags_t		usb_flags);
101static int	ohci_hcdi_bulk_transfer_size(
102				usba_device_t		*usba_device,
103				size_t			*size);
104static int	ohci_hcdi_pipe_bulk_xfer(
105				usba_pipe_handle_data_t	*ph,
106				usb_bulk_req_t		*bulk_reqp,
107				usb_flags_t		usb_flags);
108static int	ohci_hcdi_pipe_intr_xfer(
109				usba_pipe_handle_data_t	*ph,
110				usb_intr_req_t		*intr_req,
111				usb_flags_t		usb_flags);
112static int	ohci_hcdi_pipe_stop_intr_polling(
113				usba_pipe_handle_data_t	*ph,
114				usb_flags_t		usb_flags);
115static int	ohci_hcdi_get_current_frame_number(
116				usba_device_t		*usba_device,
117				usb_frame_number_t	*frame_number);
118static int	ohci_hcdi_get_max_isoc_pkts(
119				usba_device_t		*usba_device,
120				uint_t		*max_isoc_pkts_per_request);
121static int	ohci_hcdi_pipe_isoc_xfer(
122				usba_pipe_handle_data_t	*ph,
123				usb_isoc_req_t		*isoc_reqp,
124				usb_flags_t		usb_flags);
125static int	ohci_hcdi_pipe_stop_isoc_polling(
126				usba_pipe_handle_data_t	*ph,
127				usb_flags_t		usb_flags);
128
129/*
130 * Internal Function Prototypes
131 */
132
133/* Host Controller Driver (HCD) initialization functions */
134static void	ohci_set_dma_attributes(ohci_state_t	*ohcip);
135static int	ohci_allocate_pools(ohci_state_t	*ohcip);
136static void	ohci_decode_ddi_dma_addr_bind_handle_result(
137				ohci_state_t		*ohcip,
138				int			result);
139static int	ohci_map_regs(ohci_state_t		*ohcip);
140static int	ohci_register_intrs_and_init_mutex(
141				ohci_state_t		*ohcip);
142static int	ohci_add_intrs(ohci_state_t		*ohcip,
143				int			intr_type);
144static int	ohci_init_ctlr(ohci_state_t		*ohcip);
145static int	ohci_init_hcca(ohci_state_t		*ohcip);
146static void	ohci_build_interrupt_lattice(
147				ohci_state_t		*ohcip);
148static int	ohci_take_control(ohci_state_t		*ohcip);
149static usba_hcdi_ops_t *ohci_alloc_hcdi_ops(
150				ohci_state_t		*ohcip);
151
152/* Host Controller Driver (HCD) deinitialization functions */
153static int	ohci_cleanup(ohci_state_t		*ohcip);
154static void	ohci_rem_intrs(ohci_state_t		*ohcip);
155static int	ohci_cpr_suspend(ohci_state_t		*ohcip);
156static int	ohci_cpr_resume(ohci_state_t		*ohcip);
157
158/* Bandwidth Allocation functions */
159static int	ohci_allocate_bandwidth(ohci_state_t	*ohcip,
160				usba_pipe_handle_data_t	*ph,
161				uint_t			*node);
162static void	ohci_deallocate_bandwidth(ohci_state_t	*ohcip,
163				usba_pipe_handle_data_t	*ph);
164static int	ohci_compute_total_bandwidth(
165				usb_ep_descr_t		*endpoint,
166				usb_port_status_t	port_status,
167				uint_t			*bandwidth);
168static int	ohci_adjust_polling_interval(
169				ohci_state_t		*ohcip,
170				usb_ep_descr_t		*endpoint,
171				usb_port_status_t	port_status);
172static uint_t	ohci_lattice_height(uint_t		interval);
173static uint_t	ohci_lattice_parent(uint_t		node);
174static uint_t	ohci_leftmost_leaf(uint_t		node,
175				uint_t			height);
176static uint_t	ohci_hcca_intr_index(
177				uint_t			node);
178static uint_t	ohci_hcca_leaf_index(
179				uint_t			leaf);
180static uint_t	ohci_pow_2(uint_t x);
181static uint_t	ohci_log_2(uint_t x);
182
183/* Endpoint Descriptor (ED) related functions */
184static uint_t	ohci_unpack_endpoint(ohci_state_t	*ohcip,
185				usba_pipe_handle_data_t	*ph);
186static void	ohci_insert_ed(ohci_state_t		*ohcip,
187				usba_pipe_handle_data_t	*ph);
188static void	ohci_insert_ctrl_ed(
189				ohci_state_t		*ohcip,
190				ohci_pipe_private_t	*pp);
191static void	ohci_insert_bulk_ed(
192				ohci_state_t		*ohcip,
193				ohci_pipe_private_t	*pp);
194static void	ohci_insert_intr_ed(
195				ohci_state_t		*ohcip,
196				ohci_pipe_private_t	*pp);
197static void	ohci_insert_isoc_ed(
198				ohci_state_t		*ohcip,
199				ohci_pipe_private_t	*pp);
200static void	ohci_modify_sKip_bit(ohci_state_t	*ohcip,
201				ohci_pipe_private_t	*pp,
202				skip_bit_t		action,
203				usb_flags_t		flag);
204static void	ohci_remove_ed(ohci_state_t		*ohcip,
205				ohci_pipe_private_t	*pp);
206static void	ohci_remove_ctrl_ed(
207				ohci_state_t		*ohcip,
208				ohci_pipe_private_t	*pp);
209static void	ohci_remove_bulk_ed(
210				ohci_state_t		*ohcip,
211				ohci_pipe_private_t	*pp);
212static void	ohci_remove_periodic_ed(
213				ohci_state_t		*ohcip,
214				ohci_pipe_private_t	*pp);
215static void	ohci_insert_ed_on_reclaim_list(
216				ohci_state_t		*ohcip,
217				ohci_pipe_private_t	*pp);
218static void	ohci_detach_ed_from_list(
219				ohci_state_t		*ohcip,
220				ohci_ed_t		*ept,
221				uint_t			ept_type);
222static ohci_ed_t *ohci_ed_iommu_to_cpu(
223				ohci_state_t		*ohcip,
224				uintptr_t		addr);
225
226/* Transfer Descriptor (TD) related functions */
227static int	ohci_initialize_dummy(ohci_state_t	*ohcip,
228				ohci_ed_t		*ept);
229static ohci_trans_wrapper_t *ohci_allocate_ctrl_resources(
230				ohci_state_t		*ohcip,
231				ohci_pipe_private_t	*pp,
232				usb_ctrl_req_t		*ctrl_reqp,
233				usb_flags_t		usb_flags);
234static void	ohci_insert_ctrl_req(
235				ohci_state_t		*ohcip,
236				usba_pipe_handle_data_t	*ph,
237				usb_ctrl_req_t		*ctrl_reqp,
238				ohci_trans_wrapper_t	*tw,
239				usb_flags_t		usb_flags);
240static ohci_trans_wrapper_t *ohci_allocate_bulk_resources(
241				ohci_state_t		*ohcip,
242				ohci_pipe_private_t	*pp,
243				usb_bulk_req_t		*bulk_reqp,
244				usb_flags_t		usb_flags);
245static void	ohci_insert_bulk_req(ohci_state_t	*ohcip,
246				usba_pipe_handle_data_t	*ph,
247				usb_bulk_req_t		*bulk_reqp,
248				ohci_trans_wrapper_t	*tw,
249				usb_flags_t		flags);
250static int	ohci_start_pipe_polling(ohci_state_t	*ohcip,
251				usba_pipe_handle_data_t	*ph,
252				usb_flags_t		flags);
253static void	ohci_set_periodic_pipe_polling(
254				ohci_state_t		*ohcip,
255				usba_pipe_handle_data_t	*ph);
256static ohci_trans_wrapper_t *ohci_allocate_intr_resources(
257				ohci_state_t		*ohcip,
258				usba_pipe_handle_data_t	*ph,
259				usb_intr_req_t		*intr_reqp,
260				usb_flags_t		usb_flags);
261static void	ohci_insert_intr_req(ohci_state_t	*ohcip,
262				ohci_pipe_private_t	*pp,
263				ohci_trans_wrapper_t	*tw,
264				usb_flags_t		flags);
265static int	ohci_stop_periodic_pipe_polling(
266				ohci_state_t		*ohcip,
267				usba_pipe_handle_data_t	*ph,
268				usb_flags_t		flags);
269static ohci_trans_wrapper_t *ohci_allocate_isoc_resources(
270				ohci_state_t		*ohcip,
271				usba_pipe_handle_data_t	*ph,
272				usb_isoc_req_t		*isoc_reqp,
273				usb_flags_t		usb_flags);
274static int	ohci_insert_isoc_req(ohci_state_t	*ohcip,
275				ohci_pipe_private_t	*pp,
276				ohci_trans_wrapper_t	*tw,
277				uint_t			flags);
278static int	ohci_insert_hc_td(ohci_state_t		*ohcip,
279				uint_t			hctd_ctrl,
280				uint32_t		hctd_dma_offs,
281				size_t			hctd_length,
282				uint32_t		hctd_ctrl_phase,
283				ohci_pipe_private_t	*pp,
284				ohci_trans_wrapper_t	*tw);
285static ohci_td_t *ohci_allocate_td_from_pool(
286				ohci_state_t		*ohcip);
287static void	ohci_fill_in_td(ohci_state_t		*ohcip,
288				ohci_td_t		*td,
289				ohci_td_t		*new_dummy,
290				uint_t			hctd_ctrl,
291				uint32_t		hctd_dma_offs,
292				size_t			hctd_length,
293				uint32_t		hctd_ctrl_phase,
294				ohci_pipe_private_t	*pp,
295				ohci_trans_wrapper_t	*tw);
296static void	ohci_init_itd(
297				ohci_state_t		*ohcip,
298				ohci_trans_wrapper_t	*tw,
299				uint_t			hctd_ctrl,
300				uint32_t		index,
301				ohci_td_t		*td);
302static int	ohci_insert_td_with_frame_number(
303				ohci_state_t		*ohcip,
304				ohci_pipe_private_t	*pp,
305				ohci_trans_wrapper_t	*tw,
306				ohci_td_t		*current_td,
307				ohci_td_t		*dummy_td);
308static void	ohci_insert_td_on_tw(ohci_state_t	*ohcip,
309				ohci_trans_wrapper_t	*tw,
310				ohci_td_t		*td);
311static void	ohci_done_list_tds(ohci_state_t		*ohcip,
312				usba_pipe_handle_data_t	*ph);
313
314/* Transfer Wrapper (TW) functions */
315static ohci_trans_wrapper_t  *ohci_create_transfer_wrapper(
316				ohci_state_t		*ohcip,
317				ohci_pipe_private_t	*pp,
318				size_t			length,
319				uint_t			usb_flags);
320static ohci_trans_wrapper_t  *ohci_create_isoc_transfer_wrapper(
321				ohci_state_t		*ohcip,
322				ohci_pipe_private_t	*pp,
323				size_t			length,
324				usb_isoc_pkt_descr_t	*descr,
325				ushort_t		pkt_count,
326				size_t			td_count,
327				uint_t			usb_flags);
328int	ohci_allocate_tds_for_tw(
329				ohci_state_t		*ohcip,
330				ohci_trans_wrapper_t	*tw,
331				size_t			td_count);
332static ohci_trans_wrapper_t  *ohci_allocate_tw_resources(
333				ohci_state_t		*ohcip,
334				ohci_pipe_private_t	*pp,
335				size_t			length,
336				usb_flags_t		usb_flags,
337				size_t			td_count);
338static void	ohci_free_tw_tds_resources(
339				ohci_state_t		*ohcip,
340				ohci_trans_wrapper_t	*tw);
341static void	ohci_start_xfer_timer(
342				ohci_state_t		*ohcip,
343				ohci_pipe_private_t	*pp,
344				ohci_trans_wrapper_t	*tw);
345static void	ohci_stop_xfer_timer(
346				ohci_state_t		*ohcip,
347				ohci_trans_wrapper_t	*tw,
348				uint_t			flag);
349static void	ohci_xfer_timeout_handler(void		*arg);
350static void	ohci_remove_tw_from_timeout_list(
351				ohci_state_t		*ohcip,
352				ohci_trans_wrapper_t	*tw);
353static void	ohci_start_timer(ohci_state_t		*ohcip);
354static void	ohci_free_dma_resources(ohci_state_t	*ohcip,
355				usba_pipe_handle_data_t	*ph);
356static void	ohci_free_tw(ohci_state_t		*ohcip,
357				ohci_trans_wrapper_t	*tw);
358static int	ohci_tw_rebind_cookie(
359				ohci_state_t		*ohcip,
360				ohci_pipe_private_t	*pp,
361				ohci_trans_wrapper_t	*tw);
362
363/* Interrupt Handling functions */
364static uint_t	ohci_intr(caddr_t			arg1,
365				caddr_t			arg2);
366static void	ohci_handle_missed_intr(
367				ohci_state_t		*ohcip);
368static void	ohci_handle_ue(ohci_state_t		*ohcip);
369static void	ohci_handle_endpoint_reclaimation(
370				ohci_state_t		*ohcip);
371static void	ohci_traverse_done_list(
372				ohci_state_t		*ohcip,
373				ohci_td_t		*head_done_list);
374static ohci_td_t *ohci_reverse_done_list(
375				ohci_state_t		*ohcip,
376				ohci_td_t		*head_done_list);
377static usb_cr_t	ohci_parse_error(ohci_state_t		*ohcip,
378				ohci_td_t		*td);
379static void	ohci_parse_isoc_error(
380				ohci_state_t		*ohcip,
381				ohci_pipe_private_t	*pp,
382				ohci_trans_wrapper_t	*tw,
383				ohci_td_t		*td);
384static usb_cr_t ohci_check_for_error(
385				ohci_state_t		*ohcip,
386				ohci_pipe_private_t	*pp,
387				ohci_trans_wrapper_t	*tw,
388				ohci_td_t		*td,
389				uint_t			ctrl);
390static void	ohci_handle_error(
391				ohci_state_t		*ohcip,
392				ohci_td_t		*td,
393				usb_cr_t		error);
394static int	ohci_cleanup_data_underrun(
395				ohci_state_t		*ohcip,
396				ohci_pipe_private_t	*pp,
397				ohci_trans_wrapper_t	*tw,
398				ohci_td_t		*td);
399static void	ohci_handle_normal_td(
400				ohci_state_t		*ohcip,
401				ohci_td_t		*td,
402				ohci_trans_wrapper_t	*tw);
403static void	ohci_handle_ctrl_td(ohci_state_t	*ohcip,
404				ohci_pipe_private_t	*pp,
405				ohci_trans_wrapper_t	*tw,
406				ohci_td_t		*td,
407				void			*);
408static void	ohci_handle_bulk_td(ohci_state_t	*ohcip,
409				ohci_pipe_private_t	*pp,
410				ohci_trans_wrapper_t	*tw,
411				ohci_td_t		*td,
412				void			*);
413static void	ohci_handle_intr_td(ohci_state_t	*ohcip,
414				ohci_pipe_private_t	*pp,
415				ohci_trans_wrapper_t	*tw,
416				ohci_td_t		*td,
417				void			*);
418static void	ohci_handle_one_xfer_completion(
419				ohci_state_t		*ohcip,
420				ohci_trans_wrapper_t	*tw);
421static void	ohci_handle_isoc_td(ohci_state_t	*ohcip,
422				ohci_pipe_private_t	*pp,
423				ohci_trans_wrapper_t	*tw,
424				ohci_td_t		*td,
425				void			*);
426static void	ohci_sendup_td_message(
427				ohci_state_t		*ohcip,
428				ohci_pipe_private_t	*pp,
429				ohci_trans_wrapper_t	*tw,
430				ohci_td_t		*td,
431				usb_cr_t		error);
432static int	ohci_check_done_head(
433				ohci_state_t *ohcip,
434				ohci_td_t		*done_head);
435
436/* Miscillaneous functions */
437static void	ohci_cpr_cleanup(
438				ohci_state_t		*ohcip);
439static usb_req_attrs_t ohci_get_xfer_attrs(ohci_state_t *ohcip,
440				ohci_pipe_private_t	*pp,
441				ohci_trans_wrapper_t	*tw);
442static int	ohci_allocate_periodic_in_resource(
443				ohci_state_t		*ohcip,
444				ohci_pipe_private_t	*pp,
445				ohci_trans_wrapper_t	*tw,
446				usb_flags_t		flags);
447static int	ohci_wait_for_sof(
448				ohci_state_t		*ohcip);
449static void	ohci_pipe_cleanup(
450				ohci_state_t		*ohcip,
451				usba_pipe_handle_data_t	*ph);
452static void	ohci_wait_for_transfers_completion(
453				ohci_state_t		*ohcip,
454				ohci_pipe_private_t	*pp);
455static void	ohci_check_for_transfers_completion(
456				ohci_state_t		*ohcip,
457				ohci_pipe_private_t	*pp);
458static void	ohci_save_data_toggle(ohci_state_t	*ohcip,
459				usba_pipe_handle_data_t	*ph);
460static void	ohci_restore_data_toggle(ohci_state_t	*ohcip,
461				usba_pipe_handle_data_t	*ph);
462static void	ohci_deallocate_periodic_in_resource(
463				ohci_state_t		*ohcip,
464				ohci_pipe_private_t	*pp,
465				ohci_trans_wrapper_t	*tw);
466static void	ohci_do_client_periodic_in_req_callback(
467				ohci_state_t		*ohcip,
468				ohci_pipe_private_t	*pp,
469				usb_cr_t		completion_reason);
470static void	ohci_hcdi_callback(
471				usba_pipe_handle_data_t	*ph,
472				ohci_trans_wrapper_t	*tw,
473				usb_cr_t		completion_reason);
474
475/* Kstat Support */
476static void	ohci_create_stats(ohci_state_t		*ohcip);
477static void	ohci_destroy_stats(ohci_state_t		*ohcip);
478static void	ohci_do_byte_stats(
479				ohci_state_t		*ohcip,
480				size_t			len,
481				uint8_t			attr,
482				uint8_t			addr);
483static void	ohci_do_intrs_stats(
484				ohci_state_t		*ohcip,
485				int			val);
486static void	ohci_print_op_regs(ohci_state_t		*ohcip);
487static void	ohci_print_ed(ohci_state_t		*ohcip,
488				ohci_ed_t		*ed);
489static void	ohci_print_td(ohci_state_t		*ohcip,
490				ohci_td_t		*td);
491
492/* extern */
493int usba_hubdi_root_hub_power(dev_info_t *dip, int comp, int level);
494
495/*
496 * Device operations (dev_ops) entries function prototypes.
497 *
498 * We use the hub cbops since all nexus ioctl operations defined so far will
499 * be executed by the root hub. The following are the Host Controller Driver
500 * (HCD) entry points.
501 *
502 * the open/close/ioctl functions call the corresponding usba_hubdi_*
503 * calls after looking up the dip thru the dev_t.
504 */
505static int	ohci_open(dev_t	*devp, int flags, int otyp, cred_t *credp);
506static int	ohci_close(dev_t dev, int flag, int otyp, cred_t *credp);
507static int	ohci_ioctl(dev_t dev, int cmd, intptr_t arg, int mode,
508				cred_t *credp, int *rvalp);
509
510static int	ohci_attach(dev_info_t *dip, ddi_attach_cmd_t cmd);
511static int	ohci_detach(dev_info_t *dip, ddi_detach_cmd_t cmd);
512static int	ohci_quiesce(dev_info_t *dip);
513
514static int	ohci_info(dev_info_t *dip, ddi_info_cmd_t infocmd,
515				void *arg, void **result);
516
517static struct cb_ops ohci_cb_ops = {
518	ohci_open,			/* Open */
519	ohci_close,			/* Close */
520	nodev,				/* Strategy */
521	nodev,				/* Print */
522	nodev,				/* Dump */
523	nodev,				/* Read */
524	nodev,				/* Write */
525	ohci_ioctl,			/* Ioctl */
526	nodev,				/* Devmap */
527	nodev,				/* Mmap */
528	nodev,				/* Segmap */
529	nochpoll,			/* Poll */
530	ddi_prop_op,			/* cb_prop_op */
531	NULL,				/* Streamtab */
532	D_MP				/* Driver compatibility flag */
533};
534
535static struct dev_ops ohci_ops = {
536	DEVO_REV,			/* Devo_rev */
537	0,				/* Refcnt */
538	ohci_info,			/* Info */
539	nulldev,			/* Identify */
540	nulldev,			/* Probe */
541	ohci_attach,			/* Attach */
542	ohci_detach,			/* Detach */
543	nodev,				/* Reset */
544	&ohci_cb_ops,			/* Driver operations */
545	&usba_hubdi_busops,		/* Bus operations */
546	usba_hubdi_root_hub_power,	/* Power */
547	ohci_quiesce,			/* Quiesce */
548};
549
550/*
551 * The USBA library must be loaded for this driver.
552 */
553static struct modldrv modldrv = {
554	&mod_driverops,		/* Type of module. This one is a driver */
555	"USB OpenHCI Driver",	/* Name of the module. */
556	&ohci_ops,		/* Driver ops */
557};
558
559static struct modlinkage modlinkage = {
560	MODREV_1, (void *)&modldrv, NULL
561};
562
563
564int
565_init(void)
566{
567	int error;
568
569	/* Initialize the soft state structures */
570	if ((error = ddi_soft_state_init(&ohci_statep, sizeof (ohci_state_t),
571	    OHCI_INSTS)) != 0) {
572		return (error);
573	}
574
575	/* Install the loadable module */
576	if ((error = mod_install(&modlinkage)) != 0) {
577		ddi_soft_state_fini(&ohci_statep);
578	}
579
580	return (error);
581}
582
583
584int
585_info(struct modinfo *modinfop)
586{
587	return (mod_info(&modlinkage, modinfop));
588}
589
590
591int
592_fini(void)
593{
594	int error;
595
596	if ((error = mod_remove(&modlinkage)) == 0) {
597		/* Release per module resources */
598		ddi_soft_state_fini(&ohci_statep);
599	}
600
601	return (error);
602}
603
604
605/*
606 * Host Controller Driver (HCD) entry points
607 */
608
609/*
610 * ohci_attach:
611 */
612static int
613ohci_attach(dev_info_t *dip, ddi_attach_cmd_t cmd)
614{
615	int			instance;
616	ohci_state_t		*ohcip = NULL;
617	usba_hcdi_register_args_t hcdi_args;
618
619	switch (cmd) {
620	case DDI_ATTACH:
621		break;
622	case DDI_RESUME:
623		ohcip = ohci_obtain_state(dip);
624
625		return (ohci_cpr_resume(ohcip));
626	default:
627		return (DDI_FAILURE);
628	}
629
630	/* Get the instance and create soft state */
631	instance = ddi_get_instance(dip);
632
633	if (ddi_soft_state_zalloc(ohci_statep, instance) != 0) {
634
635		return (DDI_FAILURE);
636	}
637
638	ohcip = ddi_get_soft_state(ohci_statep, instance);
639	if (ohcip == NULL) {
640
641		return (DDI_FAILURE);
642	}
643
644	ohcip->ohci_flags = OHCI_ATTACH;
645
646	ohcip->ohci_log_hdl = usb_alloc_log_hdl(dip, "ohci", &ohci_errlevel,
647	    &ohci_errmask, &ohci_instance_debug, 0);
648
649	ohcip->ohci_flags |= OHCI_ZALLOC;
650
651	/* Set host controller soft state to initilization */
652	ohcip->ohci_hc_soft_state = OHCI_CTLR_INIT_STATE;
653
654	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
655	    "ohcip = 0x%p", (void *)ohcip);
656
657	/* Initialize the DMA attributes */
658	ohci_set_dma_attributes(ohcip);
659
660	/* Save the dip and instance */
661	ohcip->ohci_dip = dip;
662	ohcip->ohci_instance = instance;
663
664	/* Initialize the kstat structures */
665	ohci_create_stats(ohcip);
666
667	/* Create the td and ed pools */
668	if (ohci_allocate_pools(ohcip) != DDI_SUCCESS) {
669		(void) ohci_cleanup(ohcip);
670
671		return (DDI_FAILURE);
672	}
673
674	/* Map the registers */
675	if (ohci_map_regs(ohcip) != DDI_SUCCESS) {
676		(void) ohci_cleanup(ohcip);
677
678		return (DDI_FAILURE);
679	}
680
681	/* Get the ohci chip vendor and device id */
682	ohcip->ohci_vendor_id = pci_config_get16(
683	    ohcip->ohci_config_handle, PCI_CONF_VENID);
684	ohcip->ohci_device_id = pci_config_get16(
685	    ohcip->ohci_config_handle, PCI_CONF_DEVID);
686	ohcip->ohci_rev_id = pci_config_get8(
687	    ohcip->ohci_config_handle, PCI_CONF_REVID);
688
689	/* Register interrupts */
690	if (ohci_register_intrs_and_init_mutex(ohcip) != DDI_SUCCESS) {
691		(void) ohci_cleanup(ohcip);
692
693		return (DDI_FAILURE);
694	}
695
696	mutex_enter(&ohcip->ohci_int_mutex);
697
698	/* Initialize the controller */
699	if (ohci_init_ctlr(ohcip) != DDI_SUCCESS) {
700		mutex_exit(&ohcip->ohci_int_mutex);
701		(void) ohci_cleanup(ohcip);
702
703		return (DDI_FAILURE);
704	}
705
706	/*
707	 * At this point, the hardware wiil be okay.
708	 * Initialize the usba_hcdi structure
709	 */
710	ohcip->ohci_hcdi_ops = ohci_alloc_hcdi_ops(ohcip);
711
712	mutex_exit(&ohcip->ohci_int_mutex);
713
714	/*
715	 * Make this HCD instance known to USBA
716	 * (dma_attr must be passed for USBA busctl's)
717	 */
718	hcdi_args.usba_hcdi_register_version = HCDI_REGISTER_VERSION;
719	hcdi_args.usba_hcdi_register_dip = dip;
720	hcdi_args.usba_hcdi_register_ops = ohcip->ohci_hcdi_ops;
721	hcdi_args.usba_hcdi_register_dma_attr = &ohcip->ohci_dma_attr;
722
723	/*
724	 * Priority and iblock_cookie are one and the same
725	 * (However, retaining hcdi_soft_iblock_cookie for now
726	 * assigning it w/ priority. In future all iblock_cookie
727	 * could just go)
728	 */
729	hcdi_args.usba_hcdi_register_iblock_cookie =
730	    (ddi_iblock_cookie_t)(uintptr_t)ohcip->ohci_intr_pri;
731
732	if (usba_hcdi_register(&hcdi_args, 0) != DDI_SUCCESS) {
733		(void) ohci_cleanup(ohcip);
734
735		return (DDI_FAILURE);
736	}
737	ohcip->ohci_flags |= OHCI_USBAREG;
738
739	mutex_enter(&ohcip->ohci_int_mutex);
740
741	if ((ohci_init_root_hub(ohcip)) != USB_SUCCESS) {
742		mutex_exit(&ohcip->ohci_int_mutex);
743		(void) ohci_cleanup(ohcip);
744
745		return (DDI_FAILURE);
746	}
747
748	mutex_exit(&ohcip->ohci_int_mutex);
749
750	/* Finally load the root hub driver */
751	if (ohci_load_root_hub_driver(ohcip) != USB_SUCCESS) {
752		(void) ohci_cleanup(ohcip);
753
754		return (DDI_FAILURE);
755	}
756	ohcip->ohci_flags |= OHCI_RHREG;
757
758	/* Display information in the banner */
759	ddi_report_dev(dip);
760
761	mutex_enter(&ohcip->ohci_int_mutex);
762
763	/* Reset the ohci initilization flag */
764	ohcip->ohci_flags &= ~OHCI_ATTACH;
765
766	/* Print the Host Control's Operational registers */
767	ohci_print_op_regs(ohcip);
768
769	/* For RIO we need to call pci_report_pmcap */
770	if (OHCI_IS_RIO(ohcip)) {
771
772		(void) pci_report_pmcap(dip, PCI_PM_IDLESPEED, (void *)4000);
773	}
774
775	mutex_exit(&ohcip->ohci_int_mutex);
776
777	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
778	    "ohci_attach: dip = 0x%p done", (void *)dip);
779
780	return (DDI_SUCCESS);
781}
782
783
784/*
785 * ohci_detach:
786 */
787int
788ohci_detach(dev_info_t *dip, ddi_detach_cmd_t cmd)
789{
790	ohci_state_t		*ohcip = ohci_obtain_state(dip);
791
792	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl, "ohci_detach:");
793
794	switch (cmd) {
795	case DDI_DETACH:
796
797		return (ohci_cleanup(ohcip));
798
799	case DDI_SUSPEND:
800
801		return (ohci_cpr_suspend(ohcip));
802	default:
803
804		return (DDI_FAILURE);
805	}
806}
807
808
809/*
810 * ohci_info:
811 */
812/* ARGSUSED */
813static int
814ohci_info(dev_info_t *dip, ddi_info_cmd_t infocmd, void *arg, void **result)
815{
816	dev_t			dev;
817	ohci_state_t		*ohcip;
818	int			instance;
819	int			error = DDI_FAILURE;
820
821	switch (infocmd) {
822	case DDI_INFO_DEVT2DEVINFO:
823		dev = (dev_t)arg;
824		instance = OHCI_UNIT(dev);
825		ohcip = ddi_get_soft_state(ohci_statep, instance);
826		if (ohcip != NULL) {
827			*result = (void *)ohcip->ohci_dip;
828			if (*result != NULL) {
829				error = DDI_SUCCESS;
830			}
831		} else {
832			*result = NULL;
833		}
834
835		break;
836	case DDI_INFO_DEVT2INSTANCE:
837		dev = (dev_t)arg;
838		instance = OHCI_UNIT(dev);
839		*result = (void *)(uintptr_t)instance;
840		error = DDI_SUCCESS;
841		break;
842	default:
843		break;
844	}
845
846	return (error);
847}
848
849
850/*
851 * cb_ops entry points
852 */
853static dev_info_t *
854ohci_get_dip(dev_t dev)
855{
856	int		instance = OHCI_UNIT(dev);
857	ohci_state_t	*ohcip = ddi_get_soft_state(ohci_statep, instance);
858
859	if (ohcip) {
860
861		return (ohcip->ohci_dip);
862	} else {
863
864		return (NULL);
865	}
866}
867
868
869static int
870ohci_open(dev_t *devp, int flags, int otyp, cred_t *credp)
871{
872	dev_info_t	*dip = ohci_get_dip(*devp);
873
874	return (usba_hubdi_open(dip, devp, flags, otyp, credp));
875}
876
877
878static int
879ohci_close(dev_t dev, int flag, int otyp, cred_t *credp)
880{
881	dev_info_t	*dip = ohci_get_dip(dev);
882
883	return (usba_hubdi_close(dip, dev, flag, otyp, credp));
884}
885
886
887static int
888ohci_ioctl(dev_t dev, int cmd, intptr_t arg, int mode, cred_t *credp,
889    int *rvalp)
890{
891	dev_info_t	*dip = ohci_get_dip(dev);
892
893	return (usba_hubdi_ioctl(dip,
894	    dev, cmd, arg, mode, credp, rvalp));
895}
896
897
898/*
899 * Host Controller Driver (HCD) initialization functions
900 */
901
902/*
903 * ohci_set_dma_attributes:
904 *
905 * Set the limits in the DMA attributes structure. Most of the values used
906 * in the  DMA limit structres are the default values as specified by  the
907 * Writing PCI device drivers document.
908 */
909static void
910ohci_set_dma_attributes(ohci_state_t	*ohcip)
911{
912	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
913	    "ohci_set_dma_attributes:");
914
915	/* Initialize the DMA attributes */
916	ohcip->ohci_dma_attr.dma_attr_version = DMA_ATTR_V0;
917	ohcip->ohci_dma_attr.dma_attr_addr_lo = 0x00000000ull;
918	ohcip->ohci_dma_attr.dma_attr_addr_hi = 0xfffffffeull;
919
920	/* 32 bit addressing */
921	ohcip->ohci_dma_attr.dma_attr_count_max = OHCI_DMA_ATTR_COUNT_MAX;
922
923	/* Byte alignment */
924	ohcip->ohci_dma_attr.dma_attr_align = OHCI_DMA_ATTR_ALIGNMENT;
925
926	/*
927	 * Since PCI  specification is byte alignment, the
928	 * burstsize field should be set to 1 for PCI devices.
929	 */
930	ohcip->ohci_dma_attr.dma_attr_burstsizes = 0x1;
931
932	ohcip->ohci_dma_attr.dma_attr_minxfer = 0x1;
933	ohcip->ohci_dma_attr.dma_attr_maxxfer = OHCI_DMA_ATTR_MAX_XFER;
934	ohcip->ohci_dma_attr.dma_attr_seg = 0xffffffffull;
935	ohcip->ohci_dma_attr.dma_attr_sgllen = 1;
936	ohcip->ohci_dma_attr.dma_attr_granular = OHCI_DMA_ATTR_GRANULAR;
937	ohcip->ohci_dma_attr.dma_attr_flags = 0;
938}
939
940
941/*
942 * ohci_allocate_pools:
943 *
944 * Allocate the system memory for the Endpoint Descriptor (ED) and for the
945 * Transfer Descriptor (TD) pools. Both ED and TD structures must be aligned
946 * to a 16 byte boundary.
947 */
948static int
949ohci_allocate_pools(ohci_state_t	*ohcip)
950{
951	ddi_device_acc_attr_t		dev_attr;
952	size_t				real_length;
953	int				result;
954	uint_t				ccount;
955	int				i;
956
957	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
958	    "ohci_allocate_pools:");
959
960	/* The host controller will be little endian */
961	dev_attr.devacc_attr_version	= DDI_DEVICE_ATTR_V0;
962	dev_attr.devacc_attr_endian_flags  = DDI_STRUCTURE_LE_ACC;
963	dev_attr.devacc_attr_dataorder	= DDI_STRICTORDER_ACC;
964
965	/* Byte alignment to TD alignment */
966	ohcip->ohci_dma_attr.dma_attr_align = OHCI_DMA_ATTR_TD_ALIGNMENT;
967
968	/* Allocate the TD pool DMA handle */
969	if (ddi_dma_alloc_handle(ohcip->ohci_dip, &ohcip->ohci_dma_attr,
970	    DDI_DMA_SLEEP, 0,
971	    &ohcip->ohci_td_pool_dma_handle) != DDI_SUCCESS) {
972
973		return (DDI_FAILURE);
974	}
975
976	/* Allocate the memory for the TD pool */
977	if (ddi_dma_mem_alloc(ohcip->ohci_td_pool_dma_handle,
978	    ohci_td_pool_size * sizeof (ohci_td_t),
979	    &dev_attr,
980	    DDI_DMA_CONSISTENT,
981	    DDI_DMA_SLEEP,
982	    0,
983	    (caddr_t *)&ohcip->ohci_td_pool_addr,
984	    &real_length,
985	    &ohcip->ohci_td_pool_mem_handle)) {
986
987		return (DDI_FAILURE);
988	}
989
990	/* Map the TD pool into the I/O address space */
991	result = ddi_dma_addr_bind_handle(
992	    ohcip->ohci_td_pool_dma_handle,
993	    NULL,
994	    (caddr_t)ohcip->ohci_td_pool_addr,
995	    real_length,
996	    DDI_DMA_RDWR | DDI_DMA_CONSISTENT,
997	    DDI_DMA_SLEEP,
998	    NULL,
999	    &ohcip->ohci_td_pool_cookie,
1000	    &ccount);
1001
1002	bzero((void *)ohcip->ohci_td_pool_addr,
1003	    ohci_td_pool_size * sizeof (ohci_td_t));
1004
1005	/* Process the result */
1006	if (result == DDI_DMA_MAPPED) {
1007		/* The cookie count should be 1 */
1008		if (ccount != 1) {
1009			USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1010			    "ohci_allocate_pools: More than 1 cookie");
1011
1012			return (DDI_FAILURE);
1013		}
1014	} else {
1015		USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1016		    "ohci_allocate_pools: Result = %d", result);
1017
1018		ohci_decode_ddi_dma_addr_bind_handle_result(ohcip, result);
1019
1020		return (DDI_FAILURE);
1021	}
1022
1023	/*
1024	 * DMA addresses for TD pools are bound
1025	 */
1026	ohcip->ohci_dma_addr_bind_flag |= OHCI_TD_POOL_BOUND;
1027
1028	/* Initialize the TD pool */
1029	for (i = 0; i < ohci_td_pool_size; i ++) {
1030		Set_TD(ohcip->ohci_td_pool_addr[i].hctd_state, HC_TD_FREE);
1031	}
1032
1033	/* Byte alignment to ED alignment */
1034	ohcip->ohci_dma_attr.dma_attr_align = OHCI_DMA_ATTR_ED_ALIGNMENT;
1035
1036	/* Allocate the ED pool DMA handle */
1037	if (ddi_dma_alloc_handle(ohcip->ohci_dip,
1038	    &ohcip->ohci_dma_attr,
1039	    DDI_DMA_SLEEP,
1040	    0,
1041	    &ohcip->ohci_ed_pool_dma_handle) != DDI_SUCCESS) {
1042
1043		return (DDI_FAILURE);
1044	}
1045
1046	/* Allocate the memory for the ED pool */
1047	if (ddi_dma_mem_alloc(ohcip->ohci_ed_pool_dma_handle,
1048	    ohci_ed_pool_size * sizeof (ohci_ed_t),
1049	    &dev_attr,
1050	    DDI_DMA_CONSISTENT,
1051	    DDI_DMA_SLEEP,
1052	    0,
1053	    (caddr_t *)&ohcip->ohci_ed_pool_addr,
1054	    &real_length,
1055	    &ohcip->ohci_ed_pool_mem_handle) != DDI_SUCCESS) {
1056
1057		return (DDI_FAILURE);
1058	}
1059
1060	result = ddi_dma_addr_bind_handle(ohcip->ohci_ed_pool_dma_handle,
1061	    NULL,
1062	    (caddr_t)ohcip->ohci_ed_pool_addr,
1063	    real_length,
1064	    DDI_DMA_RDWR | DDI_DMA_CONSISTENT,
1065	    DDI_DMA_SLEEP,
1066	    NULL,
1067	    &ohcip->ohci_ed_pool_cookie,
1068	    &ccount);
1069
1070	bzero((void *)ohcip->ohci_ed_pool_addr,
1071	    ohci_ed_pool_size * sizeof (ohci_ed_t));
1072
1073	/* Process the result */
1074	if (result == DDI_DMA_MAPPED) {
1075		/* The cookie count should be 1 */
1076		if (ccount != 1) {
1077			USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1078			    "ohci_allocate_pools: More than 1 cookie");
1079
1080			return (DDI_FAILURE);
1081		}
1082	} else {
1083		ohci_decode_ddi_dma_addr_bind_handle_result(ohcip, result);
1084
1085		return (DDI_FAILURE);
1086	}
1087
1088	/*
1089	 * DMA addresses for ED pools are bound
1090	 */
1091	ohcip->ohci_dma_addr_bind_flag |= OHCI_ED_POOL_BOUND;
1092
1093	/* Initialize the ED pool */
1094	for (i = 0; i < ohci_ed_pool_size; i ++) {
1095		Set_ED(ohcip->ohci_ed_pool_addr[i].hced_state, HC_EPT_FREE);
1096	}
1097
1098	return (DDI_SUCCESS);
1099}
1100
1101
1102/*
1103 * ohci_decode_ddi_dma_addr_bind_handle_result:
1104 *
1105 * Process the return values of ddi_dma_addr_bind_handle()
1106 */
1107static void
1108ohci_decode_ddi_dma_addr_bind_handle_result(
1109	ohci_state_t	*ohcip,
1110	int		result)
1111{
1112	USB_DPRINTF_L2(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
1113	    "ohci_decode_ddi_dma_addr_bind_handle_result:");
1114
1115	switch (result) {
1116	case DDI_DMA_PARTIAL_MAP:
1117		USB_DPRINTF_L2(PRINT_MASK_ALL, ohcip->ohci_log_hdl,
1118		    "Partial transfers not allowed");
1119		break;
1120	case DDI_DMA_INUSE:
1121		USB_DPRINTF_L2(PRINT_MASK_ALL,	ohcip->ohci_log_hdl,
1122		    "Handle is in use");
1123		break;
1124	case DDI_DMA_NORESOURCES:
1125		USB_DPRINTF_L2(PRINT_MASK_ALL,	ohcip->ohci_log_hdl,
1126		    "No resources");
1127		break;
1128	case DDI_DMA_NOMAPPING:
1129		USB_DPRINTF_L2(PRINT_MASK_ALL,	ohcip->ohci_log_hdl,
1130		    "No mapping");
1131		break;
1132	case DDI_DMA_TOOBIG:
1133		USB_DPRINTF_L2(PRINT_MASK_ALL,	ohcip->ohci_log_hdl,
1134		    "Object is too big");
1135		break;
1136	default:
1137		USB_DPRINTF_L2(PRINT_MASK_ALL,	ohcip->ohci_log_hdl,
1138		    "Unknown dma error");
1139	}
1140}
1141
1142
1143/*
1144 * ohci_map_regs:
1145 *
1146 * The Host Controller (HC) contains a set of on-chip operational registers
1147 * and which should be mapped into a non-cacheable portion of the  system
1148 * addressable space.
1149 */
1150static int
1151ohci_map_regs(ohci_state_t	*ohcip)
1152{
1153	ddi_device_acc_attr_t	attr;
1154	uint16_t		cmd_reg;
1155
1156	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl, "ohci_map_regs:");
1157
1158	/* The host controller will be little endian */
1159	attr.devacc_attr_version = DDI_DEVICE_ATTR_V0;
1160	attr.devacc_attr_endian_flags  = DDI_STRUCTURE_LE_ACC;
1161	attr.devacc_attr_dataorder = DDI_STRICTORDER_ACC;
1162
1163	/* Map in operational registers */
1164	if (ddi_regs_map_setup(ohcip->ohci_dip, 1,
1165	    (caddr_t *)&ohcip->ohci_regsp, 0,
1166	    sizeof (ohci_regs_t), &attr,
1167	    &ohcip->ohci_regs_handle) != DDI_SUCCESS) {
1168
1169		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1170		    "ohci_map_regs: Map setup error");
1171
1172		return (DDI_FAILURE);
1173	}
1174
1175	if (pci_config_setup(ohcip->ohci_dip,
1176	    &ohcip->ohci_config_handle) != DDI_SUCCESS) {
1177
1178		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1179		    "ohci_map_regs: Config error");
1180
1181		return (DDI_FAILURE);
1182	}
1183
1184	/* Make sure Memory Access Enable and Master Enable are set */
1185	cmd_reg = pci_config_get16(ohcip->ohci_config_handle, PCI_CONF_COMM);
1186
1187	if (!(cmd_reg & PCI_COMM_MAE)) {
1188
1189		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1190		    "ohci_map_regs: Memory base address access disabled");
1191
1192		return (DDI_FAILURE);
1193	}
1194
1195	cmd_reg |= (PCI_COMM_MAE | PCI_COMM_ME);
1196
1197	pci_config_put16(ohcip->ohci_config_handle, PCI_CONF_COMM, cmd_reg);
1198
1199	return (DDI_SUCCESS);
1200}
1201
1202/*
1203 * The following simulated polling is for debugging purposes only.
1204 * It is activated on x86 by setting usb-polling=true in GRUB or ohci.conf.
1205 */
1206static int
1207ohci_is_polled(dev_info_t *dip)
1208{
1209	int ret;
1210	char *propval;
1211
1212	if (ddi_prop_lookup_string(DDI_DEV_T_ANY, dip, 0,
1213	    "usb-polling", &propval) != DDI_SUCCESS)
1214
1215		return (0);
1216
1217	ret = (strcmp(propval, "true") == 0);
1218	ddi_prop_free(propval);
1219
1220	return (ret);
1221}
1222
1223static void
1224ohci_poll_intr(void *arg)
1225{
1226	/* poll every millisecond */
1227	for (;;) {
1228		(void) ohci_intr(arg, NULL);
1229		delay(drv_usectohz(1000));
1230	}
1231}
1232
1233/*
1234 * ohci_register_intrs_and_init_mutex:
1235 *
1236 * Register interrupts and initialize each mutex and condition variables
1237 */
1238static int
1239ohci_register_intrs_and_init_mutex(ohci_state_t	*ohcip)
1240{
1241	int	intr_types;
1242
1243	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1244	    "ohci_register_intrs_and_init_mutex:");
1245
1246	/*
1247	 * Sometimes the OHCI controller of ULI1575 southbridge
1248	 * could not receive SOF intrs when enable MSI. Hence
1249	 * MSI is disabled for this chip.
1250	 */
1251	if ((ohcip->ohci_vendor_id == PCI_ULI1575_VENID) &&
1252	    (ohcip->ohci_device_id == PCI_ULI1575_DEVID)) {
1253		ohcip->ohci_msi_enabled = B_FALSE;
1254	} else {
1255		ohcip->ohci_msi_enabled = ohci_enable_msi;
1256	}
1257
1258	if (ohci_is_polled(ohcip->ohci_dip)) {
1259		extern pri_t maxclsyspri;
1260
1261		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1262		    "ohci_register_intrs_and_init_mutex: "
1263		    "running in simulated polled mode");
1264
1265		(void) thread_create(NULL, 0, ohci_poll_intr, ohcip, 0, &p0,
1266		    TS_RUN, maxclsyspri);
1267
1268		goto skip_intr;
1269	}
1270
1271	/* Get supported interrupt types */
1272	if (ddi_intr_get_supported_types(ohcip->ohci_dip,
1273	    &intr_types) != DDI_SUCCESS) {
1274		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1275		    "ohci_register_intrs_and_init_mutex: "
1276		    "ddi_intr_get_supported_types failed");
1277
1278		return (DDI_FAILURE);
1279	}
1280
1281	USB_DPRINTF_L3(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1282	    "ohci_register_intrs_and_init_mutex: "
1283	    "supported interrupt types 0x%x", intr_types);
1284
1285	if ((intr_types & DDI_INTR_TYPE_MSI) && ohcip->ohci_msi_enabled) {
1286		if (ohci_add_intrs(ohcip, DDI_INTR_TYPE_MSI)
1287		    != DDI_SUCCESS) {
1288			USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1289			    "ohci_register_intrs_and_init_mutex: MSI "
1290			    "registration failed, trying FIXED interrupt \n");
1291		} else {
1292			USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1293			    "ohci_register_intrs_and_init_mutex: "
1294			    "Using MSI interrupt type\n");
1295
1296			ohcip->ohci_intr_type = DDI_INTR_TYPE_MSI;
1297			ohcip->ohci_flags |= OHCI_INTR;
1298		}
1299	}
1300
1301	if ((!(ohcip->ohci_flags & OHCI_INTR)) &&
1302	    (intr_types & DDI_INTR_TYPE_FIXED)) {
1303		if (ohci_add_intrs(ohcip, DDI_INTR_TYPE_FIXED)
1304		    != DDI_SUCCESS) {
1305			USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1306			    "ohci_register_intrs_and_init_mutex: "
1307			    "FIXED interrupt registration failed\n");
1308
1309			return (DDI_FAILURE);
1310		}
1311
1312		USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1313		    "ohci_register_intrs_and_init_mutex: "
1314		    "Using FIXED interrupt type\n");
1315
1316		ohcip->ohci_intr_type = DDI_INTR_TYPE_FIXED;
1317		ohcip->ohci_flags |= OHCI_INTR;
1318	}
1319
1320skip_intr:
1321	/* Create prototype for SOF condition variable */
1322	cv_init(&ohcip->ohci_SOF_cv, NULL, CV_DRIVER, NULL);
1323
1324	/* Semaphore to serialize opens and closes */
1325	sema_init(&ohcip->ohci_ocsem, 1, NULL, SEMA_DRIVER, NULL);
1326
1327	return (DDI_SUCCESS);
1328}
1329
1330
1331/*
1332 * ohci_add_intrs:
1333 *
1334 * Register FIXED or MSI interrupts.
1335 */
1336static int
1337ohci_add_intrs(ohci_state_t *ohcip, int intr_type)
1338{
1339	int	actual, avail, intr_size, count = 0;
1340	int	i, flag, ret;
1341
1342	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1343	    "ohci_add_intrs: interrupt type 0x%x", intr_type);
1344
1345	/* Get number of interrupts */
1346	ret = ddi_intr_get_nintrs(ohcip->ohci_dip, intr_type, &count);
1347	if ((ret != DDI_SUCCESS) || (count == 0)) {
1348		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1349		    "ohci_add_intrs: ddi_intr_get_nintrs() failure, "
1350		    "ret: %d, count: %d", ret, count);
1351
1352		return (DDI_FAILURE);
1353	}
1354
1355	/* Get number of available interrupts */
1356	ret = ddi_intr_get_navail(ohcip->ohci_dip, intr_type, &avail);
1357	if ((ret != DDI_SUCCESS) || (avail == 0)) {
1358		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1359		    "ohci_add_intrs: ddi_intr_get_navail() failure, "
1360		    "ret: %d, count: %d", ret, count);
1361
1362		return (DDI_FAILURE);
1363	}
1364
1365	if (avail < count) {
1366		USB_DPRINTF_L3(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1367		    "ohci_add_intrs: ohci_add_intrs: nintrs () "
1368		    "returned %d, navail returned %d\n", count, avail);
1369	}
1370
1371	/* Allocate an array of interrupt handles */
1372	intr_size = count * sizeof (ddi_intr_handle_t);
1373	ohcip->ohci_htable = kmem_zalloc(intr_size, KM_SLEEP);
1374
1375	flag = (intr_type == DDI_INTR_TYPE_MSI) ?
1376	    DDI_INTR_ALLOC_STRICT:DDI_INTR_ALLOC_NORMAL;
1377
1378	/* call ddi_intr_alloc() */
1379	ret = ddi_intr_alloc(ohcip->ohci_dip, ohcip->ohci_htable,
1380	    intr_type, 0, count, &actual, flag);
1381
1382	if ((ret != DDI_SUCCESS) || (actual == 0)) {
1383		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1384		    "ohci_add_intrs: ddi_intr_alloc() failed %d", ret);
1385
1386		kmem_free(ohcip->ohci_htable, intr_size);
1387
1388		return (DDI_FAILURE);
1389	}
1390
1391	if (actual < count) {
1392		USB_DPRINTF_L3(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1393		    "ohci_add_intrs: Requested: %d, Received: %d\n",
1394		    count, actual);
1395
1396		for (i = 0; i < actual; i++)
1397			(void) ddi_intr_free(ohcip->ohci_htable[i]);
1398
1399		kmem_free(ohcip->ohci_htable, intr_size);
1400
1401		return (DDI_FAILURE);
1402	}
1403
1404	ohcip->ohci_intr_cnt = actual;
1405
1406	if ((ret = ddi_intr_get_pri(ohcip->ohci_htable[0],
1407	    &ohcip->ohci_intr_pri)) != DDI_SUCCESS) {
1408		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1409		    "ohci_add_intrs: ddi_intr_get_pri() failed %d", ret);
1410
1411		for (i = 0; i < actual; i++)
1412			(void) ddi_intr_free(ohcip->ohci_htable[i]);
1413
1414		kmem_free(ohcip->ohci_htable, intr_size);
1415
1416		return (DDI_FAILURE);
1417	}
1418
1419	USB_DPRINTF_L3(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1420	    "ohci_add_intrs: Supported Interrupt priority 0x%x",
1421	    ohcip->ohci_intr_pri);
1422
1423	/* Test for high level mutex */
1424	if (ohcip->ohci_intr_pri >= ddi_intr_get_hilevel_pri()) {
1425		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1426		    "ohci_add_intrs: Hi level interrupt not supported");
1427
1428		for (i = 0; i < actual; i++)
1429			(void) ddi_intr_free(ohcip->ohci_htable[i]);
1430
1431		kmem_free(ohcip->ohci_htable, intr_size);
1432
1433		return (DDI_FAILURE);
1434	}
1435
1436	/* Initialize the mutex */
1437	mutex_init(&ohcip->ohci_int_mutex, NULL, MUTEX_DRIVER,
1438	    DDI_INTR_PRI(ohcip->ohci_intr_pri));
1439
1440	/* Call ddi_intr_add_handler() */
1441	for (i = 0; i < actual; i++) {
1442		if ((ret = ddi_intr_add_handler(ohcip->ohci_htable[i],
1443		    ohci_intr, (caddr_t)ohcip,
1444		    (caddr_t)(uintptr_t)i)) != DDI_SUCCESS) {
1445			USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1446			    "ohci_add_intrs: ddi_intr_add_handler() "
1447			    "failed %d", ret);
1448
1449			for (i = 0; i < actual; i++)
1450				(void) ddi_intr_free(ohcip->ohci_htable[i]);
1451
1452			mutex_destroy(&ohcip->ohci_int_mutex);
1453			kmem_free(ohcip->ohci_htable, intr_size);
1454
1455			return (DDI_FAILURE);
1456		}
1457	}
1458
1459	if ((ret = ddi_intr_get_cap(ohcip->ohci_htable[0],
1460	    &ohcip->ohci_intr_cap)) != DDI_SUCCESS) {
1461		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1462		    "ohci_add_intrs: ddi_intr_get_cap() failed %d", ret);
1463
1464		for (i = 0; i < actual; i++) {
1465			(void) ddi_intr_remove_handler(ohcip->ohci_htable[i]);
1466			(void) ddi_intr_free(ohcip->ohci_htable[i]);
1467		}
1468
1469		mutex_destroy(&ohcip->ohci_int_mutex);
1470		kmem_free(ohcip->ohci_htable, intr_size);
1471
1472		return (DDI_FAILURE);
1473	}
1474
1475	/* Enable all interrupts */
1476	if (ohcip->ohci_intr_cap & DDI_INTR_FLAG_BLOCK) {
1477		/* Call ddi_intr_block_enable() for MSI interrupts */
1478		(void) ddi_intr_block_enable(ohcip->ohci_htable,
1479		    ohcip->ohci_intr_cnt);
1480	} else {
1481		/* Call ddi_intr_enable for MSI or FIXED interrupts */
1482		for (i = 0; i < ohcip->ohci_intr_cnt; i++)
1483			(void) ddi_intr_enable(ohcip->ohci_htable[i]);
1484	}
1485
1486	return (DDI_SUCCESS);
1487}
1488
1489
1490/*
1491 * ohci_init_ctlr:
1492 *
1493 * Initialize the Host Controller (HC).
1494 */
1495static int
1496ohci_init_ctlr(ohci_state_t	*ohcip)
1497{
1498	int			revision, curr_control, max_packet = 0;
1499	clock_t			sof_time_wait;
1500	int			retry = 0;
1501	int			ohci_frame_interval;
1502
1503	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl, "ohci_init_ctlr:");
1504
1505	if (ohci_take_control(ohcip) != DDI_SUCCESS) {
1506		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1507		    "ohci_init_ctlr: ohci_take_control failed\n");
1508
1509		return (DDI_FAILURE);
1510	}
1511
1512	/*
1513	 * Soft reset the host controller.
1514	 *
1515	 * On soft reset, the ohci host controller moves to the
1516	 * USB Suspend state in which most of the ohci operational
1517	 * registers are reset except stated ones. The soft reset
1518	 * doesn't cause a reset to the ohci root hub and even no
1519	 * subsequent reset signaling should be asserterd to its
1520	 * down stream.
1521	 */
1522	Set_OpReg(hcr_cmd_status, HCR_STATUS_RESET);
1523
1524	mutex_exit(&ohcip->ohci_int_mutex);
1525	/* Wait 10ms for reset to complete */
1526	delay(drv_usectohz(OHCI_RESET_TIMEWAIT));
1527	mutex_enter(&ohcip->ohci_int_mutex);
1528
1529	/*
1530	 * Do hard reset the host controller.
1531	 *
1532	 * Now perform USB reset in order to reset the ohci root
1533	 * hub.
1534	 */
1535	Set_OpReg(hcr_control, HCR_CONTROL_RESET);
1536
1537	/*
1538	 * According to Section 5.1.2.3 of the specification, the
1539	 * host controller will go into suspend state immediately
1540	 * after the reset.
1541	 */
1542
1543	/* Verify the version number */
1544	revision = Get_OpReg(hcr_revision);
1545
1546	if ((revision & HCR_REVISION_MASK) != HCR_REVISION_1_0) {
1547
1548		return (DDI_FAILURE);
1549	}
1550
1551	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1552	    "ohci_init_ctlr: Revision verified");
1553
1554	/* hcca area need not be initialized on resume */
1555	if (ohcip->ohci_hc_soft_state == OHCI_CTLR_INIT_STATE) {
1556
1557		/* Initialize the hcca area */
1558		if (ohci_init_hcca(ohcip) != DDI_SUCCESS) {
1559
1560			return (DDI_FAILURE);
1561		}
1562	}
1563
1564	/*
1565	 * Workaround for ULI1575 chipset. Following OHCI Operational Memory
1566	 * Registers are not cleared to their default value on reset.
1567	 * Explicitly set the registers to default value.
1568	 */
1569	if (ohcip->ohci_vendor_id == PCI_ULI1575_VENID &&
1570	    ohcip->ohci_device_id == PCI_ULI1575_DEVID) {
1571		Set_OpReg(hcr_control, HCR_CONTROL_DEFAULT);
1572		Set_OpReg(hcr_intr_enable, HCR_INT_ENABLE_DEFAULT);
1573		Set_OpReg(hcr_HCCA, HCR_HCCA_DEFAULT);
1574		Set_OpReg(hcr_ctrl_head, HCR_CONTROL_HEAD_ED_DEFAULT);
1575		Set_OpReg(hcr_bulk_head, HCR_BULK_HEAD_ED_DEFAULT);
1576		Set_OpReg(hcr_frame_interval, HCR_FRAME_INTERVAL_DEFAULT);
1577		Set_OpReg(hcr_periodic_strt, HCR_PERIODIC_START_DEFAULT);
1578	}
1579
1580	/* Set the HcHCCA to the physical address of the HCCA block */
1581	Set_OpReg(hcr_HCCA, (uint_t)ohcip->ohci_hcca_cookie.dmac_address);
1582
1583	/*
1584	 * Set HcInterruptEnable to enable all interrupts except Root
1585	 * Hub Status change and SOF interrupts.
1586	 */
1587	Set_OpReg(hcr_intr_enable, HCR_INTR_SO | HCR_INTR_WDH |
1588	    HCR_INTR_RD | HCR_INTR_UE | HCR_INTR_FNO | HCR_INTR_MIE);
1589
1590	/*
1591	 * For non-periodic transfers, reserve atleast for one low-speed
1592	 * device transaction. According to USB Bandwidth Analysis white
1593	 * paper and also as per OHCI Specification 1.0a, section 7.3.5,
1594	 * page 123, one low-speed transaction takes 0x628h full speed
1595	 * bits (197 bytes), which comes to around 13% of USB frame time.
1596	 *
1597	 * The periodic transfers will get around 87% of USB frame time.
1598	 */
1599	Set_OpReg(hcr_periodic_strt,
1600	    ((PERIODIC_XFER_STARTS * BITS_PER_BYTE) - 1));
1601
1602	/* Save the contents of the Frame Interval Registers */
1603	ohcip->ohci_frame_interval = Get_OpReg(hcr_frame_interval);
1604
1605	/*
1606	 * Initialize the FSLargestDataPacket value in the frame interval
1607	 * register. The controller compares the value of MaxPacketSize to
1608	 * this value to see if the entire packet may be sent out before
1609	 * the EOF.
1610	 */
1611	max_packet = ((((ohcip->ohci_frame_interval -
1612	    MAX_OVERHEAD) * 6) / 7) << HCR_FRME_FSMPS_SHFT);
1613
1614	Set_OpReg(hcr_frame_interval,
1615	    (max_packet | ohcip->ohci_frame_interval));
1616
1617	/*
1618	 * Sometimes the HcFmInterval register in OHCI controller does not
1619	 * maintain its value after the first write. This problem is found
1620	 * on ULI M1575 South Bridge. To workaround the hardware problem,
1621	 * check the value after write and retry if the last write failed.
1622	 */
1623	if (ohcip->ohci_vendor_id == PCI_ULI1575_VENID &&
1624	    ohcip->ohci_device_id == PCI_ULI1575_DEVID) {
1625		ohci_frame_interval = Get_OpReg(hcr_frame_interval);
1626		while ((ohci_frame_interval != (max_packet |
1627		    ohcip->ohci_frame_interval))) {
1628			if (retry >= 10) {
1629				USB_DPRINTF_L1(PRINT_MASK_ATTA,
1630				    ohcip->ohci_log_hdl, "Failed to program"
1631				    " Frame Interval Register.");
1632
1633				return (DDI_FAILURE);
1634			}
1635			retry++;
1636			USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1637			    "ohci_init_ctlr: Failed to program Frame"
1638			    " Interval Register, retry=%d", retry);
1639			Set_OpReg(hcr_frame_interval,
1640			    (max_packet | ohcip->ohci_frame_interval));
1641			ohci_frame_interval = Get_OpReg(hcr_frame_interval);
1642		}
1643	}
1644
1645	/* Begin sending SOFs */
1646	curr_control = Get_OpReg(hcr_control);
1647
1648	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1649	    "ohci_init_ctlr: curr_control=0x%x", curr_control);
1650
1651	/* Set the state to operational */
1652	curr_control = (curr_control &
1653	    (~HCR_CONTROL_HCFS)) | HCR_CONTROL_OPERAT;
1654
1655	Set_OpReg(hcr_control, curr_control);
1656
1657	ASSERT((Get_OpReg(hcr_control) &
1658	    HCR_CONTROL_HCFS) == HCR_CONTROL_OPERAT);
1659
1660	/* Set host controller soft state to operational */
1661	ohcip->ohci_hc_soft_state = OHCI_CTLR_OPERATIONAL_STATE;
1662
1663	/* Get the number of clock ticks to wait */
1664	sof_time_wait = drv_usectohz(OHCI_MAX_SOF_TIMEWAIT * 1000000);
1665
1666	/* Clear ohci_sof_flag indicating waiting for SOF interrupt */
1667	ohcip->ohci_sof_flag = B_FALSE;
1668
1669	/* Enable the SOF interrupt */
1670	Set_OpReg(hcr_intr_enable, HCR_INTR_SOF);
1671
1672	ASSERT(Get_OpReg(hcr_intr_enable) & HCR_INTR_SOF);
1673
1674	(void) cv_reltimedwait(&ohcip->ohci_SOF_cv,
1675	    &ohcip->ohci_int_mutex, sof_time_wait, TR_CLOCK_TICK);
1676
1677	/* Wait for the SOF or timeout event */
1678	if (ohcip->ohci_sof_flag == B_FALSE) {
1679
1680		/* Set host controller soft state to error */
1681		ohcip->ohci_hc_soft_state = OHCI_CTLR_ERROR_STATE;
1682
1683		USB_DPRINTF_L0(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1684		    "No SOF interrupts have been received, this USB OHCI host"
1685		    "controller is unusable");
1686		return (DDI_FAILURE);
1687	}
1688
1689	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1690	    "ohci_init_ctlr: SOF's have started");
1691
1692	return (DDI_SUCCESS);
1693}
1694
1695
1696/*
1697 * ohci_init_hcca:
1698 *
1699 * Allocate the system memory and initialize Host Controller Communication
1700 * Area (HCCA). The HCCA structure must be aligned to a 256-byte boundary.
1701 */
1702static int
1703ohci_init_hcca(ohci_state_t	*ohcip)
1704{
1705	ddi_device_acc_attr_t	dev_attr;
1706	size_t			real_length;
1707	uint_t			mask, ccount;
1708	int			result;
1709	uintptr_t		addr;
1710
1711	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
1712
1713	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl, "ohci_init_hcca:");
1714
1715	/* The host controller will be little endian */
1716	dev_attr.devacc_attr_version = DDI_DEVICE_ATTR_V0;
1717	dev_attr.devacc_attr_endian_flags  = DDI_STRUCTURE_LE_ACC;
1718	dev_attr.devacc_attr_dataorder = DDI_STRICTORDER_ACC;
1719
1720	/* Byte alignment to HCCA alignment */
1721	ohcip->ohci_dma_attr.dma_attr_align = OHCI_DMA_ATTR_HCCA_ALIGNMENT;
1722
1723	/* Create space for the HCCA block */
1724	if (ddi_dma_alloc_handle(ohcip->ohci_dip, &ohcip->ohci_dma_attr,
1725	    DDI_DMA_SLEEP,
1726	    0,
1727	    &ohcip->ohci_hcca_dma_handle)
1728	    != DDI_SUCCESS) {
1729
1730		return (DDI_FAILURE);
1731	}
1732
1733	if (ddi_dma_mem_alloc(ohcip->ohci_hcca_dma_handle,
1734	    2 * sizeof (ohci_hcca_t),
1735	    &dev_attr,
1736	    DDI_DMA_CONSISTENT,
1737	    DDI_DMA_SLEEP,
1738	    0,
1739	    (caddr_t *)&ohcip->ohci_hccap,
1740	    &real_length,
1741	    &ohcip->ohci_hcca_mem_handle)) {
1742
1743		return (DDI_FAILURE);
1744	}
1745
1746	bzero((void *)ohcip->ohci_hccap, real_length);
1747
1748	/* Figure out the alignment requirements */
1749	Set_OpReg(hcr_HCCA, 0xFFFFFFFF);
1750
1751	/*
1752	 * Read the hcr_HCCA register until
1753	 * contenets are non-zero.
1754	 */
1755	mask = Get_OpReg(hcr_HCCA);
1756
1757	mutex_exit(&ohcip->ohci_int_mutex);
1758	while (mask == 0) {
1759		delay(drv_usectohz(OHCI_TIMEWAIT));
1760		mask = Get_OpReg(hcr_HCCA);
1761	}
1762	mutex_enter(&ohcip->ohci_int_mutex);
1763
1764	ASSERT(mask != 0);
1765
1766	addr = (uintptr_t)ohcip->ohci_hccap;
1767
1768	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1769	    "ohci_init_hcca: addr=0x%lx, mask=0x%x", addr, mask);
1770
1771	while (addr & (~mask)) {
1772		addr++;
1773	}
1774
1775	ohcip->ohci_hccap = (ohci_hcca_t *)addr;
1776
1777	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1778	    "ohci_init_hcca: Real length %lu", real_length);
1779
1780	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1781	    "ohci_init_hcca: virtual hcca 0x%p", (void *)ohcip->ohci_hccap);
1782
1783	/* Map the whole HCCA into the I/O address space */
1784	result = ddi_dma_addr_bind_handle(ohcip->ohci_hcca_dma_handle,
1785	    NULL,
1786	    (caddr_t)ohcip->ohci_hccap,
1787	    real_length,
1788	    DDI_DMA_RDWR | DDI_DMA_CONSISTENT,
1789	    DDI_DMA_SLEEP, NULL,
1790	    &ohcip->ohci_hcca_cookie,
1791	    &ccount);
1792
1793	if (result == DDI_DMA_MAPPED) {
1794		/* The cookie count should be 1 */
1795		if (ccount != 1) {
1796			USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1797			    "ohci_init_hcca: More than 1 cookie");
1798
1799			return (DDI_FAILURE);
1800		}
1801	} else {
1802		ohci_decode_ddi_dma_addr_bind_handle_result(ohcip, result);
1803
1804		return (DDI_FAILURE);
1805	}
1806
1807	/*
1808	 * DMA addresses for HCCA are bound
1809	 */
1810	ohcip->ohci_dma_addr_bind_flag |= OHCI_HCCA_DMA_BOUND;
1811
1812	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1813	    "ohci_init_hcca: physical 0x%p",
1814	    (void *)(uintptr_t)ohcip->ohci_hcca_cookie.dmac_address);
1815
1816	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1817	    "ohci_init_hcca: size %lu", ohcip->ohci_hcca_cookie.dmac_size);
1818
1819	/* Initialize the interrupt lists */
1820	ohci_build_interrupt_lattice(ohcip);
1821
1822	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1823	    "ohci_init_hcca: End");
1824
1825	return (DDI_SUCCESS);
1826}
1827
1828
1829/*
1830 * ohci_build_interrupt_lattice:
1831 *
1832 * Construct the interrupt lattice tree using static Endpoint Descriptors
1833 * (ED). This interrupt lattice tree will have total of 32 interrupt  ED
1834 * lists and the Host Controller (HC) processes one interrupt ED list in
1835 * every frame. The lower five bits of the current frame number indexes
1836 * into an array of 32 interrupt Endpoint Descriptor lists found in the
1837 * HCCA.
1838 */
1839static void
1840ohci_build_interrupt_lattice(ohci_state_t	*ohcip)
1841{
1842	ohci_ed_t	*list_array = ohcip->ohci_ed_pool_addr;
1843	int		half_list = NUM_INTR_ED_LISTS / 2;
1844	ohci_hcca_t	*hccap = ohcip->ohci_hccap;
1845	uintptr_t	addr;
1846	int		i;
1847
1848	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1849	    "ohci_build_interrupt_lattice:");
1850
1851	/*
1852	 * Reserve the first 31 Endpoint Descriptor (ED) structures
1853	 * in the pool as static endpoints & these are required for
1854	 * constructing interrupt lattice tree.
1855	 */
1856	for (i = 0; i < NUM_STATIC_NODES; i++) {
1857		Set_ED(list_array[i].hced_ctrl, HC_EPT_sKip);
1858
1859		Set_ED(list_array[i].hced_state, HC_EPT_STATIC);
1860	}
1861
1862	/* Build the interrupt lattice tree */
1863	for (i = 0; i < half_list - 1; i++) {
1864
1865		/*
1866		 * The next  pointer in the host controller  endpoint
1867		 * descriptor must contain an iommu address. Calculate
1868		 * the offset into the cpu address and add this to the
1869		 * starting iommu address.
1870		 */
1871		addr = ohci_ed_cpu_to_iommu(ohcip, (ohci_ed_t *)&list_array[i]);
1872
1873		Set_ED(list_array[2*i + 1].hced_next, addr);
1874		Set_ED(list_array[2*i + 2].hced_next, addr);
1875	}
1876
1877	/*
1878	 * Initialize the interrupt list in the HCCA so that it points
1879	 * to the bottom of the tree.
1880	 */
1881	for (i = 0; i < half_list; i++) {
1882		addr = ohci_ed_cpu_to_iommu(ohcip,
1883		    (ohci_ed_t *)&list_array[half_list - 1 + ohci_index[i]]);
1884
1885		ASSERT(Get_ED(list_array[half_list - 1 +
1886		    ohci_index[i]].hced_ctrl));
1887
1888		ASSERT(addr != 0);
1889
1890		Set_HCCA(hccap->HccaIntTble[i], addr);
1891		Set_HCCA(hccap->HccaIntTble[i + half_list], addr);
1892	}
1893}
1894
1895
1896/*
1897 * ohci_take_control:
1898 *
1899 * Take control of the host controller. OpenHCI allows for optional support
1900 * of legacy devices through the use of System Management Mode software and
1901 * system Management interrupt hardware. See section 5.1.1.3 of the OpenHCI
1902 * spec for more details.
1903 */
1904static int
1905ohci_take_control(ohci_state_t	*ohcip)
1906{
1907#if defined(__x86)
1908	uint32_t hcr_control_val;
1909	uint32_t hcr_cmd_status_val;
1910	int wait;
1911#endif	/* __x86 */
1912
1913	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1914	    "ohci_take_control:");
1915
1916#if defined(__x86)
1917	/*
1918	 * On x86, we must tell the BIOS we want the controller,
1919	 * and wait for it to respond that we can have it.
1920	 */
1921	hcr_control_val = Get_OpReg(hcr_control);
1922	if ((hcr_control_val & HCR_CONTROL_IR) == 0) {
1923		USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1924		    "ohci_take_control: InterruptRouting off\n");
1925
1926		return (DDI_SUCCESS);
1927	}
1928
1929	/* attempt the OwnershipChange request */
1930	hcr_cmd_status_val = Get_OpReg(hcr_cmd_status);
1931	USB_DPRINTF_L3(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1932	    "ohci_take_control: hcr_cmd_status: 0x%x\n",
1933	    hcr_cmd_status_val);
1934	hcr_cmd_status_val |= HCR_STATUS_OCR;
1935
1936	Set_OpReg(hcr_cmd_status, hcr_cmd_status_val);
1937
1938
1939	mutex_exit(&ohcip->ohci_int_mutex);
1940	/* now wait for 5 seconds for InterruptRouting to go away */
1941	for (wait = 0; wait < 5000; wait++) {
1942		if ((Get_OpReg(hcr_control) & HCR_CONTROL_IR) == 0)
1943			break;
1944		delay(drv_usectohz(1000));
1945	}
1946	mutex_enter(&ohcip->ohci_int_mutex);
1947
1948	if (wait >= 5000) {
1949		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1950		    "ohci_take_control: couldn't take control from BIOS\n");
1951
1952		return (DDI_FAILURE);
1953	}
1954#else	/* __x86 */
1955	/*
1956	 * On Sparc, there won't be  special System Management Mode
1957	 * hardware for legacy devices, while the x86 platforms may
1958	 * have to deal with  this. This  function may be  platform
1959	 * specific.
1960	 *
1961	 * The interrupt routing bit should not be set.
1962	 */
1963	if (Get_OpReg(hcr_control) & HCR_CONTROL_IR) {
1964		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1965		    "ohci_take_control: Routing bit set");
1966
1967		return (DDI_FAILURE);
1968	}
1969#endif	/* __x86 */
1970
1971	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
1972	    "ohci_take_control: End");
1973
1974	return (DDI_SUCCESS);
1975}
1976
1977/*
1978 * ohci_pm_support:
1979 *	always return success since PM has been quite reliable on ohci
1980 */
1981/*ARGSUSED*/
1982int
1983ohci_hcdi_pm_support(dev_info_t *dip)
1984{
1985	return (USB_SUCCESS);
1986}
1987
1988/*
1989 * ohci_alloc_hcdi_ops:
1990 *
1991 * The HCDI interfaces or entry points are the software interfaces used by
1992 * the Universal Serial Bus Driver  (USBA) to  access the services of the
1993 * Host Controller Driver (HCD).  During HCD initialization, inform  USBA
1994 * about all available HCDI interfaces or entry points.
1995 */
1996static usba_hcdi_ops_t *
1997ohci_alloc_hcdi_ops(ohci_state_t	*ohcip)
1998{
1999	usba_hcdi_ops_t			*usba_hcdi_ops;
2000
2001	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
2002	    "ohci_alloc_hcdi_ops:");
2003
2004	usba_hcdi_ops = usba_alloc_hcdi_ops();
2005
2006	usba_hcdi_ops->usba_hcdi_ops_version = HCDI_OPS_VERSION;
2007
2008	usba_hcdi_ops->usba_hcdi_pm_support = ohci_hcdi_pm_support;
2009	usba_hcdi_ops->usba_hcdi_pipe_open = ohci_hcdi_pipe_open;
2010	usba_hcdi_ops->usba_hcdi_pipe_close = ohci_hcdi_pipe_close;
2011
2012	usba_hcdi_ops->usba_hcdi_pipe_reset = ohci_hcdi_pipe_reset;
2013	usba_hcdi_ops->usba_hcdi_pipe_reset_data_toggle =
2014	    ohci_hcdi_pipe_reset_data_toggle;
2015
2016	usba_hcdi_ops->usba_hcdi_pipe_ctrl_xfer = ohci_hcdi_pipe_ctrl_xfer;
2017	usba_hcdi_ops->usba_hcdi_pipe_bulk_xfer = ohci_hcdi_pipe_bulk_xfer;
2018	usba_hcdi_ops->usba_hcdi_pipe_intr_xfer = ohci_hcdi_pipe_intr_xfer;
2019	usba_hcdi_ops->usba_hcdi_pipe_isoc_xfer = ohci_hcdi_pipe_isoc_xfer;
2020
2021	usba_hcdi_ops->usba_hcdi_bulk_transfer_size =
2022	    ohci_hcdi_bulk_transfer_size;
2023
2024	usba_hcdi_ops->usba_hcdi_pipe_stop_intr_polling =
2025	    ohci_hcdi_pipe_stop_intr_polling;
2026	usba_hcdi_ops->usba_hcdi_pipe_stop_isoc_polling =
2027	    ohci_hcdi_pipe_stop_isoc_polling;
2028
2029	usba_hcdi_ops->usba_hcdi_get_current_frame_number =
2030	    ohci_hcdi_get_current_frame_number;
2031	usba_hcdi_ops->usba_hcdi_get_max_isoc_pkts =
2032	    ohci_hcdi_get_max_isoc_pkts;
2033	usba_hcdi_ops->usba_hcdi_console_input_init =
2034	    ohci_hcdi_polled_input_init;
2035	usba_hcdi_ops->usba_hcdi_console_input_enter =
2036	    ohci_hcdi_polled_input_enter;
2037	usba_hcdi_ops->usba_hcdi_console_read = ohci_hcdi_polled_read;
2038	usba_hcdi_ops->usba_hcdi_console_input_exit =
2039	    ohci_hcdi_polled_input_exit;
2040	usba_hcdi_ops->usba_hcdi_console_input_fini =
2041	    ohci_hcdi_polled_input_fini;
2042
2043	usba_hcdi_ops->usba_hcdi_console_output_init =
2044	    ohci_hcdi_polled_output_init;
2045	usba_hcdi_ops->usba_hcdi_console_output_enter =
2046	    ohci_hcdi_polled_output_enter;
2047	usba_hcdi_ops->usba_hcdi_console_write = ohci_hcdi_polled_write;
2048	usba_hcdi_ops->usba_hcdi_console_output_exit =
2049	    ohci_hcdi_polled_output_exit;
2050	usba_hcdi_ops->usba_hcdi_console_output_fini =
2051	    ohci_hcdi_polled_output_fini;
2052
2053	return (usba_hcdi_ops);
2054}
2055
2056
2057/*
2058 * Host Controller Driver (HCD) deinitialization functions
2059 */
2060
2061/*
2062 * ohci_cleanup:
2063 *
2064 * Cleanup on attach failure or detach
2065 */
2066static int
2067ohci_cleanup(ohci_state_t	*ohcip)
2068{
2069	ohci_trans_wrapper_t	*tw;
2070	ohci_pipe_private_t	*pp;
2071	ohci_td_t		*td;
2072	int			i, state, rval;
2073	int			flags = ohcip->ohci_flags;
2074
2075	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl, "ohci_cleanup:");
2076
2077	if (flags & OHCI_RHREG) {
2078		/* Unload the root hub driver */
2079		if (ohci_unload_root_hub_driver(ohcip) != USB_SUCCESS) {
2080
2081			return (DDI_FAILURE);
2082		}
2083	}
2084
2085	if (flags & OHCI_USBAREG) {
2086		/* Unregister this HCD instance with USBA */
2087		usba_hcdi_unregister(ohcip->ohci_dip);
2088	}
2089
2090	if (flags & OHCI_INTR) {
2091
2092		mutex_enter(&ohcip->ohci_int_mutex);
2093
2094		/* Disable all HC ED list processing */
2095		Set_OpReg(hcr_control,
2096		    (Get_OpReg(hcr_control) & ~(HCR_CONTROL_CLE |
2097		    HCR_CONTROL_BLE | HCR_CONTROL_PLE | HCR_CONTROL_IE)));
2098
2099		/* Disable all HC interrupts */
2100		Set_OpReg(hcr_intr_disable,
2101		    (HCR_INTR_SO | HCR_INTR_WDH | HCR_INTR_RD | HCR_INTR_UE));
2102
2103		/* Wait for the next SOF */
2104		(void) ohci_wait_for_sof(ohcip);
2105
2106		/* Disable Master and SOF interrupts */
2107		Set_OpReg(hcr_intr_disable, (HCR_INTR_MIE | HCR_INTR_SOF));
2108
2109		/* Set the Host Controller Functional State to Reset */
2110		Set_OpReg(hcr_control, ((Get_OpReg(hcr_control) &
2111		    (~HCR_CONTROL_HCFS)) | HCR_CONTROL_RESET));
2112
2113		mutex_exit(&ohcip->ohci_int_mutex);
2114		/* Wait for sometime */
2115		delay(drv_usectohz(OHCI_TIMEWAIT));
2116		mutex_enter(&ohcip->ohci_int_mutex);
2117
2118		/*
2119		 * Workaround for ULI1575 chipset. Following OHCI Operational
2120		 * Memory Registers are not cleared to their default value
2121		 * on reset. Explicitly set the registers to default value.
2122		 */
2123		if (ohcip->ohci_vendor_id == PCI_ULI1575_VENID &&
2124		    ohcip->ohci_device_id == PCI_ULI1575_DEVID) {
2125			Set_OpReg(hcr_control, HCR_CONTROL_DEFAULT);
2126			Set_OpReg(hcr_intr_enable, HCR_INT_ENABLE_DEFAULT);
2127			Set_OpReg(hcr_HCCA, HCR_HCCA_DEFAULT);
2128			Set_OpReg(hcr_ctrl_head, HCR_CONTROL_HEAD_ED_DEFAULT);
2129			Set_OpReg(hcr_bulk_head, HCR_BULK_HEAD_ED_DEFAULT);
2130			Set_OpReg(hcr_frame_interval,
2131			    HCR_FRAME_INTERVAL_DEFAULT);
2132			Set_OpReg(hcr_periodic_strt,
2133			    HCR_PERIODIC_START_DEFAULT);
2134		}
2135
2136		mutex_exit(&ohcip->ohci_int_mutex);
2137
2138		ohci_rem_intrs(ohcip);
2139	}
2140
2141	/* Unmap the OHCI registers */
2142	if (ohcip->ohci_regs_handle) {
2143		/* Reset the host controller */
2144		Set_OpReg(hcr_cmd_status, HCR_STATUS_RESET);
2145
2146		ddi_regs_map_free(&ohcip->ohci_regs_handle);
2147	}
2148
2149	if (ohcip->ohci_config_handle) {
2150		pci_config_teardown(&ohcip->ohci_config_handle);
2151	}
2152
2153	/* Free all the buffers */
2154	if (ohcip->ohci_td_pool_addr && ohcip->ohci_td_pool_mem_handle) {
2155		for (i = 0; i < ohci_td_pool_size; i ++) {
2156			td = &ohcip->ohci_td_pool_addr[i];
2157			state = Get_TD(ohcip->ohci_td_pool_addr[i].hctd_state);
2158
2159			if ((state != HC_TD_FREE) && (state != HC_TD_DUMMY) &&
2160			    (td->hctd_trans_wrapper)) {
2161
2162				mutex_enter(&ohcip->ohci_int_mutex);
2163
2164				tw = (ohci_trans_wrapper_t *)
2165				    OHCI_LOOKUP_ID((uint32_t)
2166				    Get_TD(td->hctd_trans_wrapper));
2167
2168				/* Obtain the pipe private structure */
2169				pp = tw->tw_pipe_private;
2170
2171				/* Stop the the transfer timer */
2172				ohci_stop_xfer_timer(ohcip, tw,
2173				    OHCI_REMOVE_XFER_ALWAYS);
2174
2175				ohci_deallocate_tw_resources(ohcip, pp, tw);
2176
2177				mutex_exit(&ohcip->ohci_int_mutex);
2178			}
2179		}
2180
2181		/*
2182		 * If OHCI_TD_POOL_BOUND flag is set, then unbind
2183		 * the handle for TD pools.
2184		 */
2185		if ((ohcip->ohci_dma_addr_bind_flag &
2186		    OHCI_TD_POOL_BOUND) == OHCI_TD_POOL_BOUND) {
2187
2188			rval = ddi_dma_unbind_handle(
2189			    ohcip->ohci_td_pool_dma_handle);
2190
2191			ASSERT(rval == DDI_SUCCESS);
2192		}
2193		ddi_dma_mem_free(&ohcip->ohci_td_pool_mem_handle);
2194	}
2195
2196	/* Free the TD pool */
2197	if (ohcip->ohci_td_pool_dma_handle) {
2198		ddi_dma_free_handle(&ohcip->ohci_td_pool_dma_handle);
2199	}
2200
2201	if (ohcip->ohci_ed_pool_addr && ohcip->ohci_ed_pool_mem_handle) {
2202		/*
2203		 * If OHCI_ED_POOL_BOUND flag is set, then unbind
2204		 * the handle for ED pools.
2205		 */
2206		if ((ohcip->ohci_dma_addr_bind_flag &
2207		    OHCI_ED_POOL_BOUND) == OHCI_ED_POOL_BOUND) {
2208
2209			rval = ddi_dma_unbind_handle(
2210			    ohcip->ohci_ed_pool_dma_handle);
2211
2212			ASSERT(rval == DDI_SUCCESS);
2213		}
2214
2215		ddi_dma_mem_free(&ohcip->ohci_ed_pool_mem_handle);
2216	}
2217
2218	/* Free the ED pool */
2219	if (ohcip->ohci_ed_pool_dma_handle) {
2220		ddi_dma_free_handle(&ohcip->ohci_ed_pool_dma_handle);
2221	}
2222
2223	/* Free the HCCA area */
2224	if (ohcip->ohci_hccap && ohcip->ohci_hcca_mem_handle) {
2225		/*
2226		 * If OHCI_HCCA_DMA_BOUND flag is set, then unbind
2227		 * the handle for HCCA.
2228		 */
2229		if ((ohcip->ohci_dma_addr_bind_flag &
2230		    OHCI_HCCA_DMA_BOUND) == OHCI_HCCA_DMA_BOUND) {
2231
2232			rval = ddi_dma_unbind_handle(
2233			    ohcip->ohci_hcca_dma_handle);
2234
2235			ASSERT(rval == DDI_SUCCESS);
2236		}
2237
2238		ddi_dma_mem_free(&ohcip->ohci_hcca_mem_handle);
2239	}
2240
2241	if (ohcip->ohci_hcca_dma_handle) {
2242		ddi_dma_free_handle(&ohcip->ohci_hcca_dma_handle);
2243	}
2244
2245	if (flags & OHCI_INTR) {
2246
2247		/* Destroy the mutex */
2248		mutex_destroy(&ohcip->ohci_int_mutex);
2249
2250		/* Destroy the SOF condition varibale */
2251		cv_destroy(&ohcip->ohci_SOF_cv);
2252
2253		/* Destroy the serialize opens and closes semaphore */
2254		sema_destroy(&ohcip->ohci_ocsem);
2255	}
2256
2257	/* clean up kstat structs */
2258	ohci_destroy_stats(ohcip);
2259
2260	/* Free ohci hcdi ops */
2261	if (ohcip->ohci_hcdi_ops) {
2262		usba_free_hcdi_ops(ohcip->ohci_hcdi_ops);
2263	}
2264
2265	if (flags & OHCI_ZALLOC) {
2266
2267		usb_free_log_hdl(ohcip->ohci_log_hdl);
2268
2269		/* Remove all properties that might have been created */
2270		ddi_prop_remove_all(ohcip->ohci_dip);
2271
2272		/* Free the soft state */
2273		ddi_soft_state_free(ohci_statep,
2274		    ddi_get_instance(ohcip->ohci_dip));
2275	}
2276
2277	return (DDI_SUCCESS);
2278}
2279
2280
2281/*
2282 * ohci_rem_intrs:
2283 *
2284 * Unregister FIXED or MSI interrupts
2285 */
2286static void
2287ohci_rem_intrs(ohci_state_t	*ohcip)
2288{
2289	int	i;
2290
2291	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
2292	    "ohci_rem_intrs: interrupt type 0x%x", ohcip->ohci_intr_type);
2293
2294	/* Disable all interrupts */
2295	if (ohcip->ohci_intr_cap & DDI_INTR_FLAG_BLOCK) {
2296		(void) ddi_intr_block_disable(ohcip->ohci_htable,
2297		    ohcip->ohci_intr_cnt);
2298	} else {
2299		for (i = 0; i < ohcip->ohci_intr_cnt; i++) {
2300			(void) ddi_intr_disable(ohcip->ohci_htable[i]);
2301		}
2302	}
2303
2304	/* Call ddi_intr_remove_handler() */
2305	for (i = 0; i < ohcip->ohci_intr_cnt; i++) {
2306		(void) ddi_intr_remove_handler(ohcip->ohci_htable[i]);
2307		(void) ddi_intr_free(ohcip->ohci_htable[i]);
2308	}
2309
2310	kmem_free(ohcip->ohci_htable,
2311	    ohcip->ohci_intr_cnt * sizeof (ddi_intr_handle_t));
2312}
2313
2314
2315/*
2316 * ohci_cpr_suspend
2317 */
2318static int
2319ohci_cpr_suspend(ohci_state_t	*ohcip)
2320{
2321	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
2322	    "ohci_cpr_suspend:");
2323
2324	/* Call into the root hub and suspend it */
2325	if (usba_hubdi_detach(ohcip->ohci_dip, DDI_SUSPEND) != DDI_SUCCESS) {
2326
2327		return (DDI_FAILURE);
2328	}
2329
2330	/* Only root hub's intr pipe should be open at this time */
2331	mutex_enter(&ohcip->ohci_int_mutex);
2332
2333	if (ohcip->ohci_open_pipe_count > 1) {
2334
2335		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
2336		    "ohci_cpr_suspend: fails as open pipe count = %d",
2337		    ohcip->ohci_open_pipe_count);
2338
2339		mutex_exit(&ohcip->ohci_int_mutex);
2340
2341		return (DDI_FAILURE);
2342	}
2343
2344	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
2345	    "ohci_cpr_suspend: Disable HC ED list processing");
2346
2347	/* Disable all HC ED list processing */
2348	Set_OpReg(hcr_control, (Get_OpReg(hcr_control) & ~(HCR_CONTROL_CLE |
2349	    HCR_CONTROL_BLE | HCR_CONTROL_PLE | HCR_CONTROL_IE)));
2350
2351	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
2352	    "ohci_cpr_suspend: Disable HC interrupts");
2353
2354	/* Disable all HC interrupts */
2355	Set_OpReg(hcr_intr_disable, ~(HCR_INTR_MIE|HCR_INTR_SOF));
2356
2357	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
2358	    "ohci_cpr_suspend: Wait for the next SOF");
2359
2360	/* Wait for the next SOF */
2361	if (ohci_wait_for_sof(ohcip) != USB_SUCCESS) {
2362
2363		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
2364		    "ohci_cpr_suspend: ohci host controller suspend failed");
2365
2366		mutex_exit(&ohcip->ohci_int_mutex);
2367		return (DDI_FAILURE);
2368	}
2369
2370	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
2371	    "ohci_cpr_suspend: Disable Master interrupt");
2372
2373	/*
2374	 * Disable Master interrupt so that ohci driver don't
2375	 * get any ohci interrupts.
2376	 */
2377	Set_OpReg(hcr_intr_disable, HCR_INTR_MIE);
2378
2379	/*
2380	 * Suspend the ohci host controller
2381	 * if usb keyboard is not connected.
2382	 */
2383	if (ohcip->ohci_polled_kbd_count == 0 || force_ohci_off != 0) {
2384		Set_OpReg(hcr_control, HCR_CONTROL_SUSPD);
2385	}
2386
2387	/* Set host controller soft state to suspend */
2388	ohcip->ohci_hc_soft_state = OHCI_CTLR_SUSPEND_STATE;
2389
2390	mutex_exit(&ohcip->ohci_int_mutex);
2391
2392	return (DDI_SUCCESS);
2393}
2394
2395
2396/*
2397 * ohci_cpr_resume
2398 */
2399static int
2400ohci_cpr_resume(ohci_state_t	*ohcip)
2401{
2402	mutex_enter(&ohcip->ohci_int_mutex);
2403
2404	USB_DPRINTF_L4(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
2405	    "ohci_cpr_resume: Restart the controller");
2406
2407	/* Cleanup ohci specific information across cpr */
2408	ohci_cpr_cleanup(ohcip);
2409
2410	/* Restart the controller */
2411	if (ohci_init_ctlr(ohcip) != DDI_SUCCESS) {
2412
2413		USB_DPRINTF_L2(PRINT_MASK_ATTA, ohcip->ohci_log_hdl,
2414		    "ohci_cpr_resume: ohci host controller resume failed ");
2415
2416		mutex_exit(&ohcip->ohci_int_mutex);
2417
2418		return (DDI_FAILURE);
2419	}
2420
2421	mutex_exit(&ohcip->ohci_int_mutex);
2422
2423	/* Now resume the root hub */
2424	if (usba_hubdi_attach(ohcip->ohci_dip, DDI_RESUME) != DDI_SUCCESS) {
2425
2426		return (DDI_FAILURE);
2427	}
2428
2429	return (DDI_SUCCESS);
2430}
2431
2432
2433/*
2434 * HCDI entry points
2435 *
2436 * The Host Controller Driver Interfaces (HCDI) are the software interfaces
2437 * between the Universal Serial Bus Layer (USBA) and the Host Controller
2438 * Driver (HCD). The HCDI interfaces or entry points are subject to change.
2439 */
2440
2441/*
2442 * ohci_hcdi_pipe_open:
2443 *
2444 * Member of HCD Ops structure and called during client specific pipe open
2445 * Add the pipe to the data structure representing the device and allocate
2446 * bandwidth for the pipe if it is a interrupt or isochronous endpoint.
2447 */
2448static int
2449ohci_hcdi_pipe_open(
2450	usba_pipe_handle_data_t	*ph,
2451	usb_flags_t		flags)
2452{
2453	ohci_state_t		*ohcip = ohci_obtain_state(
2454	    ph->p_usba_device->usb_root_hub_dip);
2455	usb_ep_descr_t		*epdt = &ph->p_ep;
2456	int			rval, error = USB_SUCCESS;
2457	int			kmflag = (flags & USB_FLAGS_SLEEP) ?
2458	    KM_SLEEP : KM_NOSLEEP;
2459	uint_t			node = 0;
2460	ohci_pipe_private_t	*pp;
2461
2462	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2463	    "ohci_hcdi_pipe_open: addr = 0x%x, ep%d",
2464	    ph->p_usba_device->usb_addr,
2465	    epdt->bEndpointAddress & USB_EP_NUM_MASK);
2466
2467	sema_p(&ohcip->ohci_ocsem);
2468
2469	mutex_enter(&ohcip->ohci_int_mutex);
2470	rval = ohci_state_is_operational(ohcip);
2471	mutex_exit(&ohcip->ohci_int_mutex);
2472
2473	if (rval != USB_SUCCESS) {
2474		sema_v(&ohcip->ohci_ocsem);
2475
2476		return (rval);
2477	}
2478
2479	/*
2480	 * Check and handle root hub pipe open.
2481	 */
2482	if (ph->p_usba_device->usb_addr == ROOT_HUB_ADDR) {
2483
2484		mutex_enter(&ohcip->ohci_int_mutex);
2485		error = ohci_handle_root_hub_pipe_open(ph, flags);
2486		mutex_exit(&ohcip->ohci_int_mutex);
2487		sema_v(&ohcip->ohci_ocsem);
2488
2489		return (error);
2490	}
2491
2492	/*
2493	 * Opening of other pipes excluding root hub pipe are
2494	 * handled below. Check whether pipe is already opened.
2495	 */
2496	if (ph->p_hcd_private) {
2497		USB_DPRINTF_L2(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2498		    "ohci_hcdi_pipe_open: Pipe is already opened");
2499
2500		sema_v(&ohcip->ohci_ocsem);
2501
2502		return (USB_FAILURE);
2503	}
2504
2505	/*
2506	 * A portion of the bandwidth is reserved for the non-periodic
2507	 * transfers, i.e control and bulk transfers in each of one
2508	 * millisecond frame period & usually it will be 10% of frame
2509	 * period. Hence there is no need to check for the available
2510	 * bandwidth before adding the control or bulk endpoints.
2511	 *
2512	 * There is a need to check for the available bandwidth before
2513	 * adding the periodic transfers, i.e interrupt & isochronous,
2514	 * since all these periodic transfers are guaranteed transfers.
2515	 * Usually 90% of the total frame time is reserved for periodic
2516	 * transfers.
2517	 */
2518	if (OHCI_PERIODIC_ENDPOINT(epdt)) {
2519
2520		mutex_enter(&ohcip->ohci_int_mutex);
2521		mutex_enter(&ph->p_mutex);
2522
2523		error = ohci_allocate_bandwidth(ohcip, ph, &node);
2524
2525		if (error != USB_SUCCESS) {
2526
2527			USB_DPRINTF_L2(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2528			    "ohci_hcdi_pipe_open: Bandwidth allocation failed");
2529
2530			mutex_exit(&ph->p_mutex);
2531			mutex_exit(&ohcip->ohci_int_mutex);
2532			sema_v(&ohcip->ohci_ocsem);
2533
2534			return (error);
2535		}
2536
2537		mutex_exit(&ph->p_mutex);
2538		mutex_exit(&ohcip->ohci_int_mutex);
2539	}
2540
2541	/* Create the HCD pipe private structure */
2542	pp = kmem_zalloc(sizeof (ohci_pipe_private_t), kmflag);
2543
2544	/*
2545	 * Return failure if ohci pipe private
2546	 * structure allocation fails.
2547	 */
2548	if (pp == NULL) {
2549
2550		mutex_enter(&ohcip->ohci_int_mutex);
2551
2552		/* Deallocate bandwidth */
2553		if (OHCI_PERIODIC_ENDPOINT(epdt)) {
2554
2555			mutex_enter(&ph->p_mutex);
2556			ohci_deallocate_bandwidth(ohcip, ph);
2557			mutex_exit(&ph->p_mutex);
2558		}
2559
2560		mutex_exit(&ohcip->ohci_int_mutex);
2561		sema_v(&ohcip->ohci_ocsem);
2562
2563		return (USB_NO_RESOURCES);
2564	}
2565
2566	mutex_enter(&ohcip->ohci_int_mutex);
2567
2568	/* Store the node in the interrupt lattice */
2569	pp->pp_node = node;
2570
2571	/* Create prototype for xfer completion condition variable */
2572	cv_init(&pp->pp_xfer_cmpl_cv, NULL, CV_DRIVER, NULL);
2573
2574	/* Set the state of pipe as idle */
2575	pp->pp_state = OHCI_PIPE_STATE_IDLE;
2576
2577	/* Store a pointer to the pipe handle */
2578	pp->pp_pipe_handle = ph;
2579
2580	mutex_enter(&ph->p_mutex);
2581
2582	/* Store the pointer in the pipe handle */
2583	ph->p_hcd_private = (usb_opaque_t)pp;
2584
2585	/* Store a copy of the pipe policy */
2586	bcopy(&ph->p_policy, &pp->pp_policy, sizeof (usb_pipe_policy_t));
2587
2588	mutex_exit(&ph->p_mutex);
2589
2590	/* Allocate the host controller endpoint descriptor */
2591	pp->pp_ept = ohci_alloc_hc_ed(ohcip, ph);
2592
2593	if (pp->pp_ept == NULL) {
2594		USB_DPRINTF_L2(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2595		    "ohci_hcdi_pipe_open: ED allocation failed");
2596
2597		mutex_enter(&ph->p_mutex);
2598
2599		/* Deallocate bandwidth */
2600		if (OHCI_PERIODIC_ENDPOINT(epdt)) {
2601
2602			ohci_deallocate_bandwidth(ohcip, ph);
2603		}
2604
2605		/* Destroy the xfer completion condition varibale */
2606		cv_destroy(&pp->pp_xfer_cmpl_cv);
2607
2608		/*
2609		 * Deallocate the hcd private portion
2610		 * of the pipe handle.
2611		 */
2612		kmem_free(ph->p_hcd_private, sizeof (ohci_pipe_private_t));
2613
2614		/*
2615		 * Set the private structure in the
2616		 * pipe handle equal to NULL.
2617		 */
2618		ph->p_hcd_private = NULL;
2619		mutex_exit(&ph->p_mutex);
2620
2621		mutex_exit(&ohcip->ohci_int_mutex);
2622		sema_v(&ohcip->ohci_ocsem);
2623
2624		return (USB_NO_RESOURCES);
2625	}
2626
2627	/* Restore the data toggle information */
2628	ohci_restore_data_toggle(ohcip, ph);
2629
2630	/*
2631	 * Insert the endpoint onto the host controller's
2632	 * appropriate endpoint list. The host controller
2633	 * will not schedule this endpoint and will not have
2634	 * any TD's to process.
2635	 */
2636	ohci_insert_ed(ohcip, ph);
2637
2638	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2639	    "ohci_hcdi_pipe_open: ph = 0x%p", (void *)ph);
2640
2641	ohcip->ohci_open_pipe_count++;
2642
2643	mutex_exit(&ohcip->ohci_int_mutex);
2644
2645	sema_v(&ohcip->ohci_ocsem);
2646
2647	return (USB_SUCCESS);
2648}
2649
2650
2651/*
2652 * ohci_hcdi_pipe_close:
2653 *
2654 * Member of HCD Ops structure and called during the client  specific pipe
2655 * close. Remove the pipe and the data structure representing the device.
2656 * Deallocate  bandwidth for the pipe if it is a interrupt or isochronous
2657 * endpoint.
2658 */
2659/* ARGSUSED */
2660static int
2661ohci_hcdi_pipe_close(
2662	usba_pipe_handle_data_t	*ph,
2663	usb_flags_t		flags)
2664{
2665	ohci_state_t		*ohcip = ohci_obtain_state(
2666	    ph->p_usba_device->usb_root_hub_dip);
2667	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
2668	usb_ep_descr_t		*eptd = &ph->p_ep;
2669	int			error = USB_SUCCESS;
2670
2671	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2672	    "ohci_hcdi_pipe_close: addr = 0x%x, ep%d",
2673	    ph->p_usba_device->usb_addr,
2674	    eptd->bEndpointAddress & USB_EP_NUM_MASK);
2675
2676	sema_p(&ohcip->ohci_ocsem);
2677
2678	/* Check and handle root hub pipe close */
2679	if (ph->p_usba_device->usb_addr == ROOT_HUB_ADDR) {
2680
2681		mutex_enter(&ohcip->ohci_int_mutex);
2682		error = ohci_handle_root_hub_pipe_close(ph);
2683		mutex_exit(&ohcip->ohci_int_mutex);
2684		sema_v(&ohcip->ohci_ocsem);
2685
2686		return (error);
2687	}
2688
2689	ASSERT(ph->p_hcd_private != NULL);
2690
2691	mutex_enter(&ohcip->ohci_int_mutex);
2692
2693	/* Set pipe state to pipe close */
2694	pp->pp_state = OHCI_PIPE_STATE_CLOSE;
2695
2696	ohci_pipe_cleanup(ohcip, ph);
2697
2698	/*
2699	 * Remove the endoint descriptor from Host
2700	 * Controller's appropriate endpoint list.
2701	 */
2702	ohci_remove_ed(ohcip, pp);
2703
2704	/* Deallocate bandwidth */
2705	if (OHCI_PERIODIC_ENDPOINT(eptd)) {
2706
2707		mutex_enter(&ph->p_mutex);
2708		ohci_deallocate_bandwidth(ohcip, ph);
2709		mutex_exit(&ph->p_mutex);
2710	}
2711
2712	mutex_enter(&ph->p_mutex);
2713
2714	/* Destroy the xfer completion condition varibale */
2715	cv_destroy(&pp->pp_xfer_cmpl_cv);
2716
2717	/*
2718	 * Deallocate the hcd private portion
2719	 * of the pipe handle.
2720	 */
2721	kmem_free(ph->p_hcd_private, sizeof (ohci_pipe_private_t));
2722	ph->p_hcd_private = NULL;
2723
2724	mutex_exit(&ph->p_mutex);
2725
2726	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2727	    "ohci_hcdi_pipe_close: ph = 0x%p", (void *)ph);
2728
2729	ohcip->ohci_open_pipe_count--;
2730
2731	mutex_exit(&ohcip->ohci_int_mutex);
2732	sema_v(&ohcip->ohci_ocsem);
2733
2734	return (error);
2735}
2736
2737
2738/*
2739 * ohci_hcdi_pipe_reset:
2740 */
2741/* ARGSUSED */
2742static int
2743ohci_hcdi_pipe_reset(
2744	usba_pipe_handle_data_t	*ph,
2745	usb_flags_t		usb_flags)
2746{
2747	ohci_state_t		*ohcip = ohci_obtain_state(
2748	    ph->p_usba_device->usb_root_hub_dip);
2749	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
2750	int			error = USB_SUCCESS;
2751
2752	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2753	    "ohci_hcdi_pipe_reset: ph = 0x%p ", (void *)ph);
2754
2755	/*
2756	 * Check and handle root hub pipe reset.
2757	 */
2758	if (ph->p_usba_device->usb_addr == ROOT_HUB_ADDR) {
2759
2760		error = ohci_handle_root_hub_pipe_reset(ph, usb_flags);
2761		return (error);
2762	}
2763
2764	mutex_enter(&ohcip->ohci_int_mutex);
2765
2766	/* Set pipe state to pipe reset */
2767	pp->pp_state = OHCI_PIPE_STATE_RESET;
2768
2769	ohci_pipe_cleanup(ohcip, ph);
2770
2771	mutex_exit(&ohcip->ohci_int_mutex);
2772
2773	return (error);
2774}
2775
2776/*
2777 * ohci_hcdi_pipe_reset_data_toggle:
2778 */
2779void
2780ohci_hcdi_pipe_reset_data_toggle(
2781	usba_pipe_handle_data_t	*ph)
2782{
2783	ohci_state_t		*ohcip = ohci_obtain_state(
2784	    ph->p_usba_device->usb_root_hub_dip);
2785	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
2786
2787	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2788	    "ohci_hcdi_pipe_reset_data_toggle:");
2789
2790	mutex_enter(&ohcip->ohci_int_mutex);
2791
2792	mutex_enter(&ph->p_mutex);
2793	usba_hcdi_set_data_toggle(ph->p_usba_device, ph->p_ep.bEndpointAddress,
2794	    DATA0);
2795	mutex_exit(&ph->p_mutex);
2796
2797	Set_ED(pp->pp_ept->hced_headp,
2798	    Get_ED(pp->pp_ept->hced_headp) & (~HC_EPT_Carry));
2799	mutex_exit(&ohcip->ohci_int_mutex);
2800
2801}
2802
2803/*
2804 * ohci_hcdi_pipe_ctrl_xfer:
2805 */
2806static int
2807ohci_hcdi_pipe_ctrl_xfer(
2808	usba_pipe_handle_data_t	*ph,
2809	usb_ctrl_req_t		*ctrl_reqp,
2810	usb_flags_t		usb_flags)
2811{
2812	ohci_state_t		*ohcip = ohci_obtain_state(
2813	    ph->p_usba_device->usb_root_hub_dip);
2814	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
2815	int			rval;
2816	int			error = USB_SUCCESS;
2817	ohci_trans_wrapper_t	*tw;
2818
2819	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2820	    "ohci_hcdi_pipe_ctrl_xfer: ph = 0x%p reqp = 0x%p flags = 0x%x",
2821	    (void *)ph, (void *)ctrl_reqp, usb_flags);
2822
2823	mutex_enter(&ohcip->ohci_int_mutex);
2824	rval = ohci_state_is_operational(ohcip);
2825	mutex_exit(&ohcip->ohci_int_mutex);
2826
2827	if (rval != USB_SUCCESS) {
2828
2829		return (rval);
2830	}
2831
2832	/*
2833	 * Check and handle root hub control request.
2834	 */
2835	if (ph->p_usba_device->usb_addr == ROOT_HUB_ADDR) {
2836
2837		error = ohci_handle_root_hub_request(ohcip, ph, ctrl_reqp);
2838
2839		return (error);
2840	}
2841
2842	mutex_enter(&ohcip->ohci_int_mutex);
2843
2844	/*
2845	 *  Check whether pipe is in halted state.
2846	 */
2847	if (pp->pp_state == OHCI_PIPE_STATE_ERROR) {
2848
2849		USB_DPRINTF_L2(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2850		    "ohci_hcdi_pipe_ctrl_xfer:"
2851		    "Pipe is in error state, need pipe reset to continue");
2852
2853		mutex_exit(&ohcip->ohci_int_mutex);
2854
2855		return (USB_FAILURE);
2856	}
2857
2858	/* Allocate a transfer wrapper */
2859	if ((tw = ohci_allocate_ctrl_resources(ohcip, pp, ctrl_reqp,
2860	    usb_flags)) == NULL) {
2861
2862		error = USB_NO_RESOURCES;
2863	} else {
2864		/* Insert the td's on the endpoint */
2865		ohci_insert_ctrl_req(ohcip, ph, ctrl_reqp, tw, usb_flags);
2866	}
2867
2868	mutex_exit(&ohcip->ohci_int_mutex);
2869
2870	return (error);
2871}
2872
2873
2874/*
2875 * ohci_hcdi_bulk_transfer_size:
2876 *
2877 * Return maximum bulk transfer size
2878 */
2879
2880/* ARGSUSED */
2881static int
2882ohci_hcdi_bulk_transfer_size(
2883	usba_device_t	*usba_device,
2884	size_t		*size)
2885{
2886	ohci_state_t	*ohcip = ohci_obtain_state(
2887	    usba_device->usb_root_hub_dip);
2888	int		rval;
2889
2890	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2891	    "ohci_hcdi_bulk_transfer_size:");
2892
2893	mutex_enter(&ohcip->ohci_int_mutex);
2894	rval = ohci_state_is_operational(ohcip);
2895	mutex_exit(&ohcip->ohci_int_mutex);
2896
2897	if (rval != USB_SUCCESS) {
2898
2899		return (rval);
2900	}
2901
2902	*size = OHCI_MAX_BULK_XFER_SIZE;
2903
2904	return (USB_SUCCESS);
2905}
2906
2907
2908/*
2909 * ohci_hcdi_pipe_bulk_xfer:
2910 */
2911static int
2912ohci_hcdi_pipe_bulk_xfer(
2913	usba_pipe_handle_data_t	*ph,
2914	usb_bulk_req_t		*bulk_reqp,
2915	usb_flags_t		usb_flags)
2916{
2917	ohci_state_t		*ohcip = ohci_obtain_state(
2918	    ph->p_usba_device->usb_root_hub_dip);
2919	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
2920	int			rval, error = USB_SUCCESS;
2921	ohci_trans_wrapper_t	*tw;
2922
2923	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2924	    "ohci_hcdi_pipe_bulk_xfer: ph = 0x%p reqp = 0x%p flags = 0x%x",
2925	    (void *)ph, (void *)bulk_reqp, usb_flags);
2926
2927	mutex_enter(&ohcip->ohci_int_mutex);
2928	rval = ohci_state_is_operational(ohcip);
2929
2930	if (rval != USB_SUCCESS) {
2931		mutex_exit(&ohcip->ohci_int_mutex);
2932
2933		return (rval);
2934	}
2935
2936	/*
2937	 *  Check whether pipe is in halted state.
2938	 */
2939	if (pp->pp_state == OHCI_PIPE_STATE_ERROR) {
2940
2941		USB_DPRINTF_L2(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2942		    "ohci_hcdi_pipe_bulk_xfer:"
2943		    "Pipe is in error state, need pipe reset to continue");
2944
2945		mutex_exit(&ohcip->ohci_int_mutex);
2946
2947		return (USB_FAILURE);
2948	}
2949
2950	/* Allocate a transfer wrapper */
2951	if ((tw = ohci_allocate_bulk_resources(ohcip, pp, bulk_reqp,
2952	    usb_flags)) == NULL) {
2953
2954		error = USB_NO_RESOURCES;
2955	} else {
2956		/* Add the TD into the Host Controller's bulk list */
2957		ohci_insert_bulk_req(ohcip, ph, bulk_reqp, tw, usb_flags);
2958	}
2959
2960	mutex_exit(&ohcip->ohci_int_mutex);
2961
2962	return (error);
2963}
2964
2965
2966/*
2967 * ohci_hcdi_pipe_intr_xfer:
2968 */
2969static int
2970ohci_hcdi_pipe_intr_xfer(
2971	usba_pipe_handle_data_t	*ph,
2972	usb_intr_req_t		*intr_reqp,
2973	usb_flags_t		usb_flags)
2974{
2975	ohci_state_t		*ohcip = ohci_obtain_state(
2976	    ph->p_usba_device->usb_root_hub_dip);
2977	int			pipe_dir, rval, error = USB_SUCCESS;
2978	ohci_trans_wrapper_t	*tw;
2979
2980	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
2981	    "ohci_hcdi_pipe_intr_xfer: ph = 0x%p reqp = 0x%p flags = 0x%x",
2982	    (void *)ph, (void *)intr_reqp, usb_flags);
2983
2984	mutex_enter(&ohcip->ohci_int_mutex);
2985	rval = ohci_state_is_operational(ohcip);
2986
2987	if (rval != USB_SUCCESS) {
2988		mutex_exit(&ohcip->ohci_int_mutex);
2989
2990		return (rval);
2991	}
2992
2993	/* Get the pipe direction */
2994	pipe_dir = ph->p_ep.bEndpointAddress & USB_EP_DIR_MASK;
2995
2996	if (pipe_dir == USB_EP_DIR_IN) {
2997		error = ohci_start_periodic_pipe_polling(ohcip, ph,
2998		    (usb_opaque_t)intr_reqp, usb_flags);
2999	} else {
3000		/* Allocate transaction resources */
3001		if ((tw = ohci_allocate_intr_resources(ohcip, ph,
3002		    intr_reqp, usb_flags)) == NULL) {
3003			error = USB_NO_RESOURCES;
3004		} else {
3005			ohci_insert_intr_req(ohcip,
3006			    (ohci_pipe_private_t *)ph->p_hcd_private,
3007			    tw, usb_flags);
3008		}
3009	}
3010
3011	mutex_exit(&ohcip->ohci_int_mutex);
3012
3013	return (error);
3014}
3015
3016
3017/*
3018 * ohci_hcdi_pipe_stop_intr_polling()
3019 */
3020static int
3021ohci_hcdi_pipe_stop_intr_polling(
3022	usba_pipe_handle_data_t	*ph,
3023	usb_flags_t		flags)
3024{
3025	ohci_state_t		*ohcip = ohci_obtain_state(
3026	    ph->p_usba_device->usb_root_hub_dip);
3027	int			error = USB_SUCCESS;
3028
3029	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
3030	    "ohci_hcdi_pipe_stop_intr_polling: ph = 0x%p fl = 0x%x",
3031	    (void *)ph, flags);
3032
3033	mutex_enter(&ohcip->ohci_int_mutex);
3034
3035	error = ohci_stop_periodic_pipe_polling(ohcip, ph, flags);
3036
3037	mutex_exit(&ohcip->ohci_int_mutex);
3038
3039	return (error);
3040}
3041
3042
3043/*
3044 * ohci_hcdi_get_current_frame_number:
3045 *
3046 * Get the current usb frame number.
3047 * Return whether the request is handled successfully.
3048 */
3049static int
3050ohci_hcdi_get_current_frame_number(
3051	usba_device_t		*usba_device,
3052	usb_frame_number_t	*frame_number)
3053{
3054	ohci_state_t		*ohcip = ohci_obtain_state(
3055	    usba_device->usb_root_hub_dip);
3056	int			rval;
3057
3058	ohcip = ohci_obtain_state(usba_device->usb_root_hub_dip);
3059
3060	mutex_enter(&ohcip->ohci_int_mutex);
3061	rval = ohci_state_is_operational(ohcip);
3062
3063	if (rval != USB_SUCCESS) {
3064		mutex_exit(&ohcip->ohci_int_mutex);
3065
3066		return (rval);
3067	}
3068
3069	*frame_number = ohci_get_current_frame_number(ohcip);
3070
3071	mutex_exit(&ohcip->ohci_int_mutex);
3072
3073	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
3074	    "ohci_hcdi_get_current_frame_number:"
3075	    "Current frame number 0x%llx", (unsigned long long)(*frame_number));
3076
3077	return (rval);
3078}
3079
3080
3081/*
3082 * ohci_hcdi_get_max_isoc_pkts:
3083 *
3084 * Get maximum isochronous packets per usb isochronous request.
3085 * Return whether the request is handled successfully.
3086 */
3087static int
3088ohci_hcdi_get_max_isoc_pkts(
3089	usba_device_t	*usba_device,
3090	uint_t		*max_isoc_pkts_per_request)
3091{
3092	ohci_state_t		*ohcip = ohci_obtain_state(
3093	    usba_device->usb_root_hub_dip);
3094	int			rval;
3095
3096	mutex_enter(&ohcip->ohci_int_mutex);
3097	rval = ohci_state_is_operational(ohcip);
3098	mutex_exit(&ohcip->ohci_int_mutex);
3099
3100	if (rval != USB_SUCCESS) {
3101
3102		return (rval);
3103	}
3104
3105	*max_isoc_pkts_per_request = OHCI_MAX_ISOC_PKTS_PER_XFER;
3106
3107	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
3108	    "ohci_hcdi_get_max_isoc_pkts: maximum isochronous"
3109	    "packets per usb isochronous request = 0x%x",
3110	    *max_isoc_pkts_per_request);
3111
3112	return (rval);
3113}
3114
3115
3116/*
3117 * ohci_hcdi_pipe_isoc_xfer:
3118 */
3119static int
3120ohci_hcdi_pipe_isoc_xfer(
3121	usba_pipe_handle_data_t	*ph,
3122	usb_isoc_req_t		*isoc_reqp,
3123	usb_flags_t		usb_flags)
3124{
3125	ohci_state_t		*ohcip = ohci_obtain_state(
3126	    ph->p_usba_device->usb_root_hub_dip);
3127	int			error = USB_SUCCESS;
3128	int			pipe_dir, rval;
3129	ohci_trans_wrapper_t	*tw;
3130
3131	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
3132	    "ohci_hcdi_pipe_isoc_xfer: ph = 0x%p reqp = 0x%p flags = 0x%x",
3133	    (void *)ph, (void *)isoc_reqp, usb_flags);
3134
3135	mutex_enter(&ohcip->ohci_int_mutex);
3136	rval = ohci_state_is_operational(ohcip);
3137
3138	if (rval != USB_SUCCESS) {
3139		mutex_exit(&ohcip->ohci_int_mutex);
3140
3141		return (rval);
3142	}
3143
3144	/* Get the isochronous pipe direction */
3145	pipe_dir = ph->p_ep.bEndpointAddress & USB_EP_DIR_MASK;
3146
3147	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
3148	    "ohci_hcdi_pipe_isoc_xfer: isoc_reqp = 0x%p, uf = 0x%x",
3149	    (void *)isoc_reqp, usb_flags);
3150
3151	if (pipe_dir == USB_EP_DIR_IN) {
3152		error = ohci_start_periodic_pipe_polling(ohcip, ph,
3153		    (usb_opaque_t)isoc_reqp, usb_flags);
3154	} else {
3155		/* Allocate transaction resources */
3156		if ((tw = ohci_allocate_isoc_resources(ohcip, ph,
3157		    isoc_reqp, usb_flags)) == NULL) {
3158			error = USB_NO_RESOURCES;
3159		} else {
3160			error = ohci_insert_isoc_req(ohcip,
3161			    (ohci_pipe_private_t *)ph->p_hcd_private,
3162			    tw, usb_flags);
3163		}
3164	}
3165
3166	mutex_exit(&ohcip->ohci_int_mutex);
3167
3168	return (error);
3169}
3170
3171
3172/*
3173 * ohci_hcdi_pipe_stop_isoc_polling()
3174 */
3175static int
3176ohci_hcdi_pipe_stop_isoc_polling(
3177	usba_pipe_handle_data_t	*ph,
3178	usb_flags_t		flags)
3179{
3180	ohci_state_t		*ohcip = ohci_obtain_state(
3181	    ph->p_usba_device->usb_root_hub_dip);
3182	int			rval, error = USB_SUCCESS;
3183
3184	USB_DPRINTF_L4(PRINT_MASK_HCDI, ohcip->ohci_log_hdl,
3185	    "ohci_hcdi_pipe_stop_isoc_polling: ph = 0x%p fl = 0x%x",
3186	    (void *)ph, flags);
3187
3188	mutex_enter(&ohcip->ohci_int_mutex);
3189	rval = ohci_state_is_operational(ohcip);
3190
3191	if (rval != USB_SUCCESS) {
3192		mutex_exit(&ohcip->ohci_int_mutex);
3193		return (rval);
3194	}
3195
3196	error = ohci_stop_periodic_pipe_polling(ohcip, ph, flags);
3197
3198	mutex_exit(&ohcip->ohci_int_mutex);
3199	return (error);
3200}
3201
3202
3203/*
3204 * Bandwidth Allocation functions
3205 */
3206
3207/*
3208 * ohci_allocate_bandwidth:
3209 *
3210 * Figure out whether or not this interval may be supported. Return the index
3211 * into the  lattice if it can be supported.  Return allocation failure if it
3212 * can not be supported.
3213 *
3214 * The lattice structure looks like this with the bottom leaf actually
3215 * being an array.  There is a total of 63 nodes in this tree.	The lattice tree
3216 * itself is 0 based, while the bottom leaf array is 0 based.  The 0 bucket in
3217 * the bottom leaf array is used to store the smalled allocated bandwidth of all
3218 * the leaves.
3219 *
3220 *	0
3221 *    1   2
3222 *   3 4 5 6
3223 *   ...
3224 *  (32 33 ... 62 63)	  <-- last row does not exist in lattice, but an array
3225 *   0 1 2 3 ... 30 31
3226 *
3227 * We keep track of the bandwidth that each leaf uses.	First we search for the
3228 * first leaf with the smallest used bandwidth.  Based on that leaf we find the
3229 * parent node of that leaf based on the interval time.
3230 *
3231 * From the parent node, we find all the leafs of that subtree and update the
3232 * additional bandwidth needed.  In order to balance the load the leaves are not
3233 * executed directly from left to right, but scattered.  For a better picture
3234 * refer to Section 3.3.2 in the OpenHCI 1.0 spec, there should be a figure
3235 * showing the Interrupt ED Structure.
3236 */
3237static int
3238ohci_allocate_bandwidth(
3239	ohci_state_t		*ohcip,
3240	usba_pipe_handle_data_t	*ph,
3241	uint_t			*node)
3242{
3243	int			interval, error, i;
3244	uint_t			min, min_index, height;
3245	uint_t			leftmost, list, bandwidth;
3246	usb_ep_descr_t		*endpoint = &ph->p_ep;
3247
3248	/* This routine is protected by the ohci_int_mutex */
3249	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
3250
3251	/*
3252	 * Calculate the length in bytes of a transaction on this
3253	 * periodic endpoint.
3254	 */
3255	mutex_enter(&ph->p_usba_device->usb_mutex);
3256	error = ohci_compute_total_bandwidth(
3257	    endpoint, ph->p_usba_device->usb_port_status, &bandwidth);
3258	mutex_exit(&ph->p_usba_device->usb_mutex);
3259
3260	/*
3261	 * If length is zero, then, it means endpoint maximum packet
3262	 * supported is zero.  In that case, return failure without
3263	 * allocating any bandwidth.
3264	 */
3265	if (error != USB_SUCCESS) {
3266		USB_DPRINTF_L2(PRINT_MASK_BW, ohcip->ohci_log_hdl,
3267		    "ohci_allocate_bandwidth: Periodic endpoint with "
3268		    "zero endpoint maximum packet size is not supported");
3269
3270		return (USB_NOT_SUPPORTED);
3271	}
3272
3273	/*
3274	 * If the length in bytes plus the allocated bandwidth exceeds
3275	 * the maximum, return bandwidth allocation failure.
3276	 */
3277	if ((ohcip->ohci_periodic_minimum_bandwidth + bandwidth) >
3278	    (MAX_PERIODIC_BANDWIDTH)) {
3279
3280		USB_DPRINTF_L2(PRINT_MASK_BW, ohcip->ohci_log_hdl,
3281		    "ohci_allocate_bandwidth: Reached maximum "
3282		    "bandwidth value and cannot allocate bandwidth "
3283		    "for a given periodic endpoint");
3284
3285		return (USB_NO_BANDWIDTH);
3286	}
3287
3288	/* Adjust polling interval to be a power of 2 */
3289	mutex_enter(&ph->p_usba_device->usb_mutex);
3290	interval = ohci_adjust_polling_interval(ohcip,
3291	    endpoint, ph->p_usba_device->usb_port_status);
3292	mutex_exit(&ph->p_usba_device->usb_mutex);
3293
3294	/*
3295	 * If this interval can't be supported,
3296	 * return allocation failure.
3297	 */
3298	if (interval == USB_FAILURE) {
3299
3300		return (USB_FAILURE);
3301	}
3302
3303	USB_DPRINTF_L4(PRINT_MASK_BW, ohcip->ohci_log_hdl,
3304	    "The new interval is %d", interval);
3305
3306	/* Find the leaf with the smallest allocated bandwidth */
3307	min_index = 0;
3308	min = ohcip->ohci_periodic_bandwidth[0];
3309
3310	for (i = 1; i < NUM_INTR_ED_LISTS; i++) {
3311		if (ohcip->ohci_periodic_bandwidth[i] < min) {
3312			min_index = i;
3313			min = ohcip->ohci_periodic_bandwidth[i];
3314		}
3315	}
3316
3317	USB_DPRINTF_L4(PRINT_MASK_BW, ohcip->ohci_log_hdl,
3318	    "The leaf %d for minimal bandwidth %d", min_index, min);
3319
3320	/* Adjust min for the lattice */
3321	min_index = min_index + NUM_INTR_ED_LISTS - 1;
3322
3323	/*
3324	 * Find the index into the lattice given the
3325	 * leaf with the smallest allocated bandwidth.
3326	 */
3327	height = ohci_lattice_height(interval);
3328
3329	USB_DPRINTF_L4(PRINT_MASK_BW, ohcip->ohci_log_hdl,
3330	    "The height is %d", height);
3331
3332	*node = min_index;
3333
3334	for (i = 0; i < height; i++) {
3335		*node = ohci_lattice_parent(*node);
3336	}
3337
3338	USB_DPRINTF_L4(PRINT_MASK_BW, ohcip->ohci_log_hdl,
3339	    "Real node is %d", *node);
3340
3341	/*
3342	 * Find the leftmost leaf in the subtree
3343	 * specified by the node.
3344	 */
3345	leftmost = ohci_leftmost_leaf(*node, height);
3346
3347	USB_DPRINTF_L4(PRINT_MASK_BW, ohcip->ohci_log_hdl,
3348	    "Leftmost %d", leftmost);
3349
3350	for (i = 0; i < (NUM_INTR_ED_LISTS/interval); i++) {
3351		list = ohci_hcca_leaf_index(leftmost + i);
3352		if ((ohcip->ohci_periodic_bandwidth[list] +
3353		    bandwidth) > MAX_PERIODIC_BANDWIDTH) {
3354
3355			USB_DPRINTF_L2(PRINT_MASK_BW, ohcip->ohci_log_hdl,
3356			    "ohci_allocate_bandwidth: Reached maximum "
3357			    "bandwidth value and cannot allocate bandwidth "
3358			    "for periodic endpoint");
3359
3360			return (USB_NO_BANDWIDTH);
3361		}
3362	}
3363
3364	/*
3365	 * All the leaves for this node must be updated with the bandwidth.
3366	 */
3367	for (i = 0; i < (NUM_INTR_ED_LISTS/interval); i++) {
3368		list = ohci_hcca_leaf_index(leftmost + i);
3369		ohcip->ohci_periodic_bandwidth[list] += bandwidth;
3370	}
3371
3372	/* Find the leaf with the smallest allocated bandwidth */
3373	min_index = 0;
3374	min = ohcip->ohci_periodic_bandwidth[0];
3375
3376	for (i = 1; i < NUM_INTR_ED_LISTS; i++) {
3377		if (ohcip->ohci_periodic_bandwidth[i] < min) {
3378			min_index = i;
3379			min = ohcip->ohci_periodic_bandwidth[i];
3380		}
3381	}
3382
3383	/* Save the minimum for later use */
3384	ohcip->ohci_periodic_minimum_bandwidth = min;
3385
3386	return (USB_SUCCESS);
3387}
3388
3389
3390/*
3391 * ohci_deallocate_bandwidth:
3392 *
3393 * Deallocate bandwidth for the given node in the lattice and the length
3394 * of transfer.
3395 */
3396static void
3397ohci_deallocate_bandwidth(
3398	ohci_state_t		*ohcip,
3399	usba_pipe_handle_data_t	*ph)
3400{
3401	uint_t			min, node, bandwidth;
3402	uint_t			height, leftmost, list;
3403	int			i, interval;
3404	usb_ep_descr_t		*endpoint = &ph->p_ep;
3405	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
3406
3407	/* This routine is protected by the ohci_int_mutex */
3408	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
3409
3410	/* Obtain the length */
3411	mutex_enter(&ph->p_usba_device->usb_mutex);
3412	(void) ohci_compute_total_bandwidth(
3413	    endpoint, ph->p_usba_device->usb_port_status, &bandwidth);
3414	mutex_exit(&ph->p_usba_device->usb_mutex);
3415
3416	/* Obtain the node */
3417	node = pp->pp_node;
3418
3419	/* Adjust polling interval to be a power of 2 */
3420	mutex_enter(&ph->p_usba_device->usb_mutex);
3421	interval = ohci_adjust_polling_interval(ohcip,
3422	    endpoint, ph->p_usba_device->usb_port_status);
3423	mutex_exit(&ph->p_usba_device->usb_mutex);
3424
3425	/* Find the height in the tree */
3426	height = ohci_lattice_height(interval);
3427
3428	/*
3429	 * Find the leftmost leaf in the subtree specified by the node
3430	 */
3431	leftmost = ohci_leftmost_leaf(node, height);
3432
3433	/* Delete the bandwith from the appropriate lists */
3434	for (i = 0; i < (NUM_INTR_ED_LISTS/interval); i++) {
3435		list = ohci_hcca_leaf_index(leftmost + i);
3436		ohcip->ohci_periodic_bandwidth[list] -= bandwidth;
3437	}
3438
3439	min = ohcip->ohci_periodic_bandwidth[0];
3440
3441	/* Recompute the minimum */
3442	for (i = 1; i < NUM_INTR_ED_LISTS; i++) {
3443		if (ohcip->ohci_periodic_bandwidth[i] < min) {
3444			min = ohcip->ohci_periodic_bandwidth[i];
3445		}
3446	}
3447
3448	/* Save the minimum for later use */
3449	ohcip->ohci_periodic_minimum_bandwidth = min;
3450}
3451
3452
3453/*
3454 * ohci_compute_total_bandwidth:
3455 *
3456 * Given a periodic endpoint (interrupt or isochronous) determine the total
3457 * bandwidth for one transaction. The OpenHCI host controller traverses the
3458 * endpoint descriptor lists on a first-come-first-serve basis. When the HC
3459 * services an endpoint, only a single transaction attempt is made. The  HC
3460 * moves to the next Endpoint Descriptor after the first transaction attempt
3461 * rather than finishing the entire Transfer Descriptor. Therefore, when  a
3462 * Transfer Descriptor is inserted into the lattice, we will only count the
3463 * number of bytes for one transaction.
3464 *
3465 * The following are the formulas used for  calculating bandwidth in  terms
3466 * bytes and it is for the single USB full speed and low speed	transaction
3467 * respectively. The protocol overheads will be different for each of  type
3468 * of USB transfer and all these formulas & protocol overheads are  derived
3469 * from the 5.9.3 section of USB Specification & with the help of Bandwidth
3470 * Analysis white paper which is posted on the USB  developer forum.
3471 *
3472 * Full-Speed:
3473 *		Protocol overhead  + ((MaxPacketSize * 7)/6 )  + Host_Delay
3474 *
3475 * Low-Speed:
3476 *		Protocol overhead  + Hub LS overhead +
3477 *		  (Low-Speed clock * ((MaxPacketSize * 7)/6 )) + Host_Delay
3478 */
3479static int
3480ohci_compute_total_bandwidth(
3481	usb_ep_descr_t		*endpoint,
3482	usb_port_status_t	port_status,
3483	uint_t			*bandwidth)
3484{
3485	ushort_t		maxpacketsize = endpoint->wMaxPacketSize;
3486
3487	/*
3488	 * If endpoint maximum packet is zero, then return immediately.
3489	 */
3490	if (maxpacketsize == 0) {
3491
3492		return (USB_NOT_SUPPORTED);
3493	}
3494
3495	/* Add Host Controller specific delay to required bandwidth */
3496	*bandwidth = HOST_CONTROLLER_DELAY;
3497
3498	/* Add bit-stuffing overhead */
3499	maxpacketsize = (ushort_t)((maxpacketsize * 7) / 6);
3500
3501	/* Low Speed interrupt transaction */
3502	if (port_status == USBA_LOW_SPEED_DEV) {
3503		/* Low Speed interrupt transaction */
3504		*bandwidth += (LOW_SPEED_PROTO_OVERHEAD +
3505		    HUB_LOW_SPEED_PROTO_OVERHEAD +
3506		    (LOW_SPEED_CLOCK * maxpacketsize));
3507	} else {
3508		/* Full Speed transaction */
3509		*bandwidth += maxpacketsize;
3510
3511		if ((endpoint->bmAttributes &
3512		    USB_EP_ATTR_MASK) == USB_EP_ATTR_INTR) {
3513			/* Full Speed interrupt transaction */
3514			*bandwidth += FS_NON_ISOC_PROTO_OVERHEAD;
3515		} else {
3516			/* Isochronous and input transaction */
3517			if ((endpoint->bEndpointAddress &
3518			    USB_EP_DIR_MASK) == USB_EP_DIR_IN) {
3519				*bandwidth += FS_ISOC_INPUT_PROTO_OVERHEAD;
3520			} else {
3521				/* Isochronous and output transaction */
3522				*bandwidth += FS_ISOC_OUTPUT_PROTO_OVERHEAD;
3523			}
3524		}
3525	}
3526
3527	return (USB_SUCCESS);
3528}
3529
3530
3531/*
3532 * ohci_adjust_polling_interval:
3533 */
3534static int
3535ohci_adjust_polling_interval(
3536	ohci_state_t		*ohcip,
3537	usb_ep_descr_t		*endpoint,
3538	usb_port_status_t	port_status)
3539{
3540	uint_t			interval;
3541	int			i = 0;
3542
3543	/*
3544	 * Get the polling interval from the endpoint descriptor
3545	 */
3546	interval = endpoint->bInterval;
3547
3548	/*
3549	 * The bInterval value in the endpoint descriptor can range
3550	 * from 1 to 255ms. The interrupt lattice has 32 leaf nodes,
3551	 * and the host controller cycles through these nodes every
3552	 * 32ms. The longest polling  interval that the  controller
3553	 * supports is 32ms.
3554	 */
3555
3556	/*
3557	 * Return an error if the polling interval is less than 1ms
3558	 * and greater than 255ms
3559	 */
3560	if ((interval < MIN_POLL_INTERVAL) ||
3561	    (interval > MAX_POLL_INTERVAL)) {
3562
3563		USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
3564		    "ohci_adjust_polling_interval: "
3565		    "Endpoint's poll interval must be between %d and %d ms",
3566		    MIN_POLL_INTERVAL, MAX_POLL_INTERVAL);
3567
3568		return (USB_FAILURE);
3569	}
3570
3571	/*
3572	 * According USB Specifications, a  full-speed endpoint can
3573	 * specify a desired polling interval 1ms to 255ms and a low
3574	 * speed  endpoints are limited to  specifying only 10ms to
3575	 * 255ms. But some old keyboards & mice uses polling interval
3576	 * of 8ms. For compatibility  purpose, we are using polling
3577	 * interval between 8ms & 255ms for low speed endpoints. But
3578	 * ohci driver will reject the any low speed endpoints which
3579	 * request polling interval less than 8ms.
3580	 */
3581	if ((port_status == USBA_LOW_SPEED_DEV) &&
3582	    (interval < MIN_LOW_SPEED_POLL_INTERVAL)) {
3583
3584		USB_DPRINTF_L2(PRINT_MASK_BW, ohcip->ohci_log_hdl,
3585		    "ohci_adjust_polling_interval: "
3586		    "Low speed endpoint's poll interval of %d ms "
3587		    "is below threshold.  Rounding up to %d ms",
3588		    interval, MIN_LOW_SPEED_POLL_INTERVAL);
3589
3590		interval = MIN_LOW_SPEED_POLL_INTERVAL;
3591	}
3592
3593	/*
3594	 * If polling interval is greater than 32ms,
3595	 * adjust polling interval equal to 32ms.
3596	 */
3597	if (interval > NUM_INTR_ED_LISTS) {
3598		interval = NUM_INTR_ED_LISTS;
3599	}
3600
3601	/*
3602	 * Find the nearest power of 2 that'sless
3603	 * than interval.
3604	 */
3605	while ((ohci_pow_2(i)) <= interval) {
3606		i++;
3607	}
3608
3609	return (ohci_pow_2((i - 1)));
3610}
3611
3612
3613/*
3614 * ohci_lattice_height:
3615 *
3616 * Given the requested bandwidth, find the height in the tree at which the
3617 * nodes for this bandwidth fall.  The height is measured as the number of
3618 * nodes from the leaf to the level specified by bandwidth The root of the
3619 * tree is at height TREE_HEIGHT.
3620 */
3621static uint_t
3622ohci_lattice_height(uint_t interval)
3623{
3624	return (TREE_HEIGHT - (ohci_log_2(interval)));
3625}
3626
3627
3628/*
3629 * ohci_lattice_parent:
3630 */
3631static uint_t
3632ohci_lattice_parent(uint_t node)
3633{
3634	if ((node % 2) == 0) {
3635		return ((node/2) - 1);
3636	} else {
3637		return ((node + 1)/2 - 1);
3638	}
3639}
3640
3641
3642/*
3643 * ohci_leftmost_leaf:
3644 *
3645 * Find the leftmost leaf in the subtree specified by the node. Height refers
3646 * to number of nodes from the bottom of the tree to the node,	including the
3647 * node.
3648 *
3649 * The formula for a zero based tree is:
3650 *     2^H * Node + 2^H - 1
3651 * The leaf of the tree is an array, convert the number for the array.
3652 *     Subtract the size of nodes not in the array
3653 *     2^H * Node + 2^H - 1 - (NUM_INTR_ED_LIST - 1) =
3654 *     2^H * Node + 2^H - NUM_INTR_ED_LIST =
3655 *     2^H * (Node + 1) - NUM_INTR_ED_LIST
3656 *	   0
3657 *	 1   2
3658 *	0 1 2 3
3659 */
3660static uint_t
3661ohci_leftmost_leaf(
3662	uint_t	node,
3663	uint_t	height)
3664{
3665	return ((ohci_pow_2(height) * (node + 1)) - NUM_INTR_ED_LISTS);
3666}
3667
3668/*
3669 * ohci_hcca_intr_index:
3670 *
3671 * Given a node in the lattice, find the index for the hcca interrupt table
3672 */
3673static uint_t
3674ohci_hcca_intr_index(uint_t node)
3675{
3676	/*
3677	 * Adjust the node to the array representing
3678	 * the bottom of the tree.
3679	 */
3680	node = node - NUM_STATIC_NODES;
3681
3682	if ((node % 2) == 0) {
3683		return (ohci_index[node / 2]);
3684	} else {
3685		return (ohci_index[node / 2] + (NUM_INTR_ED_LISTS / 2));
3686	}
3687}
3688
3689/*
3690 * ohci_hcca_leaf_index:
3691 *
3692 * Given a node in the bottom leaf array of the lattice, find the index
3693 * for the hcca interrupt table
3694 */
3695static uint_t
3696ohci_hcca_leaf_index(uint_t leaf)
3697{
3698	if ((leaf % 2) == 0) {
3699		return (ohci_index[leaf / 2]);
3700	} else {
3701		return (ohci_index[leaf / 2] + (NUM_INTR_ED_LISTS / 2));
3702	}
3703}
3704
3705/*
3706 * ohci_pow_2:
3707 *
3708 * Compute 2 to the power
3709 */
3710static uint_t
3711ohci_pow_2(uint_t x)
3712{
3713	if (x == 0) {
3714		return (1);
3715	} else {
3716		return (2 << (x - 1));
3717	}
3718}
3719
3720
3721/*
3722 * ohci_log_2:
3723 *
3724 * Compute log base 2 of x
3725 */
3726static uint_t
3727ohci_log_2(uint_t x)
3728{
3729	int i = 0;
3730
3731	while (x != 1) {
3732		x = x >> 1;
3733		i++;
3734	}
3735
3736	return (i);
3737}
3738
3739
3740/*
3741 * Endpoint Descriptor (ED) manipulations functions
3742 */
3743
3744/*
3745 * ohci_alloc_hc_ed:
3746 * NOTE: This function is also called from POLLED MODE.
3747 *
3748 * Allocate an endpoint descriptor (ED)
3749 */
3750ohci_ed_t *
3751ohci_alloc_hc_ed(
3752	ohci_state_t		*ohcip,
3753	usba_pipe_handle_data_t	*ph)
3754{
3755	int			i, state;
3756	ohci_ed_t		*hc_ed;
3757
3758	USB_DPRINTF_L4(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
3759	    "ohci_alloc_hc_ed: ph = 0x%p", (void *)ph);
3760
3761	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
3762
3763	/*
3764	 * The first 31 endpoints in the Endpoint Descriptor (ED)
3765	 * buffer pool are reserved for building interrupt lattice
3766	 * tree. Search for a blank endpoint descriptor in the ED
3767	 * buffer pool.
3768	 */
3769	for (i = NUM_STATIC_NODES; i < ohci_ed_pool_size; i ++) {
3770		state = Get_ED(ohcip->ohci_ed_pool_addr[i].hced_state);
3771
3772		if (state == HC_EPT_FREE) {
3773			break;
3774		}
3775	}
3776
3777	USB_DPRINTF_L4(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
3778	    "ohci_alloc_hc_ed: Allocated %d", i);
3779
3780	if (i == ohci_ed_pool_size) {
3781		USB_DPRINTF_L2(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
3782		    "ohci_alloc_hc_ed: ED exhausted");
3783
3784		return (NULL);
3785	} else {
3786
3787		hc_ed = &ohcip->ohci_ed_pool_addr[i];
3788
3789		USB_DPRINTF_L4(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
3790		    "ohci_alloc_hc_ed: Allocated address 0x%p", (void *)hc_ed);
3791
3792		ohci_print_ed(ohcip, hc_ed);
3793
3794		/* Unpack the endpoint descriptor into a control field */
3795		if (ph) {
3796			if ((ohci_initialize_dummy(ohcip,
3797			    hc_ed)) == USB_NO_RESOURCES) {
3798				bzero((void *)hc_ed, sizeof (ohci_ed_t));
3799				Set_ED(hc_ed->hced_state, HC_EPT_FREE);
3800				return (NULL);
3801			}
3802
3803			Set_ED(hc_ed->hced_prev, 0);
3804			Set_ED(hc_ed->hced_next, 0);
3805
3806			/* Change ED's state Active */
3807			Set_ED(hc_ed->hced_state, HC_EPT_ACTIVE);
3808
3809			Set_ED(hc_ed->hced_ctrl,
3810			    ohci_unpack_endpoint(ohcip, ph));
3811		} else {
3812			Set_ED(hc_ed->hced_ctrl, HC_EPT_sKip);
3813
3814			/* Change ED's state Static */
3815			Set_ED(hc_ed->hced_state, HC_EPT_STATIC);
3816		}
3817
3818		return (hc_ed);
3819	}
3820}
3821
3822
3823/*
3824 * ohci_unpack_endpoint:
3825 *
3826 * Unpack the information in the pipe handle and create the first byte
3827 * of the Host Controller's (HC) Endpoint Descriptor (ED).
3828 */
3829static uint_t
3830ohci_unpack_endpoint(
3831	ohci_state_t		*ohcip,
3832	usba_pipe_handle_data_t	*ph)
3833{
3834	usb_ep_descr_t		*endpoint = &ph->p_ep;
3835	uint_t			maxpacketsize, addr, ctrl = 0;
3836
3837	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
3838	    "ohci_unpack_endpoint:");
3839
3840	ctrl = ph->p_usba_device->usb_addr;
3841
3842	addr = endpoint->bEndpointAddress;
3843
3844	/* Assign the endpoint's address */
3845	ctrl = ctrl | ((addr & USB_EP_NUM_MASK) << HC_EPT_EP_SHFT);
3846
3847	/*
3848	 * Assign the direction. If the endpoint is a control endpoint,
3849	 * the direction is assigned by the Transfer Descriptor (TD).
3850	 */
3851	if ((endpoint->bmAttributes &
3852	    USB_EP_ATTR_MASK) != USB_EP_ATTR_CONTROL) {
3853		if (addr & USB_EP_DIR_MASK) {
3854			/* The direction is IN */
3855			ctrl = ctrl | HC_EPT_DF_IN;
3856		} else {
3857			/* The direction is OUT */
3858			ctrl = ctrl | HC_EPT_DF_OUT;
3859		}
3860	}
3861
3862	/* Assign the speed */
3863	mutex_enter(&ph->p_usba_device->usb_mutex);
3864	if (ph->p_usba_device->usb_port_status == USBA_LOW_SPEED_DEV) {
3865		ctrl = ctrl | HC_EPT_Speed;
3866	}
3867	mutex_exit(&ph->p_usba_device->usb_mutex);
3868
3869	/* Assign the format */
3870	if ((endpoint->bmAttributes &
3871	    USB_EP_ATTR_MASK) == USB_EP_ATTR_ISOCH) {
3872		ctrl = ctrl | HC_EPT_Format;
3873	}
3874
3875	maxpacketsize = endpoint->wMaxPacketSize;
3876	maxpacketsize = maxpacketsize << HC_EPT_MAXPKTSZ;
3877	ctrl = ctrl | (maxpacketsize & HC_EPT_MPS);
3878
3879	return (ctrl);
3880}
3881
3882
3883/*
3884 * ohci_insert_ed:
3885 *
3886 * Add the Endpoint Descriptor (ED) into the Host Controller's
3887 * (HC) appropriate endpoint list.
3888 */
3889static void
3890ohci_insert_ed(
3891	ohci_state_t		*ohcip,
3892	usba_pipe_handle_data_t	*ph)
3893{
3894	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
3895
3896	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
3897	    "ohci_insert_ed:");
3898
3899	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
3900
3901	switch (ph->p_ep.bmAttributes & USB_EP_ATTR_MASK) {
3902	case USB_EP_ATTR_CONTROL:
3903		ohci_insert_ctrl_ed(ohcip, pp);
3904		break;
3905	case USB_EP_ATTR_BULK:
3906		ohci_insert_bulk_ed(ohcip, pp);
3907		break;
3908	case USB_EP_ATTR_INTR:
3909		ohci_insert_intr_ed(ohcip, pp);
3910		break;
3911	case USB_EP_ATTR_ISOCH:
3912		ohci_insert_isoc_ed(ohcip, pp);
3913		break;
3914	}
3915}
3916
3917
3918/*
3919 * ohci_insert_ctrl_ed:
3920 *
3921 * Insert a control endpoint into the Host Controller's (HC)
3922 * control endpoint list.
3923 */
3924static void
3925ohci_insert_ctrl_ed(
3926	ohci_state_t		*ohcip,
3927	ohci_pipe_private_t	*pp)
3928{
3929	ohci_ed_t	*ept = pp->pp_ept;
3930	ohci_ed_t	*prev_ept;
3931
3932	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
3933	    "ohci_insert_ctrl_ed:");
3934
3935	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
3936
3937	/* Obtain a ptr to the head of the list */
3938	if (Get_OpReg(hcr_ctrl_head)) {
3939		prev_ept = ohci_ed_iommu_to_cpu(ohcip,
3940		    Get_OpReg(hcr_ctrl_head));
3941
3942		/* Set up the backwards pointer */
3943		Set_ED(prev_ept->hced_prev, ohci_ed_cpu_to_iommu(ohcip, ept));
3944	}
3945
3946	/* The new endpoint points to the head of the list */
3947	Set_ED(ept->hced_next, Get_OpReg(hcr_ctrl_head));
3948
3949	/* Set the head ptr to the new endpoint */
3950	Set_OpReg(hcr_ctrl_head, ohci_ed_cpu_to_iommu(ohcip, ept));
3951
3952	/*
3953	 * Enable Control list processing if control open
3954	 * pipe count is zero.
3955	 */
3956	if (!ohcip->ohci_open_ctrl_pipe_count) {
3957		/* Start Control list processing */
3958		Set_OpReg(hcr_control,
3959		    (Get_OpReg(hcr_control) | HCR_CONTROL_CLE));
3960	}
3961
3962	ohcip->ohci_open_ctrl_pipe_count++;
3963}
3964
3965
3966/*
3967 * ohci_insert_bulk_ed:
3968 *
3969 * Insert a bulk endpoint into the Host Controller's (HC) bulk endpoint list.
3970 */
3971static void
3972ohci_insert_bulk_ed(
3973	ohci_state_t		*ohcip,
3974	ohci_pipe_private_t	*pp)
3975{
3976	ohci_ed_t		*ept = pp->pp_ept;
3977	ohci_ed_t		*prev_ept;
3978
3979	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
3980	    "ohci_insert_bulk_ed:");
3981
3982	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
3983
3984	/* Obtain a ptr to the head of the Bulk list */
3985	if (Get_OpReg(hcr_bulk_head)) {
3986		prev_ept = ohci_ed_iommu_to_cpu(ohcip,
3987		    Get_OpReg(hcr_bulk_head));
3988
3989		/* Set up the backwards pointer */
3990		Set_ED(prev_ept->hced_prev, ohci_ed_cpu_to_iommu(ohcip, ept));
3991	}
3992
3993	/* The new endpoint points to the head of the Bulk list */
3994	Set_ED(ept->hced_next, Get_OpReg(hcr_bulk_head));
3995
3996	/* Set the Bulk head ptr to the new endpoint */
3997	Set_OpReg(hcr_bulk_head, ohci_ed_cpu_to_iommu(ohcip, ept));
3998
3999	/*
4000	 * Enable Bulk list processing if bulk open pipe
4001	 * count is zero.
4002	 */
4003	if (!ohcip->ohci_open_bulk_pipe_count) {
4004		/* Start Bulk list processing */
4005		Set_OpReg(hcr_control,
4006		    (Get_OpReg(hcr_control) | HCR_CONTROL_BLE));
4007	}
4008
4009	ohcip->ohci_open_bulk_pipe_count++;
4010}
4011
4012
4013/*
4014 * ohci_insert_intr_ed:
4015 *
4016 * Insert a interrupt endpoint into the Host Controller's (HC) interrupt
4017 * lattice tree.
4018 */
4019static void
4020ohci_insert_intr_ed(
4021	ohci_state_t		*ohcip,
4022	ohci_pipe_private_t	*pp)
4023{
4024	ohci_ed_t		*ept = pp->pp_ept;
4025	ohci_ed_t		*next_lattice_ept, *lattice_ept;
4026	uint_t			node;
4027
4028	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
4029
4030	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4031	    "ohci_insert_intr_ed:");
4032
4033	/*
4034	 * The appropriate node was found
4035	 * during the opening of the pipe.
4036	 */
4037	node = pp->pp_node;
4038
4039	if (node >= NUM_STATIC_NODES) {
4040		/* Get the hcca interrupt table index */
4041		node = ohci_hcca_intr_index(node);
4042
4043		/* Get the first endpoint on the list */
4044		next_lattice_ept = ohci_ed_iommu_to_cpu(ohcip,
4045		    Get_HCCA(ohcip->ohci_hccap->HccaIntTble[node]));
4046
4047		/* Update this endpoint to point to it */
4048		Set_ED(ept->hced_next,
4049		    ohci_ed_cpu_to_iommu(ohcip, next_lattice_ept));
4050
4051		/* Put this endpoint at the head of the list */
4052		Set_HCCA(ohcip->ohci_hccap->HccaIntTble[node],
4053		    ohci_ed_cpu_to_iommu(ohcip, ept));
4054
4055		/* The previous pointer is NULL */
4056		Set_ED(ept->hced_prev, 0);
4057
4058		/* Update the previous pointer of ept->hced_next */
4059		if (Get_ED(next_lattice_ept->hced_state) != HC_EPT_STATIC) {
4060			Set_ED(next_lattice_ept->hced_prev,
4061			    ohci_ed_cpu_to_iommu(ohcip, ept));
4062		}
4063	} else {
4064		/* Find the lattice endpoint */
4065		lattice_ept = &ohcip->ohci_ed_pool_addr[node];
4066
4067		/* Find the next lattice endpoint */
4068		next_lattice_ept = ohci_ed_iommu_to_cpu(
4069		    ohcip, Get_ED(lattice_ept->hced_next));
4070
4071		/*
4072		 * Update this endpoint to point to the next one in the
4073		 * lattice.
4074		 */
4075		Set_ED(ept->hced_next, Get_ED(lattice_ept->hced_next));
4076
4077		/* Insert this endpoint into the lattice */
4078		Set_ED(lattice_ept->hced_next,
4079		    ohci_ed_cpu_to_iommu(ohcip, ept));
4080
4081		/* Update the previous pointer */
4082		Set_ED(ept->hced_prev,
4083		    ohci_ed_cpu_to_iommu(ohcip, lattice_ept));
4084
4085		/* Update the previous pointer of ept->hced_next */
4086		if ((next_lattice_ept) &&
4087		    (Get_ED(next_lattice_ept->hced_state) != HC_EPT_STATIC)) {
4088
4089			Set_ED(next_lattice_ept->hced_prev,
4090			    ohci_ed_cpu_to_iommu(ohcip, ept));
4091		}
4092	}
4093
4094	/*
4095	 * Enable periodic list processing if periodic (interrupt
4096	 * and isochronous) open pipe count is zero.
4097	 */
4098	if (!ohcip->ohci_open_periodic_pipe_count) {
4099		ASSERT(!ohcip->ohci_open_isoch_pipe_count);
4100
4101		Set_OpReg(hcr_control,
4102		    (Get_OpReg(hcr_control) | HCR_CONTROL_PLE));
4103	}
4104
4105	ohcip->ohci_open_periodic_pipe_count++;
4106}
4107
4108
4109/*
4110 * ohci_insert_isoc_ed:
4111 *
4112 * Insert a isochronous endpoint into the Host Controller's (HC) interrupt
4113 * lattice tree. A isochronous endpoint will be inserted at the end of the
4114 * 1ms interrupt endpoint list.
4115 */
4116static void
4117ohci_insert_isoc_ed(
4118	ohci_state_t		*ohcip,
4119	ohci_pipe_private_t	*pp)
4120{
4121	ohci_ed_t		*next_lattice_ept, *lattice_ept;
4122	ohci_ed_t		*ept = pp->pp_ept;
4123	uint_t			node;
4124
4125	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
4126
4127	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4128	    "ohci_insert_isoc_ed:");
4129
4130	/*
4131	 * The appropriate node was found during the opening of the pipe.
4132	 * This  node must be root of the interrupt lattice tree.
4133	 */
4134	node = pp->pp_node;
4135
4136	ASSERT(node == 0);
4137
4138	/* Find the 1ms interrupt lattice endpoint */
4139	lattice_ept = &ohcip->ohci_ed_pool_addr[node];
4140
4141	/* Find the next lattice endpoint */
4142	next_lattice_ept = ohci_ed_iommu_to_cpu(
4143	    ohcip, Get_ED(lattice_ept->hced_next));
4144
4145	while (next_lattice_ept) {
4146		lattice_ept = next_lattice_ept;
4147
4148		/* Find the next lattice endpoint */
4149		next_lattice_ept = ohci_ed_iommu_to_cpu(
4150		    ohcip, Get_ED(lattice_ept->hced_next));
4151	}
4152
4153	/* The next pointer is NULL */
4154	Set_ED(ept->hced_next, 0);
4155
4156	/* Update the previous pointer */
4157	Set_ED(ept->hced_prev, ohci_ed_cpu_to_iommu(ohcip, lattice_ept));
4158
4159	/* Insert this endpoint into the lattice */
4160	Set_ED(lattice_ept->hced_next, ohci_ed_cpu_to_iommu(ohcip, ept));
4161
4162	/*
4163	 * Enable periodic and isoch lists processing if isoch
4164	 * open pipe count is zero.
4165	 */
4166	if (!ohcip->ohci_open_isoch_pipe_count) {
4167
4168		Set_OpReg(hcr_control, (Get_OpReg(hcr_control) |
4169		    HCR_CONTROL_PLE | HCR_CONTROL_IE));
4170	}
4171
4172	ohcip->ohci_open_periodic_pipe_count++;
4173	ohcip->ohci_open_isoch_pipe_count++;
4174}
4175
4176
4177/*
4178 * ohci_modify_sKip_bit:
4179 *
4180 * Modify the sKip bit on the Host Controller (HC) Endpoint Descriptor (ED).
4181 */
4182static void
4183ohci_modify_sKip_bit(
4184	ohci_state_t		*ohcip,
4185	ohci_pipe_private_t	*pp,
4186	skip_bit_t		action,
4187	usb_flags_t		flag)
4188{
4189	ohci_ed_t		*ept = pp->pp_ept;
4190
4191	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4192	    "ohci_modify_sKip_bit: action = 0x%x flag = 0x%x",
4193	    action, flag);
4194
4195	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
4196
4197	if (action == CLEAR_sKip) {
4198		/*
4199		 * If the skip bit is to be cleared, just clear it.
4200		 * there shouldn't be any race condition problems.
4201		 * If the host controller reads the bit before the
4202		 * driver has a chance to set the bit, the bit will
4203		 * be reread on the next frame.
4204		 */
4205		Set_ED(ept->hced_ctrl, (Get_ED(ept->hced_ctrl) & ~HC_EPT_sKip));
4206	} else {
4207		/* Sync ED and TD pool */
4208		if (flag & OHCI_FLAGS_DMA_SYNC) {
4209			Sync_ED_TD_Pool(ohcip);
4210		}
4211
4212		/* Check Halt or Skip bit is already set */
4213		if ((Get_ED(ept->hced_headp) & HC_EPT_Halt) ||
4214		    (Get_ED(ept->hced_ctrl) & HC_EPT_sKip)) {
4215
4216			USB_DPRINTF_L3(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4217			    "ohci_modify_sKip_bit: "
4218			    "Halt or Skip bit is already set");
4219		} else {
4220			/*
4221			 * The action is to set the skip bit.  In order to
4222			 * be sure that the HCD has seen the sKip bit, wait
4223			 * for the next start of frame.
4224			 */
4225			Set_ED(ept->hced_ctrl,
4226			    (Get_ED(ept->hced_ctrl) | HC_EPT_sKip));
4227
4228			if (flag & OHCI_FLAGS_SLEEP) {
4229				/* Wait for the next SOF */
4230				(void) ohci_wait_for_sof(ohcip);
4231
4232				/* Sync ED and TD pool */
4233				if (flag & OHCI_FLAGS_DMA_SYNC) {
4234					Sync_ED_TD_Pool(ohcip);
4235				}
4236			}
4237		}
4238	}
4239}
4240
4241
4242/*
4243 * ohci_remove_ed:
4244 *
4245 * Remove the Endpoint Descriptor (ED) from the Host Controller's appropriate
4246 * endpoint list.
4247 */
4248static void
4249ohci_remove_ed(
4250	ohci_state_t		*ohcip,
4251	ohci_pipe_private_t	*pp)
4252{
4253	uchar_t			attributes;
4254
4255	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
4256
4257	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4258	    "ohci_remove_ed:");
4259
4260	attributes = pp->pp_pipe_handle->p_ep.bmAttributes & USB_EP_ATTR_MASK;
4261
4262	switch (attributes) {
4263	case USB_EP_ATTR_CONTROL:
4264		ohci_remove_ctrl_ed(ohcip, pp);
4265		break;
4266	case USB_EP_ATTR_BULK:
4267		ohci_remove_bulk_ed(ohcip, pp);
4268		break;
4269	case USB_EP_ATTR_INTR:
4270	case USB_EP_ATTR_ISOCH:
4271		ohci_remove_periodic_ed(ohcip, pp);
4272		break;
4273	}
4274}
4275
4276
4277/*
4278 * ohci_remove_ctrl_ed:
4279 *
4280 * Remove a control Endpoint Descriptor (ED) from the Host Controller's (HC)
4281 * control endpoint list.
4282 */
4283static void
4284ohci_remove_ctrl_ed(
4285	ohci_state_t		*ohcip,
4286	ohci_pipe_private_t	*pp)
4287{
4288	ohci_ed_t		*ept = pp->pp_ept; /* ept to be removed */
4289
4290	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4291	    "ohci_remove_ctrl_ed:");
4292
4293	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
4294
4295	/* The control list should already be stopped */
4296	ASSERT(!(Get_OpReg(hcr_control) & HCR_CONTROL_CLE));
4297
4298	ohcip->ohci_open_ctrl_pipe_count--;
4299
4300	/* Detach the endpoint from the list that it's on */
4301	ohci_detach_ed_from_list(ohcip, ept, USB_EP_ATTR_CONTROL);
4302
4303	/*
4304	 * If next endpoint pointed by endpoint to be removed is not NULL
4305	 * then set current control pointer to the next endpoint pointed by
4306	 * endpoint to be removed. Otherwise set current control pointer to
4307	 * the beginning of the control list.
4308	 */
4309	if (Get_ED(ept->hced_next)) {
4310		Set_OpReg(hcr_ctrl_curr, Get_ED(ept->hced_next));
4311	} else {
4312		Set_OpReg(hcr_ctrl_curr, Get_OpReg(hcr_ctrl_head));
4313	}
4314
4315	if (ohcip->ohci_open_ctrl_pipe_count) {
4316		ASSERT(Get_OpReg(hcr_ctrl_head));
4317
4318		/* Reenable the control list */
4319		Set_OpReg(hcr_control,
4320		    (Get_OpReg(hcr_control) | HCR_CONTROL_CLE));
4321	}
4322
4323	ohci_insert_ed_on_reclaim_list(ohcip, pp);
4324}
4325
4326
4327/*
4328 * ohci_remove_bulk_ed:
4329 *
4330 * Remove free the  bulk Endpoint Descriptor (ED) from the Host Controller's
4331 * (HC) bulk endpoint list.
4332 */
4333static void
4334ohci_remove_bulk_ed(
4335	ohci_state_t		*ohcip,
4336	ohci_pipe_private_t	*pp)
4337{
4338	ohci_ed_t		*ept = pp->pp_ept;	/* ept to be removed */
4339
4340	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4341	    "ohci_remove_bulk_ed:");
4342
4343	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
4344
4345	/* The bulk list should already be stopped */
4346	ASSERT(!(Get_OpReg(hcr_control) & HCR_CONTROL_BLE));
4347
4348	ohcip->ohci_open_bulk_pipe_count--;
4349
4350	/* Detach the endpoint from the bulk list */
4351	ohci_detach_ed_from_list(ohcip, ept, USB_EP_ATTR_BULK);
4352
4353	/*
4354	 * If next endpoint pointed by endpoint to be removed is not NULL
4355	 * then set current bulk pointer to the next endpoint pointed by
4356	 * endpoint to be removed. Otherwise set current bulk pointer to
4357	 * the beginning of the bulk list.
4358	 */
4359	if (Get_ED(ept->hced_next)) {
4360		Set_OpReg(hcr_bulk_curr, Get_ED(ept->hced_next));
4361	} else {
4362		Set_OpReg(hcr_bulk_curr, Get_OpReg(hcr_bulk_head));
4363	}
4364
4365	if (ohcip->ohci_open_bulk_pipe_count) {
4366		ASSERT(Get_OpReg(hcr_bulk_head));
4367
4368		/* Re-enable the bulk list */
4369		Set_OpReg(hcr_control,
4370		    (Get_OpReg(hcr_control) | HCR_CONTROL_BLE));
4371	}
4372
4373	ohci_insert_ed_on_reclaim_list(ohcip, pp);
4374}
4375
4376
4377/*
4378 * ohci_remove_periodic_ed:
4379 *
4380 * Set up an periodic endpoint to be removed from the Host Controller's (HC)
4381 * interrupt lattice tree. The Endpoint Descriptor (ED) will be freed in the
4382 * interrupt handler.
4383 */
4384static void
4385ohci_remove_periodic_ed(
4386	ohci_state_t		*ohcip,
4387	ohci_pipe_private_t	*pp)
4388{
4389	ohci_ed_t		*ept = pp->pp_ept;	/* ept to be removed */
4390	uint_t			ept_type;
4391
4392	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4393	    "ohci_remove_periodic_ed:");
4394
4395	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
4396
4397	ASSERT((Get_ED(ept->hced_tailp) & HC_EPT_TD_TAIL) ==
4398	    (Get_ED(ept->hced_headp) & HC_EPT_TD_HEAD));
4399
4400	ohcip->ohci_open_periodic_pipe_count--;
4401
4402	ept_type = pp->pp_pipe_handle->
4403	    p_ep.bmAttributes & USB_EP_ATTR_MASK;
4404
4405	if (ept_type == USB_EP_ATTR_ISOCH) {
4406		ohcip->ohci_open_isoch_pipe_count--;
4407	}
4408
4409	/* Store the node number */
4410	Set_ED(ept->hced_node, pp->pp_node);
4411
4412	/* Remove the endpoint from interrupt lattice tree */
4413	ohci_detach_ed_from_list(ohcip, ept, ept_type);
4414
4415	/*
4416	 * Disable isoch list processing if isoch open pipe count
4417	 * is zero.
4418	 */
4419	if (!ohcip->ohci_open_isoch_pipe_count) {
4420		Set_OpReg(hcr_control,
4421		    (Get_OpReg(hcr_control) & ~(HCR_CONTROL_IE)));
4422	}
4423
4424	/*
4425	 * Disable periodic list processing if periodic (interrupt
4426	 * and isochrous) open pipe count is zero.
4427	 */
4428	if (!ohcip->ohci_open_periodic_pipe_count) {
4429		ASSERT(!ohcip->ohci_open_isoch_pipe_count);
4430
4431		Set_OpReg(hcr_control,
4432		    (Get_OpReg(hcr_control) & ~(HCR_CONTROL_PLE)));
4433	}
4434
4435	ohci_insert_ed_on_reclaim_list(ohcip, pp);
4436}
4437
4438
4439/*
4440 * ohci_detach_ed_from_list:
4441 *
4442 * Remove the Endpoint Descriptor (ED) from the appropriate Host Controller's
4443 * (HC) endpoint list.
4444 */
4445static void
4446ohci_detach_ed_from_list(
4447	ohci_state_t	*ohcip,
4448	ohci_ed_t	*ept,
4449	uint_t		ept_type)
4450{
4451	ohci_ed_t	*prev_ept;	/* Previous endpoint */
4452	ohci_ed_t	*next_ept;	/* Endpoint after one to be removed */
4453	uint_t		node;
4454
4455	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4456	    "ohci_detach_ed_from_list:");
4457
4458	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
4459
4460	prev_ept = ohci_ed_iommu_to_cpu(ohcip, Get_ED(ept->hced_prev));
4461	next_ept = ohci_ed_iommu_to_cpu(ohcip, Get_ED(ept->hced_next));
4462
4463	/*
4464	 * If there is no previous endpoint, then this
4465	 * endpoint is at the head of the endpoint list.
4466	 */
4467	if (prev_ept == NULL) {
4468		if (next_ept) {
4469			/*
4470			 * If this endpoint is the first element of the
4471			 * list and there is more  than one endpoint on
4472			 * the list then perform specific actions based
4473			 * on the type of endpoint list.
4474			 */
4475			switch (ept_type) {
4476			case USB_EP_ATTR_CONTROL:
4477				/* Set the head of list to next ept */
4478				Set_OpReg(hcr_ctrl_head,
4479				    Get_ED(ept->hced_next));
4480
4481				/* Clear prev ptr of  next endpoint */
4482				Set_ED(next_ept->hced_prev, 0);
4483				break;
4484			case USB_EP_ATTR_BULK:
4485				/* Set the head of list to next ept */
4486				Set_OpReg(hcr_bulk_head,
4487				    Get_ED(ept->hced_next));
4488
4489				/* Clear prev ptr of  next endpoint */
4490				Set_ED(next_ept->hced_prev, 0);
4491				break;
4492			case USB_EP_ATTR_INTR:
4493				/*
4494				 * HCCA area should point
4495				 * directly to this ept.
4496				 */
4497				ASSERT(Get_ED(ept->hced_node) >=
4498				    NUM_STATIC_NODES);
4499
4500				/* Get the hcca interrupt table index */
4501				node = ohci_hcca_intr_index(
4502				    Get_ED(ept->hced_node));
4503
4504				/*
4505				 * Delete the ept from the
4506				 * bottom of the tree.
4507				 */
4508				Set_HCCA(ohcip->ohci_hccap->
4509				    HccaIntTble[node], Get_ED(ept->hced_next));
4510
4511				/*
4512				 * Update the previous pointer
4513				 * of ept->hced_next
4514				 */
4515				if (Get_ED(next_ept->hced_state) !=
4516				    HC_EPT_STATIC) {
4517
4518					Set_ED(next_ept->hced_prev, 0);
4519				}
4520
4521				break;
4522			case USB_EP_ATTR_ISOCH:
4523			default:
4524				break;
4525			}
4526		} else {
4527			/*
4528			 * If there was only one element on the list
4529			 * perform specific actions based on the type
4530			 * of the list.
4531			 */
4532			switch (ept_type) {
4533			case USB_EP_ATTR_CONTROL:
4534				/* Set the head to NULL */
4535				Set_OpReg(hcr_ctrl_head, 0);
4536				break;
4537			case USB_EP_ATTR_BULK:
4538				/* Set the head to NULL */
4539				Set_OpReg(hcr_bulk_head, 0);
4540				break;
4541			case USB_EP_ATTR_INTR:
4542			case USB_EP_ATTR_ISOCH:
4543			default:
4544				break;
4545			}
4546		}
4547	} else {
4548		/* The previous ept points to the next one */
4549		Set_ED(prev_ept->hced_next, Get_ED(ept->hced_next));
4550
4551		/*
4552		 * Set the previous ptr of the next_ept to prev_ept
4553		 * if this isn't the last endpoint on the list
4554		 */
4555		if ((next_ept) &&
4556		    (Get_ED(next_ept->hced_state) != HC_EPT_STATIC)) {
4557
4558			/* Set the previous ptr of the next one */
4559			Set_ED(next_ept->hced_prev, Get_ED(ept->hced_prev));
4560		}
4561	}
4562}
4563
4564
4565/*
4566 * ohci_insert_ed_on_reclaim_list:
4567 *
4568 * Insert Endpoint onto the reclaim list
4569 */
4570static void
4571ohci_insert_ed_on_reclaim_list(
4572	ohci_state_t		*ohcip,
4573	ohci_pipe_private_t	*pp)
4574{
4575	ohci_ed_t		*ept = pp->pp_ept; /* ept to be removed */
4576	ohci_ed_t		*next_ept, *prev_ept;
4577	usb_frame_number_t	frame_number;
4578
4579	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
4580
4581	/*
4582	 * Read current usb frame number and add appropriate number of
4583	 * usb frames needs to wait before reclaiming current endpoint.
4584	 */
4585	frame_number =
4586	    ohci_get_current_frame_number(ohcip) + MAX_SOF_WAIT_COUNT;
4587
4588	/* Store 32bit ID */
4589	Set_ED(ept->hced_reclaim_frame,
4590	    ((uint32_t)(OHCI_GET_ID((void *)(uintptr_t)frame_number))));
4591
4592	/* Insert the endpoint onto the reclaimation list */
4593	if (ohcip->ohci_reclaim_list) {
4594		next_ept = ohcip->ohci_reclaim_list;
4595
4596		while (next_ept) {
4597			prev_ept = next_ept;
4598			next_ept = ohci_ed_iommu_to_cpu(ohcip,
4599			    Get_ED(next_ept->hced_reclaim_next));
4600		}
4601
4602		Set_ED(prev_ept->hced_reclaim_next,
4603		    ohci_ed_cpu_to_iommu(ohcip, ept));
4604	} else {
4605		ohcip->ohci_reclaim_list = ept;
4606	}
4607
4608	ASSERT(Get_ED(ept->hced_reclaim_next) == 0);
4609
4610	/* Enable the SOF interrupt */
4611	Set_OpReg(hcr_intr_enable, HCR_INTR_SOF);
4612}
4613
4614
4615/*
4616 * ohci_deallocate_ed:
4617 * NOTE: This function is also called from POLLED MODE.
4618 *
4619 * Deallocate a Host Controller's (HC) Endpoint Descriptor (ED).
4620 */
4621void
4622ohci_deallocate_ed(
4623	ohci_state_t	*ohcip,
4624	ohci_ed_t	*old_ed)
4625{
4626	ohci_td_t	*dummy_td;
4627
4628	USB_DPRINTF_L4(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
4629	    "ohci_deallocate_ed:");
4630
4631	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
4632
4633	dummy_td = ohci_td_iommu_to_cpu(ohcip, Get_ED(old_ed->hced_headp));
4634
4635	if (dummy_td) {
4636
4637		ASSERT(Get_TD(dummy_td->hctd_state) == HC_TD_DUMMY);
4638		ohci_deallocate_td(ohcip, dummy_td);
4639	}
4640
4641	USB_DPRINTF_L4(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
4642	    "ohci_deallocate_ed: Deallocated 0x%p", (void *)old_ed);
4643
4644	bzero((void *)old_ed, sizeof (ohci_ed_t));
4645	Set_ED(old_ed->hced_state, HC_EPT_FREE);
4646}
4647
4648
4649/*
4650 * ohci_ed_cpu_to_iommu:
4651 * NOTE: This function is also called from POLLED MODE.
4652 *
4653 * This function converts for the given Endpoint Descriptor (ED) CPU address
4654 * to IO address.
4655 */
4656uint32_t
4657ohci_ed_cpu_to_iommu(
4658	ohci_state_t	*ohcip,
4659	ohci_ed_t	*addr)
4660{
4661	uint32_t	ed;
4662
4663	ed = (uint32_t)ohcip->ohci_ed_pool_cookie.dmac_address +
4664	    (uint32_t)((uintptr_t)addr - (uintptr_t)(ohcip->ohci_ed_pool_addr));
4665
4666	ASSERT(ed >= ohcip->ohci_ed_pool_cookie.dmac_address);
4667	ASSERT(ed <= ohcip->ohci_ed_pool_cookie.dmac_address +
4668	    sizeof (ohci_ed_t) * ohci_ed_pool_size);
4669
4670	return (ed);
4671}
4672
4673
4674/*
4675 * ohci_ed_iommu_to_cpu:
4676 *
4677 * This function converts for the given Endpoint Descriptor (ED) IO address
4678 * to CPU address.
4679 */
4680static ohci_ed_t *
4681ohci_ed_iommu_to_cpu(
4682	ohci_state_t	*ohcip,
4683	uintptr_t	addr)
4684{
4685	ohci_ed_t	*ed;
4686
4687	if (addr == 0)
4688		return (NULL);
4689
4690	ed = (ohci_ed_t *)((uintptr_t)
4691	    (addr - ohcip->ohci_ed_pool_cookie.dmac_address) +
4692	    (uintptr_t)ohcip->ohci_ed_pool_addr);
4693
4694	ASSERT(ed >= ohcip->ohci_ed_pool_addr);
4695	ASSERT((uintptr_t)ed <= (uintptr_t)ohcip->ohci_ed_pool_addr +
4696	    (uintptr_t)(sizeof (ohci_ed_t) * ohci_ed_pool_size));
4697
4698	return (ed);
4699}
4700
4701
4702/*
4703 * Transfer Descriptor manipulations functions
4704 */
4705
4706/*
4707 * ohci_initialize_dummy:
4708 *
4709 * An Endpoint Descriptor (ED) has a  dummy Transfer Descriptor (TD) on the
4710 * end of its TD list. Initially, both the head and tail pointers of the ED
4711 * point to the dummy TD.
4712 */
4713static int
4714ohci_initialize_dummy(
4715	ohci_state_t	*ohcip,
4716	ohci_ed_t	*ept)
4717{
4718	ohci_td_t *dummy;
4719
4720	/* Obtain a  dummy TD */
4721	dummy = ohci_allocate_td_from_pool(ohcip);
4722
4723	if (dummy == NULL) {
4724		return (USB_NO_RESOURCES);
4725	}
4726
4727	/*
4728	 * Both the head and tail pointers of an ED point
4729	 * to this new dummy TD.
4730	 */
4731	Set_ED(ept->hced_headp, (ohci_td_cpu_to_iommu(ohcip, dummy)));
4732	Set_ED(ept->hced_tailp, (ohci_td_cpu_to_iommu(ohcip, dummy)));
4733
4734	return (USB_SUCCESS);
4735}
4736
4737/*
4738 * ohci_allocate_ctrl_resources:
4739 *
4740 * Calculates the number of tds necessary for a ctrl transfer, and allocates
4741 * all the resources necessary.
4742 *
4743 * Returns NULL if there is insufficient resources otherwise TW.
4744 */
4745static ohci_trans_wrapper_t *
4746ohci_allocate_ctrl_resources(
4747	ohci_state_t		*ohcip,
4748	ohci_pipe_private_t	*pp,
4749	usb_ctrl_req_t		*ctrl_reqp,
4750	usb_flags_t		usb_flags)
4751{
4752	size_t			td_count = 2;
4753	size_t			ctrl_buf_size;
4754	ohci_trans_wrapper_t	*tw;
4755
4756	/* Add one more td for data phase */
4757	if (ctrl_reqp->ctrl_wLength) {
4758		td_count++;
4759	}
4760
4761	/*
4762	 * If we have a control data phase, the data buffer starts
4763	 * on the next 4K page boundary. So the TW buffer is allocated
4764	 * to be larger than required. The buffer in the range of
4765	 * [SETUP_SIZE, OHCI_MAX_TD_BUF_SIZE) is just for padding
4766	 * and not to be transferred.
4767	 */
4768	if (ctrl_reqp->ctrl_wLength) {
4769		ctrl_buf_size = OHCI_MAX_TD_BUF_SIZE +
4770		    ctrl_reqp->ctrl_wLength;
4771	} else {
4772		ctrl_buf_size = SETUP_SIZE;
4773	}
4774
4775	tw = ohci_allocate_tw_resources(ohcip, pp, ctrl_buf_size,
4776	    usb_flags, td_count);
4777
4778	return (tw);
4779}
4780
4781/*
4782 * ohci_insert_ctrl_req:
4783 *
4784 * Create a Transfer Descriptor (TD) and a data buffer for a control endpoint.
4785 */
4786/* ARGSUSED */
4787static void
4788ohci_insert_ctrl_req(
4789	ohci_state_t		*ohcip,
4790	usba_pipe_handle_data_t	*ph,
4791	usb_ctrl_req_t		*ctrl_reqp,
4792	ohci_trans_wrapper_t	*tw,
4793	usb_flags_t		usb_flags)
4794{
4795	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
4796	uchar_t			bmRequestType = ctrl_reqp->ctrl_bmRequestType;
4797	uchar_t			bRequest = ctrl_reqp->ctrl_bRequest;
4798	uint16_t		wValue = ctrl_reqp->ctrl_wValue;
4799	uint16_t		wIndex = ctrl_reqp->ctrl_wIndex;
4800	uint16_t		wLength = ctrl_reqp->ctrl_wLength;
4801	mblk_t			*data = ctrl_reqp->ctrl_data;
4802	uint32_t		ctrl = 0;
4803	int			sdata;
4804
4805	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4806	    "ohci_insert_ctrl_req:");
4807
4808	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
4809
4810	/*
4811	 * Save current control request pointer and timeout values
4812	 * in transfer wrapper.
4813	 */
4814	tw->tw_curr_xfer_reqp = (usb_opaque_t)ctrl_reqp;
4815	tw->tw_timeout = ctrl_reqp->ctrl_timeout ?
4816	    ctrl_reqp->ctrl_timeout : OHCI_DEFAULT_XFER_TIMEOUT;
4817
4818	/*
4819	 * Initialize the callback and any callback data for when
4820	 * the td completes.
4821	 */
4822	tw->tw_handle_td = ohci_handle_ctrl_td;
4823	tw->tw_handle_callback_value = NULL;
4824
4825	/* Create the first four bytes of the setup packet */
4826	sdata = (bmRequestType << 24) | (bRequest << 16) |
4827	    (((wValue >> 8) | (wValue << 8)) & 0x0000FFFF);
4828
4829	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4830	    "ohci_create_setup_pkt: sdata = 0x%x", sdata);
4831
4832	ddi_put32(tw->tw_accesshandle, (uint_t *)tw->tw_buf, sdata);
4833
4834	/* Create the second four bytes */
4835	sdata = (uint32_t)(((((wIndex >> 8) |
4836	    (wIndex << 8)) << 16) & 0xFFFF0000) |
4837	    (((wLength >> 8) | (wLength << 8)) & 0x0000FFFF));
4838
4839	USB_DPRINTF_L4(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
4840	    "ohci_create_setup_pkt: sdata = 0x%x", sdata);
4841
4842	ddi_put32(tw->tw_accesshandle,
4843	    (uint_t *)((uintptr_t)tw->tw_buf + sizeof (uint_t)), sdata);
4844
4845	ctrl = HC_TD_SETUP|HC_TD_MS_DT|HC_TD_DT_0|HC_TD_6I;
4846
4847	/*
4848	 * The TD's are placed on the ED one at a time.
4849	 * Once this TD is placed on the done list, the
4850	 * data or status phase TD will be enqueued.
4851	 */
4852	(void) ohci_insert_hc_td(ohcip, ctrl, 0, SETUP_SIZE,
4853	    OHCI_CTRL_SETUP_PHASE, pp, tw);
4854
4855	USB_DPRINTF_L3(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
4856	    "Create_setup: pp 0x%p", (void *)pp);
4857
4858	/*
4859	 * If this control transfer has a data phase, record the
4860	 * direction. If the data phase is an OUT transaction,
4861	 * copy the data into the buffer of the transfer wrapper.
4862	 */
4863	if (wLength != 0) {
4864		/* There is a data stage.  Find the direction */
4865		if (bmRequestType & USB_DEV_REQ_DEV_TO_HOST) {
4866			tw->tw_direction = HC_TD_IN;
4867		} else {
4868			tw->tw_direction = HC_TD_OUT;
4869
4870			/* Copy the data into the message */
4871			ddi_rep_put8(tw->tw_accesshandle, data->b_rptr,
4872			    (uint8_t *)(tw->tw_buf + OHCI_MAX_TD_BUF_SIZE),
4873			    wLength, DDI_DEV_AUTOINCR);
4874
4875		}
4876
4877		ctrl = (ctrl_reqp->ctrl_attributes & USB_ATTRS_SHORT_XFER_OK) ?
4878		    HC_TD_R : 0;
4879
4880		/*
4881		 * There is a data stage.
4882		 * Find the direction.
4883		 */
4884		if (tw->tw_direction == HC_TD_IN) {
4885			ctrl = ctrl|HC_TD_IN|HC_TD_MS_DT|HC_TD_DT_1|HC_TD_6I;
4886		} else {
4887			ctrl = ctrl|HC_TD_OUT|HC_TD_MS_DT|HC_TD_DT_1|HC_TD_6I;
4888		}
4889
4890		/*
4891		 * Create the TD.  If this is an OUT transaction,
4892		 * the data is already in the buffer of the TW.
4893		 */
4894		(void) ohci_insert_hc_td(ohcip, ctrl, OHCI_MAX_TD_BUF_SIZE,
4895		    wLength, OHCI_CTRL_DATA_PHASE, pp, tw);
4896
4897		/*
4898		 * The direction of the STATUS TD depends on
4899		 * the direction of the transfer.
4900		 */
4901		if (tw->tw_direction == HC_TD_IN) {
4902			ctrl = HC_TD_OUT|HC_TD_MS_DT|HC_TD_DT_1|HC_TD_1I;
4903		} else {
4904			ctrl = HC_TD_IN|HC_TD_MS_DT|HC_TD_DT_1|HC_TD_1I;
4905		}
4906	} else {
4907		ctrl = HC_TD_IN|HC_TD_MS_DT|HC_TD_DT_1|HC_TD_1I;
4908	}
4909
4910	/* Status stage */
4911	(void) ohci_insert_hc_td(ohcip, ctrl, 0,
4912	    0, OHCI_CTRL_STATUS_PHASE, pp, tw);
4913
4914	/* Indicate that the control list is filled */
4915	Set_OpReg(hcr_cmd_status, HCR_STATUS_CLF);
4916
4917	/* Start the timer for this control transfer */
4918	ohci_start_xfer_timer(ohcip, pp, tw);
4919}
4920
4921/*
4922 * ohci_allocate_bulk_resources:
4923 *
4924 * Calculates the number of tds necessary for a ctrl transfer, and allocates
4925 * all the resources necessary.
4926 *
4927 * Returns NULL if there is insufficient resources otherwise TW.
4928 */
4929static ohci_trans_wrapper_t *
4930ohci_allocate_bulk_resources(
4931	ohci_state_t		*ohcip,
4932	ohci_pipe_private_t	*pp,
4933	usb_bulk_req_t		*bulk_reqp,
4934	usb_flags_t		usb_flags)
4935{
4936	size_t			td_count = 0;
4937	ohci_trans_wrapper_t	*tw;
4938
4939	/* Check the size of bulk request */
4940	if (bulk_reqp->bulk_len > OHCI_MAX_BULK_XFER_SIZE) {
4941
4942		USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4943		    "ohci_allocate_bulk_resources: Bulk request size 0x%x is "
4944		    "more than 0x%x", bulk_reqp->bulk_len,
4945		    OHCI_MAX_BULK_XFER_SIZE);
4946
4947		return (NULL);
4948	}
4949
4950	/* Get the required bulk packet size */
4951	td_count = bulk_reqp->bulk_len / OHCI_MAX_TD_XFER_SIZE;
4952	if (bulk_reqp->bulk_len % OHCI_MAX_TD_XFER_SIZE ||
4953	    bulk_reqp->bulk_len == 0) {
4954		td_count++;
4955	}
4956
4957	tw = ohci_allocate_tw_resources(ohcip, pp, bulk_reqp->bulk_len,
4958	    usb_flags, td_count);
4959
4960	return (tw);
4961}
4962
4963/*
4964 * ohci_insert_bulk_req:
4965 *
4966 * Create a Transfer Descriptor (TD) and a data buffer for a bulk
4967 * endpoint.
4968 */
4969/* ARGSUSED */
4970static void
4971ohci_insert_bulk_req(
4972	ohci_state_t		*ohcip,
4973	usba_pipe_handle_data_t	*ph,
4974	usb_bulk_req_t		*bulk_reqp,
4975	ohci_trans_wrapper_t	*tw,
4976	usb_flags_t		flags)
4977{
4978	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
4979	uint_t			bulk_pkt_size, count;
4980	size_t			residue = 0, len = 0;
4981	uint32_t		ctrl = 0;
4982	int			pipe_dir;
4983
4984	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
4985	    "ohci_insert_bulk_req: bulk_reqp = 0x%p flags = 0x%x",
4986	    (void *)bulk_reqp, flags);
4987
4988	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
4989
4990	/* Get the bulk pipe direction */
4991	pipe_dir = ph->p_ep.bEndpointAddress & USB_EP_DIR_MASK;
4992
4993	/* Get the required bulk packet size */
4994	bulk_pkt_size = min(bulk_reqp->bulk_len, OHCI_MAX_TD_XFER_SIZE);
4995
4996	if (bulk_pkt_size)
4997		residue = tw->tw_length % bulk_pkt_size;
4998
4999	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5000	    "ohci_insert_bulk_req: bulk_pkt_size = %d", bulk_pkt_size);
5001
5002	/*
5003	 * Save current bulk request pointer and timeout values
5004	 * in transfer wrapper.
5005	 */
5006	tw->tw_curr_xfer_reqp = (usb_opaque_t)bulk_reqp;
5007	tw->tw_timeout = bulk_reqp->bulk_timeout;
5008
5009	/*
5010	 * Initialize the callback and any callback
5011	 * data required when the td completes.
5012	 */
5013	tw->tw_handle_td = ohci_handle_bulk_td;
5014	tw->tw_handle_callback_value = NULL;
5015
5016	tw->tw_direction =
5017	    (pipe_dir == USB_EP_DIR_OUT) ? HC_TD_OUT : HC_TD_IN;
5018
5019	if (tw->tw_direction == HC_TD_OUT && bulk_reqp->bulk_len) {
5020
5021		ASSERT(bulk_reqp->bulk_data != NULL);
5022
5023		/* Copy the data into the message */
5024		ddi_rep_put8(tw->tw_accesshandle,
5025		    bulk_reqp->bulk_data->b_rptr, (uint8_t *)tw->tw_buf,
5026		    bulk_reqp->bulk_len, DDI_DEV_AUTOINCR);
5027	}
5028
5029	ctrl = tw->tw_direction|HC_TD_DT_0|HC_TD_6I;
5030
5031	/* Insert all the bulk TDs */
5032	for (count = 0; count < tw->tw_num_tds; count++) {
5033
5034		/* Check for last td */
5035		if (count == (tw->tw_num_tds - 1)) {
5036
5037			ctrl = ((ctrl & ~HC_TD_DI) | HC_TD_1I);
5038
5039			/* Check for inserting residue data */
5040			if (residue) {
5041				bulk_pkt_size = (uint_t)residue;
5042			}
5043
5044			/*
5045			 * Only set the round bit on the last TD, to ensure
5046			 * the controller will always HALT the ED in case of
5047			 * a short transfer.
5048			 */
5049			if (bulk_reqp->bulk_attributes &
5050			    USB_ATTRS_SHORT_XFER_OK) {
5051				ctrl |= HC_TD_R;
5052			}
5053		}
5054
5055		/* Insert the TD onto the endpoint */
5056		(void) ohci_insert_hc_td(ohcip, ctrl, len,
5057		    bulk_pkt_size, 0, pp, tw);
5058
5059		len = len + bulk_pkt_size;
5060	}
5061
5062	/* Indicate that the bulk list is filled */
5063	Set_OpReg(hcr_cmd_status, HCR_STATUS_BLF);
5064
5065	/* Start the timer for this bulk transfer */
5066	ohci_start_xfer_timer(ohcip, pp, tw);
5067}
5068
5069
5070/*
5071 * ohci_start_periodic_pipe_polling:
5072 * NOTE: This function is also called from POLLED MODE.
5073 */
5074int
5075ohci_start_periodic_pipe_polling(
5076	ohci_state_t		*ohcip,
5077	usba_pipe_handle_data_t	*ph,
5078	usb_opaque_t		periodic_in_reqp,
5079	usb_flags_t		flags)
5080{
5081	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
5082	usb_ep_descr_t		*eptd = &ph->p_ep;
5083	int			error = USB_SUCCESS;
5084
5085	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5086	    "ohci_start_periodic_pipe_polling: ep%d",
5087	    ph->p_ep.bEndpointAddress & USB_EP_NUM_MASK);
5088
5089	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
5090
5091	/*
5092	 * Check and handle start polling on root hub interrupt pipe.
5093	 */
5094	if ((ph->p_usba_device->usb_addr == ROOT_HUB_ADDR) &&
5095	    ((eptd->bmAttributes & USB_EP_ATTR_MASK) ==
5096	    USB_EP_ATTR_INTR)) {
5097
5098		error = ohci_handle_root_hub_pipe_start_intr_polling(ph,
5099		    (usb_intr_req_t *)periodic_in_reqp, flags);
5100
5101		return (error);
5102	}
5103
5104	switch (pp->pp_state) {
5105	case OHCI_PIPE_STATE_IDLE:
5106		/* Save the Original client's Periodic IN request */
5107		pp->pp_client_periodic_in_reqp = periodic_in_reqp;
5108
5109		/*
5110		 * This pipe is uninitialized or if a valid TD is
5111		 * not found then insert a TD on the interrupt or
5112		 * isochronous IN endpoint.
5113		 */
5114		error = ohci_start_pipe_polling(ohcip, ph, flags);
5115
5116		if (error != USB_SUCCESS) {
5117			USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5118			    "ohci_start_periodic_pipe_polling: "
5119			    "Start polling failed");
5120
5121			pp->pp_client_periodic_in_reqp = NULL;
5122
5123			return (error);
5124		}
5125
5126		USB_DPRINTF_L3(PRINT_MASK_INTR, ohcip->ohci_log_hdl,
5127		    "ohci_start_periodic_pipe_polling: PP = 0x%p", (void *)pp);
5128
5129		ASSERT((pp->pp_tw_head != NULL) && (pp->pp_tw_tail != NULL));
5130
5131		break;
5132	case OHCI_PIPE_STATE_ACTIVE:
5133		USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5134		    "ohci_start_periodic_pipe_polling: "
5135		    "Polling is already in progress");
5136
5137		error = USB_FAILURE;
5138		break;
5139	case OHCI_PIPE_STATE_ERROR:
5140		USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5141		    "ohci_start_periodic_pipe_polling: "
5142		    "Pipe is halted and perform reset before restart polling");
5143
5144		error = USB_FAILURE;
5145		break;
5146	default:
5147		USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5148		    "ohci_start_periodic_pipe_polling: Undefined state");
5149
5150		error = USB_FAILURE;
5151		break;
5152	}
5153
5154	return (error);
5155}
5156
5157
5158/*
5159 * ohci_start_pipe_polling:
5160 *
5161 * Insert the number of periodic requests corresponding to polling
5162 * interval as calculated during pipe open.
5163 */
5164static int
5165ohci_start_pipe_polling(
5166	ohci_state_t		*ohcip,
5167	usba_pipe_handle_data_t	*ph,
5168	usb_flags_t		flags)
5169{
5170	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
5171	usb_ep_descr_t		*eptd = &ph->p_ep;
5172	ohci_trans_wrapper_t	*tw_list, *tw;
5173	int			i, total_tws;
5174	int			error = USB_SUCCESS;
5175
5176	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5177	    "ohci_start_pipe_polling:");
5178
5179	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
5180
5181	/*
5182	 * For the start polling, pp_max_periodic_req_cnt will be zero
5183	 * and for the restart polling request, it will be non zero.
5184	 *
5185	 * In case of start polling request, find out number of requests
5186	 * required for the Interrupt IN endpoints corresponding to the
5187	 * endpoint polling interval. For Isochronous IN endpoints, it is
5188	 * always fixed since its polling interval will be one ms.
5189	 */
5190	if (pp->pp_max_periodic_req_cnt == 0) {
5191
5192		ohci_set_periodic_pipe_polling(ohcip, ph);
5193	}
5194
5195	ASSERT(pp->pp_max_periodic_req_cnt != 0);
5196
5197	/* Allocate all the necessary resources for the IN transfer */
5198	tw_list = NULL;
5199	total_tws = pp->pp_max_periodic_req_cnt - pp->pp_cur_periodic_req_cnt;
5200	for (i = 0; i < total_tws; i++) {
5201		switch (eptd->bmAttributes & USB_EP_ATTR_MASK) {
5202		case USB_EP_ATTR_INTR:
5203			tw = ohci_allocate_intr_resources(
5204			    ohcip, ph, NULL, flags);
5205			break;
5206		case USB_EP_ATTR_ISOCH:
5207			tw = ohci_allocate_isoc_resources(
5208			    ohcip, ph, NULL, flags);
5209			break;
5210		}
5211		if (tw == NULL) {
5212			error = USB_NO_RESOURCES;
5213			/* There are not enough resources, deallocate the TWs */
5214			tw = tw_list;
5215			while (tw != NULL) {
5216				tw_list = tw->tw_next;
5217				ohci_deallocate_periodic_in_resource(
5218				    ohcip, pp, tw);
5219				ohci_deallocate_tw_resources(ohcip, pp, tw);
5220				tw = tw_list;
5221			}
5222			return (error);
5223		} else {
5224			if (tw_list == NULL) {
5225				tw_list = tw;
5226			}
5227		}
5228	}
5229
5230	i = 0;
5231	while (pp->pp_cur_periodic_req_cnt < pp->pp_max_periodic_req_cnt) {
5232
5233		USB_DPRINTF_L3(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5234		    "ohci_start_pipe_polling: max = %d curr = %d tw = %p:",
5235		    pp->pp_max_periodic_req_cnt, pp->pp_cur_periodic_req_cnt,
5236		    (void *)tw_list);
5237
5238		tw = tw_list;
5239		tw_list = tw->tw_next;
5240
5241		switch (eptd->bmAttributes & USB_EP_ATTR_MASK) {
5242		case USB_EP_ATTR_INTR:
5243			ohci_insert_intr_req(ohcip, pp, tw, flags);
5244			break;
5245		case USB_EP_ATTR_ISOCH:
5246			error = ohci_insert_isoc_req(ohcip, pp, tw, flags);
5247			break;
5248		}
5249		if (error == USB_SUCCESS) {
5250			pp->pp_cur_periodic_req_cnt++;
5251		} else {
5252			/*
5253			 * Deallocate the remaining tw
5254			 * The current tw should have already been deallocated
5255			 */
5256			tw = tw_list;
5257			while (tw != NULL) {
5258				tw_list = tw->tw_next;
5259				ohci_deallocate_periodic_in_resource(
5260				    ohcip, pp, tw);
5261				ohci_deallocate_tw_resources(ohcip, pp, tw);
5262				tw = tw_list;
5263			}
5264			/*
5265			 * If this is the first req return an error.
5266			 * Otherwise return success.
5267			 */
5268			if (i != 0) {
5269				error = USB_SUCCESS;
5270			}
5271
5272			break;
5273		}
5274		i++;
5275	}
5276
5277	return (error);
5278}
5279
5280
5281/*
5282 * ohci_set_periodic_pipe_polling:
5283 *
5284 * Calculate the number of periodic requests needed corresponding to the
5285 * interrupt/isochronous IN endpoints polling interval. Table below gives
5286 * the number of periodic requests needed for the interrupt/isochronous
5287 * IN endpoints according to endpoint polling interval.
5288 *
5289 * Polling interval		Number of periodic requests
5290 *
5291 * 1ms				4
5292 * 2ms				2
5293 * 4ms to 32ms			1
5294 */
5295static void
5296ohci_set_periodic_pipe_polling(
5297	ohci_state_t		*ohcip,
5298	usba_pipe_handle_data_t	*ph)
5299{
5300	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
5301	usb_ep_descr_t		*endpoint = &ph->p_ep;
5302	uchar_t			ep_attr = endpoint->bmAttributes;
5303	uint_t			interval;
5304
5305	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5306	    "ohci_set_periodic_pipe_polling:");
5307
5308	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
5309
5310	pp->pp_cur_periodic_req_cnt = 0;
5311
5312	/*
5313	 * Check usb flag whether USB_FLAGS_ONE_TIME_POLL flag is
5314	 * set and if so, set pp->pp_max_periodic_req_cnt to one.
5315	 */
5316	if (((ep_attr & USB_EP_ATTR_MASK) == USB_EP_ATTR_INTR) &&
5317	    (pp->pp_client_periodic_in_reqp)) {
5318		usb_intr_req_t *intr_reqp =
5319		    (usb_intr_req_t *)pp->pp_client_periodic_in_reqp;
5320
5321		if (intr_reqp->intr_attributes &
5322		    USB_ATTRS_ONE_XFER) {
5323
5324			pp->pp_max_periodic_req_cnt = INTR_XMS_REQS;
5325
5326			return;
5327		}
5328	}
5329
5330	mutex_enter(&ph->p_usba_device->usb_mutex);
5331
5332	/*
5333	 * The ohci_adjust_polling_interval function will not fail
5334	 * at this instance since bandwidth allocation is already
5335	 * done. Here we are getting only the periodic interval.
5336	 */
5337	interval = ohci_adjust_polling_interval(ohcip, endpoint,
5338	    ph->p_usba_device->usb_port_status);
5339
5340	mutex_exit(&ph->p_usba_device->usb_mutex);
5341
5342	switch (interval) {
5343	case INTR_1MS_POLL:
5344		pp->pp_max_periodic_req_cnt = INTR_1MS_REQS;
5345		break;
5346	case INTR_2MS_POLL:
5347		pp->pp_max_periodic_req_cnt = INTR_2MS_REQS;
5348		break;
5349	default:
5350		pp->pp_max_periodic_req_cnt = INTR_XMS_REQS;
5351		break;
5352	}
5353
5354	USB_DPRINTF_L3(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5355	    "ohci_set_periodic_pipe_polling: Max periodic requests = %d",
5356	    pp->pp_max_periodic_req_cnt);
5357}
5358
5359/*
5360 * ohci_allocate_intr_resources:
5361 *
5362 * Calculates the number of tds necessary for a intr transfer, and allocates
5363 * all the necessary resources.
5364 *
5365 * Returns NULL if there is insufficient resources otherwise TW.
5366 */
5367static ohci_trans_wrapper_t *
5368ohci_allocate_intr_resources(
5369	ohci_state_t		*ohcip,
5370	usba_pipe_handle_data_t	*ph,
5371	usb_intr_req_t		*intr_reqp,
5372	usb_flags_t		flags)
5373{
5374	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
5375	int			pipe_dir;
5376	size_t			td_count = 1;
5377	size_t			tw_length;
5378	ohci_trans_wrapper_t	*tw;
5379
5380	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5381	    "ohci_allocate_intr_resources:");
5382
5383	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
5384
5385	pipe_dir = ph->p_ep.bEndpointAddress & USB_EP_DIR_MASK;
5386
5387	/* Get the length of interrupt transfer & alloc data */
5388	if (intr_reqp) {
5389		tw_length = intr_reqp->intr_len;
5390	} else {
5391		ASSERT(pipe_dir == USB_EP_DIR_IN);
5392		tw_length = (pp->pp_client_periodic_in_reqp) ?
5393		    (((usb_intr_req_t *)pp->
5394		    pp_client_periodic_in_reqp)->intr_len) :
5395		    ph->p_ep.wMaxPacketSize;
5396	}
5397
5398	/* Check the size of interrupt request */
5399	if (tw_length > OHCI_MAX_TD_XFER_SIZE) {
5400
5401		USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5402		    "ohci_allocate_intr_resources: Intr request size 0x%lx is "
5403		    "more than 0x%x", tw_length, OHCI_MAX_TD_XFER_SIZE);
5404
5405		return (NULL);
5406	}
5407
5408	if ((tw = ohci_allocate_tw_resources(ohcip, pp, tw_length,
5409	    flags, td_count)) == NULL) {
5410
5411		return (NULL);
5412	}
5413
5414	if (pipe_dir == USB_EP_DIR_IN) {
5415		if (ohci_allocate_periodic_in_resource(ohcip, pp, tw, flags) !=
5416		    USB_SUCCESS) {
5417
5418			ohci_deallocate_tw_resources(ohcip, pp, tw);
5419			return (NULL);
5420		}
5421		tw->tw_direction = HC_TD_IN;
5422	} else {
5423		if (tw_length) {
5424			ASSERT(intr_reqp->intr_data != NULL);
5425
5426			/* Copy the data into the message */
5427			ddi_rep_put8(tw->tw_accesshandle,
5428			    intr_reqp->intr_data->b_rptr, (uint8_t *)tw->tw_buf,
5429			    intr_reqp->intr_len, DDI_DEV_AUTOINCR);
5430		}
5431
5432		tw->tw_curr_xfer_reqp = (usb_opaque_t)intr_reqp;
5433		tw->tw_direction = HC_TD_OUT;
5434	}
5435
5436	if (intr_reqp) {
5437		tw->tw_timeout = intr_reqp->intr_timeout;
5438	}
5439
5440	/*
5441	 * Initialize the callback and any callback
5442	 * data required when the td completes.
5443	 */
5444	tw->tw_handle_td = ohci_handle_intr_td;
5445	tw->tw_handle_callback_value = NULL;
5446
5447	return (tw);
5448}
5449
5450/*
5451 * ohci_insert_intr_req:
5452 *
5453 * Insert an Interrupt request into the Host Controller's periodic list.
5454 */
5455/* ARGSUSED */
5456static void
5457ohci_insert_intr_req(
5458	ohci_state_t		*ohcip,
5459	ohci_pipe_private_t	*pp,
5460	ohci_trans_wrapper_t	*tw,
5461	usb_flags_t		flags)
5462{
5463	usb_intr_req_t		*curr_intr_reqp = NULL;
5464	uint_t			ctrl = 0;
5465
5466	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
5467
5468	ASSERT(tw->tw_curr_xfer_reqp != NULL);
5469
5470	/* Get the current interrupt request pointer */
5471	curr_intr_reqp = (usb_intr_req_t *)tw->tw_curr_xfer_reqp;
5472
5473	ctrl = tw->tw_direction | HC_TD_DT_0 | HC_TD_1I;
5474
5475	if (curr_intr_reqp->intr_attributes & USB_ATTRS_SHORT_XFER_OK) {
5476		ctrl |= HC_TD_R;
5477	}
5478
5479	/* Insert another interrupt TD */
5480	(void) ohci_insert_hc_td(ohcip, ctrl, 0, tw->tw_length, 0, pp, tw);
5481
5482	/* Start the timer for this Interrupt transfer */
5483	ohci_start_xfer_timer(ohcip, pp, tw);
5484}
5485
5486
5487/*
5488 * ohci_stop_periodic_pipe_polling:
5489 */
5490/* ARGSUSED */
5491static int
5492ohci_stop_periodic_pipe_polling(
5493	ohci_state_t		*ohcip,
5494	usba_pipe_handle_data_t	*ph,
5495	usb_flags_t		flags)
5496{
5497	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
5498	usb_ep_descr_t		*eptd = &ph->p_ep;
5499
5500	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5501	    "ohci_stop_periodic_pipe_polling: Flags = 0x%x", flags);
5502
5503	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
5504
5505	/*
5506	 * Check and handle stop polling on root hub interrupt pipe.
5507	 */
5508	if ((ph->p_usba_device->usb_addr == ROOT_HUB_ADDR) &&
5509	    ((eptd->bmAttributes & USB_EP_ATTR_MASK) ==
5510	    USB_EP_ATTR_INTR)) {
5511
5512		ohci_handle_root_hub_pipe_stop_intr_polling(
5513		    ph, flags);
5514		return (USB_SUCCESS);
5515	}
5516
5517	if (pp->pp_state != OHCI_PIPE_STATE_ACTIVE) {
5518
5519		USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5520		    "ohci_stop_periodic_pipe_polling: Polling already stopped");
5521
5522		return (USB_SUCCESS);
5523	}
5524
5525	/* Set pipe state to pipe stop polling */
5526	pp->pp_state = OHCI_PIPE_STATE_STOP_POLLING;
5527
5528	ohci_pipe_cleanup(ohcip, ph);
5529
5530	return (USB_SUCCESS);
5531}
5532
5533/*
5534 * ohci_allocate_isoc_resources:
5535 *
5536 * Calculates the number of tds necessary for a intr transfer, and allocates
5537 * all the necessary resources.
5538 *
5539 * Returns NULL if there is insufficient resources otherwise TW.
5540 */
5541static ohci_trans_wrapper_t *
5542ohci_allocate_isoc_resources(
5543	ohci_state_t		*ohcip,
5544	usba_pipe_handle_data_t	*ph,
5545	usb_isoc_req_t		*isoc_reqp,
5546	usb_flags_t		flags)
5547{
5548	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
5549	int			pipe_dir;
5550	uint_t			max_pkt_size = ph->p_ep.wMaxPacketSize;
5551	uint_t			max_isoc_xfer_size;
5552	usb_isoc_pkt_descr_t	*isoc_pkt_descr, *start_isoc_pkt_descr;
5553	ushort_t		isoc_pkt_count;
5554	size_t			count, td_count;
5555	size_t			tw_length;
5556	size_t			isoc_pkts_length;
5557	ohci_trans_wrapper_t	*tw;
5558
5559
5560	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5561	    "ohci_allocate_isoc_resources: flags = ox%x", flags);
5562
5563	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
5564
5565	/*
5566	 *  Check whether pipe is in halted state.
5567	 */
5568	if (pp->pp_state == OHCI_PIPE_STATE_ERROR) {
5569		USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5570		    "ohci_allocate_isoc_resources:"
5571		    "Pipe is in error state, need pipe reset to continue");
5572
5573		return (NULL);
5574	}
5575
5576	pipe_dir = ph->p_ep.bEndpointAddress & USB_EP_DIR_MASK;
5577
5578	/* Calculate the maximum isochronous transfer size */
5579	max_isoc_xfer_size = OHCI_MAX_ISOC_PKTS_PER_XFER * max_pkt_size;
5580
5581	if (isoc_reqp) {
5582		isoc_pkt_descr = isoc_reqp->isoc_pkt_descr;
5583		isoc_pkt_count = isoc_reqp->isoc_pkts_count;
5584		isoc_pkts_length = isoc_reqp->isoc_pkts_length;
5585	} else {
5586		isoc_pkt_descr = ((usb_isoc_req_t *)
5587		    pp->pp_client_periodic_in_reqp)->isoc_pkt_descr;
5588
5589		isoc_pkt_count = ((usb_isoc_req_t *)
5590		    pp->pp_client_periodic_in_reqp)->isoc_pkts_count;
5591
5592		isoc_pkts_length = ((usb_isoc_req_t *)
5593		    pp->pp_client_periodic_in_reqp)->isoc_pkts_length;
5594	}
5595
5596	start_isoc_pkt_descr = isoc_pkt_descr;
5597
5598	/*
5599	 * For isochronous IN pipe, get value of number of isochronous
5600	 * packets per usb isochronous request
5601	 */
5602	if (pipe_dir == USB_EP_DIR_IN) {
5603		for (count = 0, tw_length = 0;
5604		    count < isoc_pkt_count; count++) {
5605			tw_length += isoc_pkt_descr->isoc_pkt_length;
5606			isoc_pkt_descr++;
5607		}
5608
5609		if ((isoc_pkts_length) && (isoc_pkts_length != tw_length)) {
5610
5611			USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5612			    "ohci_allocate_isoc_resources: "
5613			    "isoc_pkts_length 0x%lx is not equal to the sum of "
5614			    "all pkt lengths 0x%lx in an isoc request",
5615			    isoc_pkts_length, tw_length);
5616
5617			return (NULL);
5618		}
5619
5620	} else {
5621		ASSERT(isoc_reqp != NULL);
5622		tw_length = MBLKL(isoc_reqp->isoc_data);
5623	}
5624
5625	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5626	    "ohci_allocate_isoc_resources: length = 0x%lx", tw_length);
5627
5628	/* Check the size of isochronous request */
5629	if (tw_length > max_isoc_xfer_size) {
5630
5631		USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5632		    "ohci_allocate_isoc_resources: Maximum isoc request"
5633		    "size 0x%x Given isoc request size 0x%lx",
5634		    max_isoc_xfer_size, tw_length);
5635
5636		return (NULL);
5637	}
5638
5639	/*
5640	 * Each isochronous TD can hold data upto eight isochronous
5641	 * data packets. Calculate the number of isochronous TDs needs
5642	 * to be insert to complete current isochronous request.
5643	 */
5644	td_count = isoc_pkt_count / OHCI_ISOC_PKTS_PER_TD;
5645
5646	if (isoc_pkt_count % OHCI_ISOC_PKTS_PER_TD) {
5647		td_count++;
5648	}
5649
5650	tw = ohci_create_isoc_transfer_wrapper(ohcip, pp, tw_length,
5651	    start_isoc_pkt_descr, isoc_pkt_count, td_count, flags);
5652
5653	if (tw == NULL) {
5654		USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5655		    "ohci_create_isoc_transfer_wrapper: "
5656		    "Unable to allocate TW");
5657
5658		return (NULL);
5659	}
5660
5661	if (ohci_allocate_tds_for_tw(ohcip, tw, td_count) ==
5662	    USB_SUCCESS) {
5663		tw->tw_num_tds = (uint_t)td_count;
5664	} else {
5665		ohci_deallocate_tw_resources(ohcip, pp, tw);
5666
5667		return (NULL);
5668	}
5669
5670	if (pipe_dir == USB_EP_DIR_IN) {
5671		if (ohci_allocate_periodic_in_resource(ohcip, pp, tw, flags) !=
5672		    USB_SUCCESS) {
5673
5674			ohci_deallocate_tw_resources(ohcip, pp, tw);
5675			return (NULL);
5676		}
5677		tw->tw_direction = HC_TD_IN;
5678	} else {
5679		if (tw->tw_length) {
5680			uchar_t *p;
5681			int i;
5682
5683			ASSERT(isoc_reqp->isoc_data != NULL);
5684			p = isoc_reqp->isoc_data->b_rptr;
5685
5686			/* Copy the data into the message */
5687			for (i = 0; i < td_count; i++) {
5688				ddi_rep_put8(
5689				    tw->tw_isoc_bufs[i].mem_handle, p,
5690				    (uint8_t *)tw->tw_isoc_bufs[i].buf_addr,
5691				    tw->tw_isoc_bufs[i].length,
5692				    DDI_DEV_AUTOINCR);
5693				p += tw->tw_isoc_bufs[i].length;
5694			}
5695		}
5696		tw->tw_curr_xfer_reqp = (usb_opaque_t)isoc_reqp;
5697		tw->tw_direction = HC_TD_OUT;
5698	}
5699
5700	/*
5701	 * Initialize the callback and any callback
5702	 * data required when the td completes.
5703	 */
5704	tw->tw_handle_td = ohci_handle_isoc_td;
5705	tw->tw_handle_callback_value = NULL;
5706
5707	return (tw);
5708}
5709
5710/*
5711 * ohci_insert_isoc_req:
5712 *
5713 * Insert an isochronous request into the Host Controller's
5714 * isochronous list.  If there is an error is will appropriately
5715 * deallocate the unused resources.
5716 */
5717static int
5718ohci_insert_isoc_req(
5719	ohci_state_t		*ohcip,
5720	ohci_pipe_private_t	*pp,
5721	ohci_trans_wrapper_t	*tw,
5722	uint_t			flags)
5723{
5724	size_t			curr_isoc_xfer_offset, curr_isoc_xfer_len;
5725	uint_t			isoc_pkts, residue, count;
5726	uint_t			i, ctrl, frame_count;
5727	uint_t			error = USB_SUCCESS;
5728	usb_isoc_req_t		*curr_isoc_reqp;
5729	usb_isoc_pkt_descr_t	*curr_isoc_pkt_descr;
5730
5731	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5732	    "ohci_insert_isoc_req: flags = 0x%x", flags);
5733
5734	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
5735
5736	/*
5737	 * Get the current isochronous request and packet
5738	 * descriptor pointers.
5739	 */
5740	curr_isoc_reqp = (usb_isoc_req_t *)tw->tw_curr_xfer_reqp;
5741	curr_isoc_pkt_descr = curr_isoc_reqp->isoc_pkt_descr;
5742
5743	ASSERT(curr_isoc_reqp != NULL);
5744	ASSERT(curr_isoc_reqp->isoc_pkt_descr != NULL);
5745
5746	/*
5747	 * Save address of first usb isochronous packet descriptor.
5748	 */
5749	tw->tw_curr_isoc_pktp = curr_isoc_reqp->isoc_pkt_descr;
5750
5751	/* Insert all the isochronous TDs */
5752	for (count = 0, curr_isoc_xfer_offset = 0,
5753	    isoc_pkts = 0; count < tw->tw_num_tds; count++) {
5754
5755		residue = curr_isoc_reqp->isoc_pkts_count - isoc_pkts;
5756
5757		/* Check for inserting residue data */
5758		if ((count == (tw->tw_num_tds - 1)) &&
5759		    (residue < OHCI_ISOC_PKTS_PER_TD)) {
5760			frame_count = residue;
5761		} else {
5762			frame_count = OHCI_ISOC_PKTS_PER_TD;
5763		}
5764
5765		curr_isoc_pkt_descr = tw->tw_curr_isoc_pktp;
5766
5767		/*
5768		 * Calculate length of isochronous transfer
5769		 * for the current TD.
5770		 */
5771		for (i = 0, curr_isoc_xfer_len = 0;
5772		    i < frame_count; i++, curr_isoc_pkt_descr++) {
5773			curr_isoc_xfer_len +=
5774			    curr_isoc_pkt_descr->isoc_pkt_length;
5775		}
5776
5777		/*
5778		 * Programm td control field by checking whether this
5779		 * is last td.
5780		 */
5781		if (count == (tw->tw_num_tds - 1)) {
5782			ctrl = ((((frame_count - 1) << HC_ITD_FC_SHIFT) &
5783			    HC_ITD_FC) | HC_TD_DT_0 | HC_TD_0I);
5784		} else {
5785			ctrl = ((((frame_count - 1) << HC_ITD_FC_SHIFT) &
5786			    HC_ITD_FC) | HC_TD_DT_0 | HC_TD_6I);
5787		}
5788
5789		/* Insert the TD into the endpoint */
5790		if ((error = ohci_insert_hc_td(ohcip, ctrl, count,
5791		    curr_isoc_xfer_len, 0, pp, tw)) !=
5792		    USB_SUCCESS) {
5793			tw->tw_num_tds = count;
5794			tw->tw_length  = curr_isoc_xfer_offset;
5795			break;
5796		}
5797
5798		isoc_pkts += frame_count;
5799		tw->tw_curr_isoc_pktp += frame_count;
5800		curr_isoc_xfer_offset += curr_isoc_xfer_len;
5801	}
5802
5803	if (error != USB_SUCCESS) {
5804		/* Free periodic in resources */
5805		if (tw->tw_direction == USB_EP_DIR_IN) {
5806			ohci_deallocate_periodic_in_resource(ohcip, pp, tw);
5807		}
5808
5809		/* Free all resources if IN or if count == 0(for both IN/OUT) */
5810		if (tw->tw_direction == USB_EP_DIR_IN || count == 0) {
5811
5812			ohci_deallocate_tw_resources(ohcip, pp, tw);
5813
5814			if (pp->pp_cur_periodic_req_cnt) {
5815				/*
5816				 * Set pipe state to stop polling and
5817				 * error to no resource. Don't insert
5818				 * any more isochronous polling requests.
5819				 */
5820				pp->pp_state = OHCI_PIPE_STATE_STOP_POLLING;
5821				pp->pp_error = error;
5822			} else {
5823				/* Set periodic in pipe state to idle */
5824				pp->pp_state = OHCI_PIPE_STATE_IDLE;
5825			}
5826		}
5827	} else {
5828
5829		/*
5830		 * Reset back to the address of first usb isochronous
5831		 * packet descriptor.
5832		 */
5833		tw->tw_curr_isoc_pktp = curr_isoc_reqp->isoc_pkt_descr;
5834
5835		/* Reset the CONTINUE flag */
5836		pp->pp_flag &= ~OHCI_ISOC_XFER_CONTINUE;
5837	}
5838
5839	return (error);
5840}
5841
5842
5843/*
5844 * ohci_insert_hc_td:
5845 *
5846 * Insert a Transfer Descriptor (TD) on an Endpoint Descriptor (ED).
5847 * Always returns USB_SUCCESS, except for ISOCH.
5848 */
5849static int
5850ohci_insert_hc_td(
5851	ohci_state_t		*ohcip,
5852	uint_t			hctd_ctrl,
5853	uint32_t		hctd_dma_offs,
5854	size_t			hctd_length,
5855	uint32_t		hctd_ctrl_phase,
5856	ohci_pipe_private_t	*pp,
5857	ohci_trans_wrapper_t	*tw)
5858{
5859	ohci_td_t		*new_dummy;
5860	ohci_td_t		*cpu_current_dummy;
5861	ohci_ed_t		*ept = pp->pp_ept;
5862	int			error;
5863
5864	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
5865
5866	/* Retrieve preallocated td from the TW */
5867	new_dummy = tw->tw_hctd_free_list;
5868
5869	ASSERT(new_dummy != NULL);
5870
5871	tw->tw_hctd_free_list = ohci_td_iommu_to_cpu(ohcip,
5872	    Get_TD(new_dummy->hctd_tw_next_td));
5873	Set_TD(new_dummy->hctd_tw_next_td, NULL);
5874
5875	/* Fill in the current dummy */
5876	cpu_current_dummy = (ohci_td_t *)
5877	    (ohci_td_iommu_to_cpu(ohcip, Get_ED(ept->hced_tailp)));
5878
5879	/*
5880	 * Fill in the current dummy td and
5881	 * add the new dummy to the end.
5882	 */
5883	ohci_fill_in_td(ohcip, cpu_current_dummy, new_dummy,
5884	    hctd_ctrl, hctd_dma_offs, hctd_length, hctd_ctrl_phase, pp, tw);
5885
5886	/*
5887	 * If this is an isochronous TD, first write proper
5888	 * starting usb frame number in which this TD must
5889	 * can be processed. After writing the frame number
5890	 * insert this TD into the ED's list.
5891	 */
5892	if ((pp->pp_pipe_handle->p_ep.bmAttributes &
5893	    USB_EP_ATTR_MASK) == USB_EP_ATTR_ISOCH) {
5894
5895		error = ohci_insert_td_with_frame_number(
5896		    ohcip, pp, tw, cpu_current_dummy, new_dummy);
5897
5898		if (error != USB_SUCCESS) {
5899			/* Reset the current dummy back to a dummy */
5900			bzero((char *)cpu_current_dummy, sizeof (ohci_td_t));
5901			Set_TD(cpu_current_dummy->hctd_state, HC_TD_DUMMY);
5902
5903			/* return the new dummy back to the free list */
5904			bzero((char *)new_dummy, sizeof (ohci_td_t));
5905			Set_TD(new_dummy->hctd_state, HC_TD_DUMMY);
5906			if (tw->tw_hctd_free_list != NULL) {
5907				Set_TD(new_dummy->hctd_tw_next_td,
5908				    ohci_td_cpu_to_iommu(ohcip,
5909				    tw->tw_hctd_free_list));
5910			}
5911			tw->tw_hctd_free_list = new_dummy;
5912
5913			return (error);
5914		}
5915	} else {
5916		/*
5917		 * For control, bulk and interrupt TD, just
5918		 * add the new dummy to the ED's list. When
5919		 * this occurs, the Host Controller ill see
5920		 * the newly filled in dummy TD.
5921		 */
5922		Set_ED(ept->hced_tailp,
5923		    (ohci_td_cpu_to_iommu(ohcip, new_dummy)));
5924	}
5925
5926	/* Insert this td onto the tw */
5927	ohci_insert_td_on_tw(ohcip, tw, cpu_current_dummy);
5928
5929	return (USB_SUCCESS);
5930}
5931
5932
5933/*
5934 * ohci_allocate_td_from_pool:
5935 *
5936 * Allocate a Transfer Descriptor (TD) from the TD buffer pool.
5937 */
5938static ohci_td_t *
5939ohci_allocate_td_from_pool(ohci_state_t	*ohcip)
5940{
5941	int				i, state;
5942	ohci_td_t			*td;
5943
5944	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
5945
5946	/*
5947	 * Search for a blank Transfer Descriptor (TD)
5948	 * in the TD buffer pool.
5949	 */
5950	for (i = 0; i < ohci_td_pool_size; i ++) {
5951		state = Get_TD(ohcip->ohci_td_pool_addr[i].hctd_state);
5952		if (state == HC_TD_FREE) {
5953			break;
5954		}
5955	}
5956
5957	if (i >= ohci_td_pool_size) {
5958		USB_DPRINTF_L2(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
5959		    "ohci_allocate_td_from_pool: TD exhausted");
5960
5961		return (NULL);
5962	}
5963
5964	USB_DPRINTF_L4(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
5965	    "ohci_allocate_td_from_pool: Allocated %d", i);
5966
5967	/* Create a new dummy for the end of the TD list */
5968	td = &ohcip->ohci_td_pool_addr[i];
5969
5970	USB_DPRINTF_L3(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
5971	    "ohci_allocate_td_from_pool: td 0x%p", (void *)td);
5972
5973	/* Mark the newly allocated TD as a dummy */
5974	Set_TD(td->hctd_state, HC_TD_DUMMY);
5975
5976	return (td);
5977}
5978
5979/*
5980 * ohci_fill_in_td:
5981 *
5982 * Fill in the fields of a Transfer Descriptor (TD).
5983 *
5984 * hctd_dma_offs - different meanings for non-isoc and isoc TDs:
5985 *	    starting offset into the TW buffer for a non-isoc TD
5986 *	    and the index into the isoc TD list for an isoc TD.
5987 *	    For non-isoc TDs, the starting offset should be 4k
5988 *	    aligned and the TDs in one transfer must be filled in
5989 *	    increasing order.
5990 */
5991static void
5992ohci_fill_in_td(
5993	ohci_state_t		*ohcip,
5994	ohci_td_t		*td,
5995	ohci_td_t		*new_dummy,
5996	uint_t			hctd_ctrl,
5997	uint32_t		hctd_dma_offs,
5998	size_t			hctd_length,
5999	uint32_t		hctd_ctrl_phase,
6000	ohci_pipe_private_t	*pp,
6001	ohci_trans_wrapper_t	*tw)
6002{
6003	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6004	    "ohci_fill_in_td: td 0x%p bufoffs 0x%x len 0x%lx",
6005	    (void *)td, hctd_dma_offs, hctd_length);
6006
6007	/* Assert that the td to be filled in is a dummy */
6008	ASSERT(Get_TD(td->hctd_state) == HC_TD_DUMMY);
6009
6010	/* Change TD's state Active */
6011	Set_TD(td->hctd_state, HC_TD_ACTIVE);
6012
6013	/* Update the TD special fields */
6014	if ((pp->pp_pipe_handle->p_ep.bmAttributes &
6015	    USB_EP_ATTR_MASK) == USB_EP_ATTR_ISOCH) {
6016		ohci_init_itd(ohcip, tw, hctd_ctrl, hctd_dma_offs, td);
6017	} else {
6018		/* Update the dummy with control information */
6019		Set_TD(td->hctd_ctrl, (hctd_ctrl | HC_TD_CC_NA));
6020
6021		ohci_init_td(ohcip, tw, hctd_dma_offs, hctd_length, td);
6022	}
6023
6024	/* The current dummy now points to the new dummy */
6025	Set_TD(td->hctd_next_td, (ohci_td_cpu_to_iommu(ohcip, new_dummy)));
6026
6027	/*
6028	 * For Control transfer, hctd_ctrl_phase is a valid field.
6029	 */
6030	if (hctd_ctrl_phase) {
6031		Set_TD(td->hctd_ctrl_phase, hctd_ctrl_phase);
6032	}
6033
6034	/* Print the td */
6035	ohci_print_td(ohcip, td);
6036
6037	/* Fill in the wrapper portion of the TD */
6038
6039	/* Set the transfer wrapper */
6040	ASSERT(tw != NULL);
6041	ASSERT(tw->tw_id != 0);
6042
6043	Set_TD(td->hctd_trans_wrapper, tw->tw_id);
6044	Set_TD(td->hctd_tw_next_td, NULL);
6045}
6046
6047
6048/*
6049 * ohci_init_td:
6050 *
6051 * Initialize the buffer address portion of non-isoc Transfer
6052 * Descriptor (TD).
6053 */
6054void
6055ohci_init_td(
6056	ohci_state_t		*ohcip,
6057	ohci_trans_wrapper_t	*tw,
6058	uint32_t		hctd_dma_offs,
6059	size_t			hctd_length,
6060	ohci_td_t		*td)
6061{
6062	uint32_t	page_addr, start_addr = 0, end_addr = 0;
6063	size_t		buf_len = hctd_length;
6064	int		rem_len, i;
6065
6066	/*
6067	 * TDs must be filled in increasing DMA offset order.
6068	 * tw_dma_offs is initialized to be 0 at TW creation and
6069	 * is only increased in this function.
6070	 */
6071	ASSERT(buf_len == 0 || hctd_dma_offs >= tw->tw_dma_offs);
6072
6073	Set_TD(td->hctd_xfer_offs, hctd_dma_offs);
6074	Set_TD(td->hctd_xfer_len, buf_len);
6075
6076	/* Computing the starting buffer address and end buffer address */
6077	for (i = 0; (i < 2) && (buf_len > 0); i++) {
6078		/* Advance to the next DMA cookie if necessary */
6079		if ((tw->tw_dma_offs + tw->tw_cookie.dmac_size) <=
6080		    hctd_dma_offs) {
6081			/*
6082			 * tw_dma_offs always points to the starting offset
6083			 * of a cookie
6084			 */
6085			tw->tw_dma_offs += tw->tw_cookie.dmac_size;
6086			ddi_dma_nextcookie(tw->tw_dmahandle, &tw->tw_cookie);
6087			tw->tw_cookie_idx++;
6088			ASSERT(tw->tw_cookie_idx < tw->tw_ncookies);
6089		}
6090
6091		ASSERT((tw->tw_dma_offs + tw->tw_cookie.dmac_size) >
6092		    hctd_dma_offs);
6093
6094		/*
6095		 * Counting the remained buffer length to be filled in
6096		 * the TD for current DMA cookie
6097		 */
6098		rem_len = (tw->tw_dma_offs + tw->tw_cookie.dmac_size) -
6099		    hctd_dma_offs;
6100
6101		/* Get the beginning address of the buffer */
6102		page_addr = (hctd_dma_offs - tw->tw_dma_offs) +
6103		    tw->tw_cookie.dmac_address;
6104		ASSERT((page_addr % OHCI_4K_ALIGN) == 0);
6105
6106		if (i == 0) {
6107			start_addr = page_addr;
6108		}
6109
6110		USB_DPRINTF_L3(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6111		    "ohci_init_td: page_addr 0x%x dmac_size "
6112		    "0x%lx idx %d", page_addr, tw->tw_cookie.dmac_size,
6113		    tw->tw_cookie_idx);
6114
6115		if (buf_len <= OHCI_MAX_TD_BUF_SIZE) {
6116			ASSERT(buf_len <= rem_len);
6117			end_addr = page_addr + buf_len - 1;
6118			buf_len = 0;
6119			break;
6120		} else {
6121			ASSERT(rem_len >= OHCI_MAX_TD_BUF_SIZE);
6122			buf_len -= OHCI_MAX_TD_BUF_SIZE;
6123			hctd_dma_offs += OHCI_MAX_TD_BUF_SIZE;
6124		}
6125	}
6126
6127	ASSERT(buf_len == 0);
6128
6129	Set_TD(td->hctd_cbp, start_addr);
6130	Set_TD(td->hctd_buf_end, end_addr);
6131}
6132
6133
6134/*
6135 * ohci_init_itd:
6136 *
6137 * Initialize the buffer address portion of isoc Transfer Descriptor (TD).
6138 */
6139static void
6140ohci_init_itd(
6141	ohci_state_t		*ohcip,
6142	ohci_trans_wrapper_t	*tw,
6143	uint_t			hctd_ctrl,
6144	uint32_t		index,
6145	ohci_td_t		*td)
6146{
6147	uint32_t		start_addr, end_addr, offset, offset_addr;
6148	ohci_isoc_buf_t		*bufp;
6149	size_t			buf_len;
6150	uint_t			buf, fc, toggle, flag;
6151	usb_isoc_pkt_descr_t	*temp_pkt_descr;
6152	int			i;
6153
6154	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
6155
6156	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6157	    "ohci_init_itd: ctrl = 0x%x", hctd_ctrl);
6158
6159	/*
6160	 * Write control information except starting
6161	 * usb frame number.
6162	 */
6163	Set_TD(td->hctd_ctrl, (hctd_ctrl | HC_TD_CC_NA));
6164
6165	bufp = &tw->tw_isoc_bufs[index];
6166	Set_TD(td->hctd_xfer_offs, index);
6167	Set_TD(td->hctd_xfer_len, bufp->length);
6168
6169	start_addr = bufp->cookie.dmac_address;
6170	ASSERT((start_addr % OHCI_4K_ALIGN) == 0);
6171
6172	buf_len = bufp->length;
6173	if (bufp->ncookies == OHCI_DMA_ATTR_TD_SGLLEN) {
6174		buf_len = bufp->length - bufp->cookie.dmac_size;
6175		ddi_dma_nextcookie(bufp->dma_handle, &bufp->cookie);
6176	}
6177	end_addr = bufp->cookie.dmac_address + buf_len - 1;
6178
6179	/*
6180	 * For an isochronous transfer, the hctd_cbp contains,
6181	 * the 4k page, and not the actual start of the buffer.
6182	 */
6183	Set_TD(td->hctd_cbp, ((uint32_t)start_addr & HC_ITD_PAGE_MASK));
6184	Set_TD(td->hctd_buf_end, end_addr);
6185
6186	fc = (hctd_ctrl & HC_ITD_FC) >> HC_ITD_FC_SHIFT;
6187	toggle = 0;
6188	buf = start_addr;
6189
6190	/*
6191	 * Get the address of first isochronous data packet
6192	 * for the current isochronous TD.
6193	 */
6194	temp_pkt_descr =  tw->tw_curr_isoc_pktp;
6195
6196	/* The offsets are actually offsets into the page */
6197	for (i = 0; i <= fc; i++) {
6198		offset_addr = (uint32_t)((buf &
6199		    HC_ITD_OFFSET_ADDR) | (HC_ITD_OFFSET_CC));
6200
6201		flag =	((start_addr &
6202		    HC_ITD_PAGE_MASK) ^ (buf & HC_ITD_PAGE_MASK));
6203
6204		if (flag) {
6205			offset_addr |= HC_ITD_4KBOUNDARY_CROSS;
6206		}
6207
6208		if (toggle) {
6209			offset = (uint32_t)((offset_addr <<
6210			    HC_ITD_OFFSET_SHIFT) & HC_ITD_ODD_OFFSET);
6211
6212			Set_TD(td->hctd_offsets[i / 2],
6213			    Get_TD(td->hctd_offsets[i / 2]) | offset);
6214			toggle = 0;
6215		} else {
6216			offset = (uint32_t)(offset_addr & HC_ITD_EVEN_OFFSET);
6217
6218			Set_TD(td->hctd_offsets[i / 2],
6219			    Get_TD(td->hctd_offsets[i / 2]) | offset);
6220			toggle = 1;
6221		}
6222
6223		buf = (uint32_t)(buf + temp_pkt_descr->isoc_pkt_length);
6224		temp_pkt_descr++;
6225	}
6226}
6227
6228
6229/*
6230 * ohci_insert_td_with_frame_number:
6231 *
6232 * Insert current isochronous TD into the ED's list. with proper
6233 * usb frame number in which this TD can be processed.
6234 */
6235static int
6236ohci_insert_td_with_frame_number(
6237	ohci_state_t		*ohcip,
6238	ohci_pipe_private_t	*pp,
6239	ohci_trans_wrapper_t	*tw,
6240	ohci_td_t		*current_td,
6241	ohci_td_t		*dummy_td)
6242{
6243	usb_isoc_req_t		*isoc_reqp =
6244	    (usb_isoc_req_t *)tw->tw_curr_xfer_reqp;
6245	usb_frame_number_t	current_frame_number, start_frame_number;
6246	uint_t			ddic, ctrl, isoc_pkts;
6247	ohci_ed_t		*ept = pp->pp_ept;
6248
6249	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6250	    "ohci_insert_td_with_frame_number:"
6251	    "isoc flags 0x%x", isoc_reqp->isoc_attributes);
6252
6253	/* Get the TD ctrl information */
6254	isoc_pkts = ((Get_TD(current_td->hctd_ctrl) &
6255	    HC_ITD_FC) >> HC_ITD_FC_SHIFT) + 1;
6256
6257	/*
6258	 * Enter critical, while programming the usb frame number
6259	 * and inserting current isochronous TD into the ED's list.
6260	 */
6261	ddic = ddi_enter_critical();
6262
6263	/* Get the current frame number */
6264	current_frame_number = ohci_get_current_frame_number(ohcip);
6265
6266	/* Check the given isochronous flags */
6267	switch (isoc_reqp->isoc_attributes &
6268	    (USB_ATTRS_ISOC_START_FRAME | USB_ATTRS_ISOC_XFER_ASAP)) {
6269	case USB_ATTRS_ISOC_START_FRAME:
6270		/* Starting frame number is specified */
6271		if (pp->pp_flag & OHCI_ISOC_XFER_CONTINUE) {
6272			/* Get the starting usb frame number */
6273			start_frame_number = pp->pp_next_frame_number;
6274		} else {
6275			/* Check for the Starting usb frame number */
6276			if ((isoc_reqp->isoc_frame_no == 0) ||
6277			    ((isoc_reqp->isoc_frame_no +
6278			    isoc_reqp->isoc_pkts_count) <
6279			    current_frame_number)) {
6280
6281				/* Exit the critical */
6282				ddi_exit_critical(ddic);
6283
6284				USB_DPRINTF_L2(PRINT_MASK_LISTS,
6285				    ohcip->ohci_log_hdl,
6286				    "ohci_insert_td_with_frame_number:"
6287				    "Invalid starting frame number");
6288
6289				return (USB_INVALID_START_FRAME);
6290			}
6291
6292			/* Get the starting usb frame number */
6293			start_frame_number = isoc_reqp->isoc_frame_no;
6294
6295			pp->pp_next_frame_number = 0;
6296		}
6297		break;
6298	case USB_ATTRS_ISOC_XFER_ASAP:
6299		/* ohci has to specify starting frame number */
6300		if ((pp->pp_next_frame_number) &&
6301		    (pp->pp_next_frame_number > current_frame_number)) {
6302			/*
6303			 * Get the next usb frame number.
6304			 */
6305			start_frame_number = pp->pp_next_frame_number;
6306		} else {
6307			/*
6308			 * Add appropriate offset to the current usb
6309			 * frame number and use it as a starting frame
6310			 * number.
6311			 */
6312			start_frame_number =
6313			    current_frame_number + OHCI_FRAME_OFFSET;
6314		}
6315
6316		if (!(pp->pp_flag & OHCI_ISOC_XFER_CONTINUE)) {
6317			isoc_reqp->isoc_frame_no = start_frame_number;
6318		}
6319		break;
6320	default:
6321		/* Exit the critical */
6322		ddi_exit_critical(ddic);
6323
6324		USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6325		    "ohci_insert_td_with_frame_number: Either starting "
6326		    "frame number or ASAP flags are not set, attrs = 0x%x",
6327		    isoc_reqp->isoc_attributes);
6328
6329		return (USB_NO_FRAME_NUMBER);
6330	}
6331
6332	/* Get the TD ctrl information */
6333	ctrl = Get_TD(current_td->hctd_ctrl) & (~(HC_ITD_SF));
6334
6335	/* Set the frame number field */
6336	Set_TD(current_td->hctd_ctrl, ctrl | (start_frame_number & HC_ITD_SF));
6337
6338	/*
6339	 * Add the new dummy to the ED's list. When this occurs,
6340	 * the Host Controller will see newly filled in dummy TD.
6341	 */
6342	Set_ED(ept->hced_tailp, (ohci_td_cpu_to_iommu(ohcip, dummy_td)));
6343
6344	/* Exit the critical */
6345	ddi_exit_critical(ddic);
6346
6347	USB_DPRINTF_L3(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6348	    "ohci_insert_td_with_frame_number:"
6349	    "current frame number 0x%llx start frame number 0x%llx",
6350	    (unsigned long long)current_frame_number,
6351	    (unsigned long long)start_frame_number);
6352
6353	/*
6354	 * Increment this saved frame number by current number
6355	 * of data packets needs to be transfer.
6356	 */
6357	pp->pp_next_frame_number = start_frame_number + isoc_pkts;
6358
6359	/*
6360	 * Set OHCI_ISOC_XFER_CONTINUE flag in order to send other
6361	 * isochronous packets,  part of the current isoch request
6362	 * in the subsequent frames.
6363	 */
6364	pp->pp_flag |= OHCI_ISOC_XFER_CONTINUE;
6365
6366	return (USB_SUCCESS);
6367}
6368
6369
6370/*
6371 * ohci_insert_td_on_tw:
6372 *
6373 * The transfer wrapper keeps a list of all Transfer Descriptors (TD) that
6374 * are allocated for this transfer. Insert a TD  onto this list. The  list
6375 * of TD's does not include the dummy TD that is at the end of the list of
6376 * TD's for the endpoint.
6377 */
6378static void
6379ohci_insert_td_on_tw(
6380	ohci_state_t		*ohcip,
6381	ohci_trans_wrapper_t	*tw,
6382	ohci_td_t		*td)
6383{
6384	/*
6385	 * Set the next pointer to NULL because
6386	 * this is the last TD on list.
6387	 */
6388	Set_TD(td->hctd_tw_next_td, NULL);
6389
6390	if (tw->tw_hctd_head == NULL) {
6391		ASSERT(tw->tw_hctd_tail == NULL);
6392		tw->tw_hctd_head = td;
6393		tw->tw_hctd_tail = td;
6394	} else {
6395		ohci_td_t *dummy = (ohci_td_t *)tw->tw_hctd_tail;
6396
6397		ASSERT(dummy != NULL);
6398		ASSERT(dummy != td);
6399		ASSERT(Get_TD(td->hctd_state) != HC_TD_DUMMY);
6400
6401		/* Add the td to the end of the list */
6402		Set_TD(dummy->hctd_tw_next_td,
6403		    ohci_td_cpu_to_iommu(ohcip, td));
6404
6405		tw->tw_hctd_tail = td;
6406
6407		ASSERT(Get_TD(td->hctd_tw_next_td) == 0);
6408	}
6409}
6410
6411
6412/*
6413 * ohci_traverse_tds:
6414 * NOTE: This function is also called from POLLED MODE.
6415 *
6416 * Traverse the list of TD's for an endpoint.  Since the endpoint is marked
6417 * as sKipped,	the Host Controller (HC) is no longer accessing these TD's.
6418 * Remove all the TD's that are attached to the endpoint.
6419 */
6420void
6421ohci_traverse_tds(
6422	ohci_state_t		*ohcip,
6423	usba_pipe_handle_data_t	*ph)
6424{
6425	ohci_trans_wrapper_t	*tw;
6426	ohci_ed_t		*ept;
6427	ohci_pipe_private_t	*pp;
6428	uint32_t		addr;
6429	ohci_td_t		*tailp, *headp, *next;
6430
6431	pp = (ohci_pipe_private_t *)ph->p_hcd_private;
6432	ept = pp->pp_ept;
6433
6434	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6435	    "ohci_traverse_tds: ph = 0x%p ept = 0x%p",
6436	    (void *)ph, (void *)ept);
6437
6438	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
6439
6440	addr = Get_ED(ept->hced_headp) & (uint32_t)HC_EPT_TD_HEAD;
6441
6442	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6443	    "ohci_traverse_tds: addr (head) = 0x%x", addr);
6444
6445	headp = (ohci_td_t *)(ohci_td_iommu_to_cpu(ohcip, addr));
6446
6447	addr = Get_ED(ept->hced_tailp) & (uint32_t)HC_EPT_TD_TAIL;
6448
6449	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6450	    "ohci_traverse_tds: addr (tail) = 0x%x", addr);
6451
6452	tailp = (ohci_td_t *)(ohci_td_iommu_to_cpu(ohcip, addr));
6453
6454	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6455	    "ohci_traverse_tds: cpu head = 0x%p cpu tail = 0x%p",
6456	    (void *)headp, (void *)tailp);
6457
6458	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6459	    "ohci_traverse_tds: iommu head = 0x%x iommu tail = 0x%x",
6460	    ohci_td_cpu_to_iommu(ohcip, headp),
6461	    ohci_td_cpu_to_iommu(ohcip, tailp));
6462
6463	/*
6464	 * Traverse the list of TD's that are currently on the endpoint.
6465	 * These TD's have not been processed and will not be processed
6466	 * because the endpoint processing is stopped.
6467	 */
6468	while (headp != tailp) {
6469		next = (ohci_td_t *)(ohci_td_iommu_to_cpu(ohcip,
6470		    (Get_TD(headp->hctd_next_td) & HC_EPT_TD_TAIL)));
6471
6472		tw = (ohci_trans_wrapper_t *)OHCI_LOOKUP_ID(
6473		    (uint32_t)Get_TD(headp->hctd_trans_wrapper));
6474
6475		/* Stop the the transfer timer */
6476		ohci_stop_xfer_timer(ohcip, tw, OHCI_REMOVE_XFER_ALWAYS);
6477
6478		ohci_deallocate_td(ohcip, headp);
6479		headp = next;
6480	}
6481
6482	/* Both head and tail pointers must be same */
6483	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6484	    "ohci_traverse_tds: head = 0x%p tail = 0x%p",
6485	    (void *)headp, (void *)tailp);
6486
6487	/* Update the pointer in the endpoint descriptor */
6488	Set_ED(ept->hced_headp, (ohci_td_cpu_to_iommu(ohcip, headp)));
6489
6490	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6491	    "ohci_traverse_tds: new head = 0x%x",
6492	    (ohci_td_cpu_to_iommu(ohcip, headp)));
6493
6494	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6495	    "ohci_traverse_tds: tailp = 0x%x headp = 0x%x",
6496	    (Get_ED(ept->hced_tailp) & HC_EPT_TD_TAIL),
6497	    (Get_ED(ept->hced_headp) & HC_EPT_TD_HEAD));
6498
6499	ASSERT((Get_ED(ept->hced_tailp) & HC_EPT_TD_TAIL) ==
6500	    (Get_ED(ept->hced_headp) & HC_EPT_TD_HEAD));
6501}
6502
6503
6504/*
6505 * ohci_done_list_tds:
6506 *
6507 * There may be TD's on the done list that have not been processed yet. Walk
6508 * through these TD's and mark them as RECLAIM. All the mappings for the  TD
6509 * will be torn down, so the interrupt handle is alerted of this fact through
6510 * the RECLAIM flag.
6511 */
6512static void
6513ohci_done_list_tds(
6514	ohci_state_t		*ohcip,
6515	usba_pipe_handle_data_t	*ph)
6516{
6517	ohci_pipe_private_t	*pp = (ohci_pipe_private_t *)ph->p_hcd_private;
6518	ohci_trans_wrapper_t	*head_tw = pp->pp_tw_head;
6519	ohci_trans_wrapper_t	*next_tw;
6520	ohci_td_t		*head_td, *next_td;
6521
6522	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
6523
6524	USB_DPRINTF_L4(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6525	    "ohci_done_list_tds:");
6526
6527	/* Process the transfer wrappers for this pipe */
6528	next_tw = head_tw;
6529	while (next_tw) {
6530		head_td = (ohci_td_t *)next_tw->tw_hctd_head;
6531		next_td = head_td;
6532
6533		if (head_td) {
6534			/*
6535			 * Walk through each TD for this transfer
6536			 * wrapper. If a TD still exists, then it
6537			 * is currently on the done list.
6538			 */
6539			while (next_td) {
6540
6541				/* To free TD, set TD state to RECLAIM */
6542				Set_TD(next_td->hctd_state, HC_TD_RECLAIM);
6543
6544				Set_TD(next_td->hctd_trans_wrapper, NULL);
6545
6546				next_td = ohci_td_iommu_to_cpu(ohcip,
6547				    Get_TD(next_td->hctd_tw_next_td));
6548			}
6549		}
6550
6551		/* Stop the the transfer timer */
6552		ohci_stop_xfer_timer(ohcip, next_tw, OHCI_REMOVE_XFER_ALWAYS);
6553
6554		next_tw = next_tw->tw_next;
6555	}
6556}
6557
6558
6559/*
6560 * Remove old_td from tw and update the links.
6561 */
6562void
6563ohci_unlink_td_from_tw(
6564	ohci_state_t		*ohcip,
6565	ohci_td_t		*old_td,
6566	ohci_trans_wrapper_t	*tw)
6567{
6568	ohci_td_t *next, *head, *tail;
6569
6570	USB_DPRINTF_L4(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
6571	    "ohci_unlink_td_from_tw: ohcip = 0x%p, old_td = 0x%p, tw = 0x%p",
6572	    (void *)ohcip, (void *)old_td, (void *)tw);
6573
6574	if (old_td == NULL || tw == NULL) {
6575
6576		return;
6577	}
6578
6579	head = tw->tw_hctd_head;
6580	tail = tw->tw_hctd_tail;
6581
6582	if (head == NULL) {
6583
6584		return;
6585	}
6586
6587	/* if this old_td is on head */
6588	if (old_td == head) {
6589		if (old_td == tail) {
6590			tw->tw_hctd_head = NULL;
6591			tw->tw_hctd_tail = NULL;
6592		} else {
6593			tw->tw_hctd_head = ohci_td_iommu_to_cpu(ohcip,
6594			    Get_TD(head->hctd_tw_next_td));
6595		}
6596
6597		return;
6598	}
6599
6600	/* find this old_td's position in the tw */
6601	next = ohci_td_iommu_to_cpu(ohcip, Get_TD(head->hctd_tw_next_td));
6602	while (next && (old_td != next)) {
6603		head = next;
6604		next = ohci_td_iommu_to_cpu(ohcip,
6605		    Get_TD(next->hctd_tw_next_td));
6606	}
6607
6608	/* unlink the found old_td from the tw */
6609	if (old_td == next) {
6610		Set_TD(head->hctd_tw_next_td, Get_TD(next->hctd_tw_next_td));
6611		if (old_td == tail) {
6612			tw->tw_hctd_tail = head;
6613		}
6614	}
6615}
6616
6617
6618/*
6619 * ohci_deallocate_td:
6620 * NOTE: This function is also called from POLLED MODE.
6621 *
6622 * Deallocate a Host Controller's (HC) Transfer Descriptor (TD).
6623 */
6624void
6625ohci_deallocate_td(
6626	ohci_state_t	*ohcip,
6627	ohci_td_t	*old_td)
6628{
6629	ohci_trans_wrapper_t	*tw;
6630
6631	USB_DPRINTF_L4(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
6632	    "ohci_deallocate_td: old_td = 0x%p", (void *)old_td);
6633
6634	ASSERT(mutex_owned(&ohcip->ohci_int_mutex));
6635
6636	/*
6637	 * Obtain the transaction wrapper and tw will be
6638	 * NULL for the dummy and for the reclaim TD's.
6639	 */
6640	if ((Get_TD(old_td->hctd_state) == HC_TD_DUMMY) ||
6641	    (Get_TD(old_td->hctd_state) == HC_TD_RECLAIM)) {
6642		tw = (ohci_trans_wrapper_t *)((uintptr_t)
6643		    Get_TD(old_td->hctd_trans_wrapper));
6644		ASSERT(tw == NULL);
6645	} else {
6646		tw = (ohci_trans_wrapper_t *)
6647		    OHCI_LOOKUP_ID((uint32_t)
6648		    Get_TD(old_td->hctd_trans_wrapper));
6649		ASSERT(tw != NULL);
6650	}
6651
6652	/*
6653	 * If this TD should be reclaimed, don't try to access its
6654	 * transfer wrapper.
6655	 */
6656	if ((Get_TD(old_td->hctd_state) != HC_TD_RECLAIM) && tw) {
6657
6658		ohci_unlink_td_from_tw(ohcip, old_td, tw);
6659	}
6660
6661	bzero((void *)old_td, sizeof (ohci_td_t));
6662	Set_TD(old_td->hctd_state, HC_TD_FREE);
6663
6664	USB_DPRINTF_L3(PRINT_MASK_ALLOC, ohcip->ohci_log_hdl,
6665	    "ohci_deallocate_td: td 0x%p", (void *)old_td);
6666}
6667
6668
6669/*
6670 * ohci_td_cpu_to_iommu:
6671 * NOTE: This function is also called from POLLED MODE.
6672 *
6673 * This function converts for the given Transfer Descriptor (TD) CPU address
6674 * to IO address.
6675 */
6676uint32_t
6677ohci_td_cpu_to_iommu(
6678	ohci_state_t	*ohcip,
6679	ohci_td_t	*addr)
6680{
6681	uint32_t	td;
6682
6683	td  = (uint32_t)ohcip->ohci_td_pool_cookie.dmac_address +
6684	    (uint32_t)((uintptr_t)addr - (uintptr_t)(ohcip->ohci_td_pool_addr));
6685
6686	ASSERT((ohcip->ohci_td_pool_cookie.dmac_address +
6687	    (uint32_t) (sizeof (ohci_td_t) *
6688	    (addr - ohcip->ohci_td_pool_addr))) ==
6689	    (ohcip->ohci_td_pool_cookie.dmac_address +
6690	    (uint32_t)((uintptr_t)addr - (uintptr_t)
6691	    (ohcip->ohci_td_pool_addr))));
6692
6693	ASSERT(td >= ohcip->ohci_td_pool_cookie.dmac_address);
6694	ASSERT(td <= ohcip->ohci_td_pool_cookie.dmac_address +
6695	    sizeof (ohci_td_t) * ohci_td_pool_size);
6696
6697	return (td);
6698}
6699
6700
6701/*
6702 * ohci_td_iommu_to_cpu:
6703 * NOTE: This function is also called from POLLED MODE.
6704 *
6705 * This function converts for the given Transfer Descriptor (TD) IO address
6706 * to CPU address.
6707 */
6708ohci_td_t *
6709ohci_td_iommu_to_cpu(
6710	ohci_state_t	*ohcip,
6711	uintptr_t	addr)
6712{
6713	ohci_td_t	*td;
6714
6715	if (addr == 0)
6716		return (NULL);
6717
6718	td = (ohci_td_t *)((uintptr_t)
6719	    (addr - ohcip->ohci_td_pool_cookie.dmac_address) +
6720	    (uintptr_t)ohcip->ohci_td_pool_addr);
6721
6722	ASSERT(td >= ohcip->ohci_td_pool_addr);
6723	ASSERT((uintptr_t)td <= (uintptr_t)ohcip->ohci_td_pool_addr +
6724	    (uintptr_t)(sizeof (ohci_td_t) * ohci_td_pool_size));
6725
6726	return (td);
6727}
6728
6729/*
6730 * ohci_allocate_tds_for_tw:
6731 *
6732 * Allocate n Transfer Descriptors (TD) from the TD buffer pool and places it
6733 * into the TW.
6734 *
6735 * Returns USB_NO_RESOURCES if it was not able to allocate all the requested TD
6736 * otherwise USB_SUCCESS.
6737 */
6738int
6739ohci_allocate_tds_for_tw(
6740	ohci_state_t		*ohcip,
6741	ohci_trans_wrapper_t	*tw,
6742	size_t			td_count)
6743{
6744	ohci_td_t		*td;
6745	uint32_t		td_addr;
6746	int			i;
6747	int			error = USB_SUCCESS;
6748
6749	for (i = 0; i < td_count; i++) {
6750		td = ohci_allocate_td_from_pool(ohcip);
6751		if (td == NULL) {
6752			error = USB_NO_RESOURCES;
6753			USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6754			    "ohci_allocate_tds_for_tw: "
6755			    "Unable to allocate %lu TDs",
6756			    td_count);
6757			break;
6758		}
6759		if (tw->tw_hctd_free_list != NULL) {
6760			td_addr = ohci_td_cpu_to_iommu(ohcip,
6761			    tw->tw_hctd_free_list);
6762			Set_TD(td->hctd_tw_next_td, td_addr);
6763		}
6764		tw->tw_hctd_free_list = td;
6765	}
6766
6767	return (error);
6768}
6769
6770/*
6771 * ohci_allocate_tw_resources:
6772 *
6773 * Allocate a Transaction Wrapper (TW) and n Transfer Descriptors (TD)
6774 * from the TD buffer pool and places it into the TW.  It does an all
6775 * or nothing transaction.
6776 *
6777 * Returns NULL if there is insufficient resources otherwise TW.
6778 */
6779static ohci_trans_wrapper_t *
6780ohci_allocate_tw_resources(
6781	ohci_state_t		*ohcip,
6782	ohci_pipe_private_t	*pp,
6783	size_t			tw_length,
6784	usb_flags_t		usb_flags,
6785	size_t			td_count)
6786{
6787	ohci_trans_wrapper_t	*tw;
6788
6789	tw = ohci_create_transfer_wrapper(ohcip, pp, tw_length, usb_flags);
6790
6791	if (tw == NULL) {
6792		USB_DPRINTF_L2(PRINT_MASK_LISTS, ohcip->ohci_log_hdl,
6793		    "ohci_allocate_tw_resources: Unable to allocate TW");
6794	} else {
6795		if (ohci_allocate_tds_for_tw(ohcip, tw, td_count) ==
6796		    USB_SUCCESS) {
6797			tw->tw_num_tds = (uint_t)td_count;
6798		} else {
6799			ohci_deallocate_tw_resources(ohcip, pp, tw);
6800			tw = NULL;
6801		}
6802	}
6803
6804	return (tw);
6805}
6806
6807/*
6808 * ohci_free_tw_tds_resources:
6809 *
6810 * Free all allocated resources for Transaction Wrapper (TW).
6811 * Does not free the TW itself.
6812 */
6813static void
6814ohci_free_tw_tds_resources(
6815	ohci_state_t		*ohcip,
6816	ohci_trans_wrapper_t	*tw)
6817{
6818	ohci_td_t		*td;
6819	ohci_td_t		*temp_td;
6820
6821	td = tw->tw_hctd_free_list;
6822	while (td != NULL) {
6823		/* Save the pointer to the next td before destroying it */
6824		temp_td = ohci_td_iommu_to_cpu(ohcip,
6825		    Get_TD(td->hctd_tw_next_td));
6826		ohci_deallocate_td(ohcip, td);
6827		td = temp_td;
6828	}
6829	tw->tw_hctd_free_list = NULL;
6830}
6831
6832
6833/*
6834 * Transfer Wrapper functions
6835 *
6836 * ohci_create_transfer_wrapper:
6837 *
6838 * Create a Transaction Wrapper (TW) for non-isoc transfer types
6839 * and this involves the allocating of DMA resources.
6840 */
6841static ohci_trans_wrapper_t *
6842ohci_create_transfer_wrapper(
6843	ohci_state_t		*ohcip,
6844	ohci_pipe_private_t	*pp,
6845	size_t			length,
6846	uint_t			usb_flags)
6847{
6848	ddi_device_acc_attr_t	dev_attr;