xref: /illumos-gate/usr/src/uts/common/io/nxge/npi/npi_vir.c (revision 56d930ae)
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 2007 Sun Microsystems, Inc.  All rights reserved.
23  * Use is subject to license terms.
24  */
25 
26 #pragma ident	"%Z%%M%	%I%	%E% SMI"
27 
28 #include <npi_vir.h>
29 
30 /* One register only */
31 uint64_t pio_offset[] = {
32 	DEV_FUNC_SR_REG
33 };
34 
35 const char *pio_name[] = {
36 	"DEV_FUNC_SR_REG",
37 };
38 
39 /* One register only */
40 uint64_t fzc_pio_offset[] = {
41 	MULTI_PART_CTL_REG,
42 	LDGITMRES_REG
43 };
44 
45 const char *fzc_pio_name[] = {
46 	"MULTI_PART_CTL_REG",
47 	"LDGITMRES_REG"
48 };
49 
50 /* 64 sets */
51 uint64_t fzc_pio_dma_bind_offset[] = {
52 	DMA_BIND_REG
53 };
54 
55 const char *fzc_pio_dma_bind_name[] = {
56 	"DMA_BIND_REG",
57 };
58 
59 /* 69 logical devices */
60 uint64_t fzc_pio_ldgnum_offset[] = {
61 	LDG_NUM_REG
62 };
63 
64 const char *fzc_pio_ldgnum_name[] = {
65 	"LDG_NUM_REG",
66 };
67 
68 /* PIO_LDSV, 64 sets by 8192 bytes */
69 uint64_t pio_ldsv_offset[] = {
70 	LDSV0_REG,
71 	LDSV1_REG,
72 	LDSV2_REG,
73 	LDGIMGN_REG
74 };
75 const char *pio_ldsv_name[] = {
76 	"LDSV0_REG",
77 	"LDSV1_REG",
78 	"LDSV2_REG",
79 	"LDGIMGN_REG"
80 };
81 
82 /* PIO_IMASK0: 64 by 8192 */
83 uint64_t pio_imask0_offset[] = {
84 	LD_IM0_REG,
85 };
86 
87 const char *pio_imask0_name[] = {
88 	"LD_IM0_REG",
89 };
90 
91 /* PIO_IMASK1: 5 by 8192 */
92 uint64_t pio_imask1_offset[] = {
93 	LD_IM1_REG
94 };
95 
96 const char *pio_imask1_name[] = {
97 	"LD_IM1_REG"
98 };
99 
100 /* SID: 64 by 8 */
101 uint64_t fzc_pio_sid_offset[] = {
102 	SID_REG
103 };
104 
105 const char *fzc_pio_sid_name[] = {
106 	"SID_REG"
107 };
108 
109 npi_status_t
110 npi_vir_dump_pio_fzc_regs_one(npi_handle_t handle)
111 {
112 	uint64_t value;
113 	int num_regs, i;
114 
115 	NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
116 		"\nPIO FZC Common Register Dump\n"));
117 
118 	num_regs = sizeof (pio_offset) / sizeof (uint64_t);
119 	for (i = 0; i < num_regs; i++) {
120 		value = 0;
121 		NXGE_REG_RD64(handle, pio_offset[i], &value);
122 		NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL, "0x%08llx "
123 			"%s\t 0x%08llx \n",
124 			pio_offset[i],
125 			pio_name[i], value));
126 	}
127 
128 	num_regs = sizeof (fzc_pio_offset) / sizeof (uint64_t);
129 	for (i = 0; i < num_regs; i++) {
130 		NXGE_REG_RD64(handle, fzc_pio_offset[i], &value);
131 		NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL, "0x%08llx "
132 			"%s\t 0x%08llx \n",
133 			fzc_pio_offset[i],
134 			fzc_pio_name[i], value));
135 	}
136 
137 	NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
138 		"\n PIO FZC Register Dump Done \n"));
139 	return (NPI_SUCCESS);
140 }
141 
142 npi_status_t
143 npi_vir_dump_ldgnum(npi_handle_t handle)
144 {
145 	uint64_t value = 0, offset = 0;
146 	int num_regs, i, ldv;
147 
148 	NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
149 		"\nFZC PIO LDG Number Register Dump\n"));
150 
151 	num_regs = sizeof (fzc_pio_ldgnum_offset) / sizeof (uint64_t);
152 	for (ldv = 0; ldv < NXGE_INT_MAX_LDS; ldv++) {
153 		for (i = 0; i < num_regs; i++) {
154 			value = 0;
155 			offset = fzc_pio_ldgnum_offset[i] + 8 * ldv;
156 			NXGE_REG_RD64(handle, offset, &value);
157 			NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
158 				"Logical Device %d: 0x%08llx "
159 				"%s\t 0x%08llx \n",
160 				ldv, offset,
161 				fzc_pio_ldgnum_name[i], value));
162 		}
163 	}
164 
165 	NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
166 		"\n FZC PIO LDG Register Dump Done \n"));
167 
168 	return (NPI_SUCCESS);
169 }
170 
171 npi_status_t
172 npi_vir_dump_ldsv(npi_handle_t handle)
173 {
174 	uint64_t value, offset;
175 	int num_regs, i, ldg;
176 
177 	NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
178 		"\nLD Device State Vector Register Dump\n"));
179 
180 	num_regs = sizeof (pio_ldsv_offset) / sizeof (uint64_t);
181 	for (ldg = 0; ldg < NXGE_INT_MAX_LDGS; ldg++) {
182 		for (i = 0; i < num_regs; i++) {
183 			value = 0;
184 			offset = pio_ldsv_offset[i] + 8192 * ldg;
185 			NXGE_REG_RD64(handle, offset, &value);
186 			NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
187 				    "LDG State: group %d: 0x%08llx "
188 				    "%s\t 0x%08llx \n",
189 				ldg, offset,
190 				pio_ldsv_name[i], value));
191 		}
192 	}
193 
194 	NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
195 		"\n FZC PIO LDG Register Dump Done \n"));
196 
197 	return (NPI_SUCCESS);
198 }
199 
200 npi_status_t
201 npi_vir_dump_imask0(npi_handle_t handle)
202 {
203 	uint64_t value, offset;
204 	int num_regs, i, ldv;
205 
206 	NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
207 		"\nLD Interrupt Mask Register Dump\n"));
208 
209 	num_regs = sizeof (pio_imask0_offset) / sizeof (uint64_t);
210 	for (ldv = 0; ldv < 64; ldv++) {
211 		for (i = 0; i < num_regs; i++) {
212 			value = 0;
213 			offset = pio_imask0_offset[i] + 8192 * ldv;
214 			NXGE_REG_RD64(handle, offset,
215 				&value);
216 			NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
217 				"LD Interrupt Mask %d: 0x%08llx "
218 				"%s\t 0x%08llx \n",
219 				ldv, offset,
220 				pio_imask0_name[i], value));
221 		}
222 	}
223 	num_regs = sizeof (pio_imask1_offset) / sizeof (uint64_t);
224 	for (ldv = 64; ldv < 69; ldv++) {
225 		for (i = 0; i < num_regs; i++) {
226 			value = 0;
227 			offset = pio_imask1_offset[i] + 8192 * (ldv - 64);
228 			NXGE_REG_RD64(handle, offset,
229 				&value);
230 			NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
231 				"LD Interrupt Mask %d: 0x%08llx "
232 				"%s\t 0x%08llx \n",
233 				ldv, offset,
234 				pio_imask1_name[i], value));
235 		}
236 	}
237 
238 	NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
239 		"\n FZC PIO Logical Device Group Register Dump Done \n"));
240 
241 	return (NPI_SUCCESS);
242 }
243 
244 npi_status_t
245 npi_vir_dump_sid(npi_handle_t handle)
246 {
247 	uint64_t value, offset;
248 	int num_regs, i, ldg;
249 
250 	NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
251 		"\nSystem Interrupt Data Register Dump\n"));
252 
253 	num_regs = sizeof (fzc_pio_sid_offset) / sizeof (uint64_t);
254 	for (ldg = 0; ldg < NXGE_INT_MAX_LDGS; ldg++) {
255 		for (i = 0; i < num_regs; i++) {
256 			value = 0;
257 			offset = fzc_pio_sid_offset[i] + 8 * ldg;
258 			NXGE_REG_RD64(handle, offset,
259 				&value);
260 			NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
261 				"SID for group %d: 0x%08llx "
262 				"%s\t 0x%08llx \n",
263 				ldg, offset,
264 				fzc_pio_sid_name[i], value));
265 		}
266 	}
267 
268 	NPI_REG_DUMP_MSG((handle.function, NPI_REG_CTL,
269 		"\n FZC PIO SID Register Dump Done \n"));
270 
271 	return (NPI_SUCCESS);
272 }
273 
274 /*
275  * npi_dev_func_sr_init():
276  *	This function is called to initialize the device function
277  *	shared register (set the software implementation lock
278  *	state to FREE).
279  * Parameters:
280  *	handle		- NPI handle
281  * Return:
282  *	NPI_SUCCESS	- If initialization is complete successfully.
283  *			  (set sr bits to free).
284  *	Error:
285  *	NPI_FAILURE
286  *		VIR_TAS_BUSY
287  */
288 
289 npi_status_t
290 npi_dev_func_sr_init(npi_handle_t handle)
291 {
292 	dev_func_sr_t		sr;
293 	int			status = NPI_SUCCESS;
294 
295 	NXGE_REG_RD64(handle, DEV_FUNC_SR_REG, &sr.value);
296 	if (!sr.bits.ldw.tas) {
297 		/*
298 		 * After read, this bit is set to 1 by hardware.
299 		 * We own it if tas bit read as 0.
300 		 * Set the lock state to free if it is in reset state.
301 		 */
302 		if (!sr.bits.ldw.sr) {
303 			/* reset state */
304 			sr.bits.ldw.sr |= NPI_DEV_SR_LOCK_ST_FREE;
305 			NXGE_REG_WR64(handle, DEV_FUNC_SR_REG, sr.value);
306 			sr.bits.ldw.tas = 0;
307 			NXGE_REG_WR64(handle, DEV_FUNC_SR_REG, sr.value);
308 		}
309 
310 		NPI_DEBUG_MSG((handle.function, NPI_VIR_CTL,
311 			" npi_dev_func_sr_init"
312 			" sr <0x%x>",
313 			sr.bits.ldw.sr));
314 	} else {
315 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
316 				    " npi_dev_func_sr_init"
317 				    " tas busy <0x%x>",
318 				    sr.bits.ldw));
319 		status = NPI_VIR_TAS_BUSY(sr.bits.ldw.funcid);
320 	}
321 
322 	return (status);
323 }
324 
325 /*
326  * npi_dev_func_sr_lock_enter():
327  *	This function is called to lock the function shared register
328  *	by setting the lock state to busy.
329  * Parameters:
330  *	handle		- NPI handle
331  * Return:
332  *	NPI_SUCCESS	- If the function id can own the lock.
333  *
334  *	Error:
335  *	NPI_FAILURE
336  *		VIR_SR_RESET
337  *		VIR_SR_BUSY
338  *		VIR_SR_INVALID
339  *		VIR_TAS_BUSY
340  */
341 
342 npi_status_t
343 npi_dev_func_sr_lock_enter(npi_handle_t handle)
344 {
345 	dev_func_sr_t		sr;
346 	int			status = NPI_SUCCESS;
347 	uint32_t		state;
348 
349 	NXGE_REG_RD64(handle, DEV_FUNC_SR_REG, &sr.value);
350 	if (!sr.bits.ldw.tas) {
351 		/*
352 		 * tas bit will be set to 1 by hardware.
353 		 * reset tas bit when we unlock the sr.
354 		 */
355 		state = sr.bits.ldw.sr & NPI_DEV_SR_LOCK_ST_MASK;
356 		switch (state) {
357 		case NPI_DEV_SR_LOCK_ST_FREE:
358 			/*
359 			 * set it to busy and our function id.
360 			 */
361 			sr.bits.ldw.sr |= (NPI_DEV_SR_LOCK_ST_BUSY |
362 						(sr.bits.ldw.funcid <<
363 						NPI_DEV_SR_LOCK_FID_SHIFT));
364 			NXGE_REG_WR64(handle, DEV_FUNC_SR_REG, sr.value);
365 			break;
366 
367 		case NPI_DEV_SR_LOCK_ST_RESET:
368 			NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
369 					    " npi_dev_func_sr_lock_enter"
370 					    " reset state <0x%x>",
371 					    sr.bits.ldw.sr));
372 			status = NPI_VIR_SR_RESET(sr.bits.ldw.funcid);
373 			break;
374 
375 		case NPI_DEV_SR_LOCK_ST_BUSY:
376 			NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
377 					    " npi_dev_func_sr_lock_enter"
378 					    " busy <0x%x>",
379 					    sr.bits.ldw.sr));
380 			status = NPI_VIR_SR_BUSY(sr.bits.ldw.funcid);
381 			break;
382 
383 		default:
384 			NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
385 					    " npi_dev_func_sr_lock_enter",
386 					    " invalid state",
387 					    sr.bits.ldw.sr));
388 			status = NPI_VIR_SR_INVALID(sr.bits.ldw.funcid);
389 			break;
390 		}
391 	} else {
392 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
393 				    " npi_dev_func_sr_lock_enter",
394 				    " tas busy", sr.bits.ldw));
395 		status = NPI_VIR_TAS_BUSY(sr.bits.ldw.funcid);
396 	}
397 
398 	return (status);
399 }
400 
401 /*
402  * npi_dev_func_sr_lock_free():
403  *	This function is called to free the function shared register
404  *	by setting the lock state to free.
405  * Parameters:
406  *	handle		- NPI handle
407  * Return:
408  *	NPI_SUCCESS	- If the function id can free the lock.
409  *
410  *	Error:
411  *	NPI_FAILURE
412  *		VIR_SR_NOTOWNER
413  *		VIR_TAS_NOTREAD
414  */
415 
416 npi_status_t
417 npi_dev_func_sr_lock_free(npi_handle_t handle)
418 {
419 	dev_func_sr_t		sr;
420 	int			status = NPI_SUCCESS;
421 
422 	NXGE_REG_RD64(handle, DEV_FUNC_SR_REG, &sr.value);
423 	if (sr.bits.ldw.tas) {
424 		if (sr.bits.ldw.funcid == NPI_GET_LOCK_OWNER(sr.bits.ldw.sr)) {
425 			sr.bits.ldw.sr &= NPI_DEV_SR_IMPL_ST_MASK;
426 			sr.bits.ldw.sr |= NPI_DEV_SR_LOCK_ST_FREE;
427 			sr.bits.ldw.tas = 0;
428 			NXGE_REG_WR64(handle, DEV_FUNC_SR_REG, sr.value);
429 		} else {
430 			NPI_DEBUG_MSG((handle.function, NPI_VIR_CTL,
431 					    " npi_dev_func_sr_lock_free"
432 					    " not owner <0x%x>",
433 					    sr.bits.ldw.sr));
434 			status = NPI_VIR_SR_NOTOWNER(sr.bits.ldw.funcid);
435 		}
436 	} else {
437 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
438 				    " npi_dev_func_sr_lock_free",
439 				    " invalid tas state <0x%x>",
440 				    sr.bits.ldw.tas));
441 		status = NPI_VIR_TAS_NOTREAD(sr.bits.ldw.funcid);
442 	}
443 
444 	return (status);
445 }
446 
447 /*
448  * npi_dev_func_sr_funcid_get():
449  *	This function is called to get the caller's function ID.
450  *	(based on address bits [25:26] on read access.
451  *	(After read, the TAS bit is always set to 1. Software needs
452  *	to write 0 to clear.) This function will write 0 to clear
453  *	the TAS bit if we own it.
454  * Parameters:
455  *	handle		- NPI handle
456  *	funcid_p	- pointer to store the function id.
457  * Return:
458  *	NPI_SUCCESS	- If get function id is complete successfully.
459  *
460  *	Error:
461  */
462 
463 npi_status_t
464 npi_dev_func_sr_funcid_get(npi_handle_t handle, uint8_t *funcid_p)
465 {
466 	dev_func_sr_t		sr;
467 
468 	NXGE_REG_RD64(handle, DEV_FUNC_SR_REG, &sr.value);
469 	*funcid_p = NXGE_VAL(DEV_FUNC_SR_FUNCID, sr.value);
470 	if (!sr.bits.ldw.tas) {
471 		/*
472 		 * After read, this bit is set to 1 by hardware.
473 		 * We own it if tas bit read as 0.
474 		 */
475 		sr.bits.ldw.tas = 0;
476 		NXGE_REG_WR64(handle, DEV_FUNC_SR_REG, sr.value);
477 	}
478 
479 	return (NPI_SUCCESS);
480 }
481 
482 /*
483  * npi_dev_func_sr_sr_get():
484  *	This function is called to get the shared register value.
485  *	(After read, the TAS bit is always set to 1. Software needs
486  *	to write 0 to clear if we own it.)
487  *
488  * Parameters:
489  *	handle		- NPI handle
490  *	sr_p		- pointer to store the shared value of this register.
491  *
492  * Return:
493  *	NPI_SUCCESS		- If shared value get is complete successfully.
494  *
495  *	Error:
496  */
497 npi_status_t
498 npi_dev_func_sr_sr_raw_get(npi_handle_t handle, uint16_t *sr_p)
499 {
500 	dev_func_sr_t		sr;
501 
502 	NXGE_REG_RD64(handle, DEV_FUNC_SR_REG, &sr.value);
503 	*sr_p = NXGE_VAL(DEV_FUNC_SR_FUNCID, sr.value);
504 	if (!sr.bits.ldw.tas) {
505 		/*
506 		 * After read, this bit is set to 1 by hardware.
507 		 * We own it if tas bit read as 0.
508 		 */
509 		sr.bits.ldw.tas = 0;
510 		NXGE_REG_WR64(handle, DEV_FUNC_SR_REG, sr.value);
511 	}
512 
513 	return (NPI_SUCCESS);
514 }
515 
516 /*
517  * npi_dev_func_sr_sr_get():
518  *	This function is called to get the shared register value.
519  *	(After read, the TAS bit is always set to 1. Software needs
520  *	to write 0 to clear if we own it.)
521  *
522  * Parameters:
523  *	handle	- NPI handle
524  *	sr_p	- pointer to store the shared value of this register.
525  *		. this will get only non-lock, non-function id portion
526  *              . of the register
527  *
528  *
529  * Return:
530  *	NPI_SUCCESS		- If shared value get is complete successfully.
531  *
532  *	Error:
533  */
534 
535 npi_status_t
536 npi_dev_func_sr_sr_get(npi_handle_t handle, uint16_t *sr_p)
537 {
538 	dev_func_sr_t		sr;
539 	uint16_t sr_impl = 0;
540 
541 	NXGE_REG_RD64(handle, DEV_FUNC_SR_REG, &sr.value);
542 	sr_impl = NXGE_VAL(DEV_FUNC_SR_FUNCID, sr.value);
543 	*sr_p =  (sr_impl << NPI_DEV_SR_IMPL_ST_SHIFT);
544 	if (!sr.bits.ldw.tas) {
545 		/*
546 		 * After read, this bit is set to 1 by hardware.
547 		 * We own it if tas bit read as 0.
548 		 */
549 		sr.bits.ldw.tas = 0;
550 		NXGE_REG_WR64(handle, DEV_FUNC_SR_REG, sr.value);
551 	}
552 
553 	return (NPI_SUCCESS);
554 }
555 
556 /*
557  * npi_dev_func_sr_sr_get_set_clear():
558  *	This function is called to set the shared register value.
559  *	(Shared register must be read first. If tas bit is 0, then
560  *	it implies that the software can proceed to set). After
561  *	setting, tas bit will be cleared.
562  * Parameters:
563  *	handle		- NPI handle
564  *	impl_sr		- shared value to set (only the 8 bit
565  *			  implementation specific state info).
566  *
567  * Return:
568  *	NPI_SUCCESS		- If shared value is set successfully.
569  *
570  *	Error:
571  *	NPI_FAILURE
572  *		VIR_TAS_BUSY
573  */
574 
575 npi_status_t
576 npi_dev_func_sr_sr_get_set_clear(npi_handle_t handle, uint16_t impl_sr)
577 {
578 	dev_func_sr_t		sr;
579 	int			status;
580 
581 	status = npi_dev_func_sr_lock_enter(handle);
582 	if (status != NPI_SUCCESS) {
583 		NPI_DEBUG_MSG((handle.function, NPI_VIR_CTL,
584 				    " npi_dev_func_sr_src_get_set_clear"
585 				    " unable to acquire lock:"
586 				    " status <0x%x>", status));
587 		return (status);
588 	}
589 
590 	NXGE_REG_RD64(handle, DEV_FUNC_SR_REG, &sr.value);
591 	sr.bits.ldw.sr |= (impl_sr << NPI_DEV_SR_IMPL_ST_SHIFT);
592 	NXGE_REG_WR64(handle, DEV_FUNC_SR_REG, sr.value);
593 
594 	return (npi_dev_func_sr_lock_free(handle));
595 }
596 
597 /*
598  * npi_dev_func_sr_sr_set_only():
599  *	This function is called to only set the shared register value.
600  * Parameters:
601  *	handle		- NPI handle
602  *	impl_sr		- shared value to set.
603  *
604  * Return:
605  *	NPI_SUCCESS		- If shared value is set successfully.
606  *
607  *	Error:
608  *	NPI_FAILURE
609  *		VIR_TAS_BUSY
610  */
611 
612 npi_status_t
613 npi_dev_func_sr_sr_set_only(npi_handle_t handle, uint16_t impl_sr)
614 {
615 	int		status = NPI_SUCCESS;
616 	dev_func_sr_t	sr;
617 
618 	NXGE_REG_RD64(handle, DEV_FUNC_SR_REG, &sr.value);
619 	/* must be the owner */
620 	if (sr.bits.ldw.funcid == NPI_GET_LOCK_OWNER(sr.bits.ldw.sr)) {
621 		sr.bits.ldw.sr |= (impl_sr << NPI_DEV_SR_IMPL_ST_SHIFT);
622 		NXGE_REG_WR64(handle, DEV_FUNC_SR_REG, sr.value);
623 	} else {
624 		NPI_DEBUG_MSG((handle.function, NPI_VIR_CTL,
625 				    " npi_dev_func_sr_sr_set_only"
626 				    " not owner <0x%x>",
627 				    sr.bits.ldw.sr));
628 		status = NPI_VIR_SR_NOTOWNER(sr.bits.ldw.funcid);
629 	}
630 
631 	return (status);
632 }
633 
634 /*
635  * npi_dev_func_sr_busy():
636  *	This function is called to see if we can own the device.
637  *	It will not reset the tas bit.
638  * Parameters:
639  *	handle		- NPI handle
640  *	busy_p		- pointer to store busy flag.
641  *				(B_TRUE: device is in use, B_FALSE: free).
642  * Return:
643  *	NPI_SUCCESS		- If tas bit is read successfully.
644  *	Error:
645  */
646 
647 npi_status_t
648 npi_dev_func_sr_busy(npi_handle_t handle, boolean_t *busy_p)
649 {
650 	dev_func_sr_t	sr;
651 
652 	NXGE_REG_RD64(handle, DEV_FUNC_SR_REG, &sr.value);
653 	if (!sr.bits.ldw.tas) {
654 		sr.bits.ldw.tas = 0;
655 		NXGE_REG_WR64(handle, DEV_FUNC_SR_REG, sr.value);
656 		*busy_p = B_FALSE;
657 	} else {
658 		/* Other function already owns it */
659 		*busy_p = B_TRUE;
660 	}
661 
662 	return (NPI_SUCCESS);
663 }
664 
665 /*
666  * npi_dev_func_sr_tas_get():
667  *	This function is called to get the tas bit
668  *	(after read, this bit is always set to 1, software write 0
669  *	 to clear it).
670  *
671  * Parameters:
672  *	handle		- NPI handle
673  *	tas_p		- pointer to store the tas value
674  *
675  * Return:
676  *	NPI_SUCCESS		- If tas value get is complete successfully.
677  *	Error:
678  */
679 
680 npi_status_t
681 npi_dev_func_sr_tas_get(npi_handle_t handle, uint8_t *tas_p)
682 {
683 	dev_func_sr_t		sr;
684 
685 	NXGE_REG_RD64(handle, DEV_FUNC_SR_REG, &sr.value);
686 	*tas_p = sr.bits.ldw.tas;
687 	if (!sr.bits.ldw.tas) {
688 		sr.bits.ldw.tas = 0;
689 		NXGE_REG_WR64(handle, DEV_FUNC_SR_REG, sr.value);
690 
691 	}
692 
693 	return (NPI_SUCCESS);
694 }
695 
696 /*
697  * npi_fzc_mpc_set():
698  *	This function is called to enable the write access
699  *	to FZC region to function zero.
700  * Parameters:
701  *	handle		- NPI handle
702  * Return:
703  *	NPI_SUCCESS	-
704  *	Error:
705  */
706 
707 npi_status_t
708 npi_fzc_mpc_set(npi_handle_t handle, boolean_t mpc)
709 {
710 	multi_part_ctl_t	mp;
711 
712 	mp.value = 0;
713 	if (mpc) {
714 		mp.bits.ldw.mpc = 1;
715 	}
716 	NXGE_REG_WR64(handle, MULTI_PART_CTL_REG, mp.value);
717 
718 	return (NPI_SUCCESS);
719 }
720 
721 /*
722  * npi_fzc_mpc_get():
723  *	This function is called to get the access mode.
724  * Parameters:
725  *	handle		- NPI handle
726  * Return:
727  *	NPI_SUCCESS	-
728  *
729  */
730 
731 npi_status_t
732 npi_fzc_mpc_get(npi_handle_t handle, boolean_t *mpc_p)
733 {
734 	multi_part_ctl_t	mpc;
735 
736 	mpc.value = 0;
737 	NXGE_REG_RD64(handle, MULTI_PART_CTL_REG, &mpc.value);
738 	*mpc_p = mpc.bits.ldw.mpc;
739 
740 	return (NPI_SUCCESS);
741 }
742 
743 /*
744  * npi_fzc_dma_bind_set():
745  *	This function is called to set DMA binding register.
746  * Parameters:
747  *	handle		- NPI handle
748  *	dma_bind	- NPI defined data structure that
749  *			  contains the tx/rx channel binding info.
750  *			  to set.
751  * Return:
752  *	NPI_SUCCESS	-
753  *	Error:
754  *	NPI_FAILURE
755  *
756  */
757 
758 npi_status_t
759 npi_fzc_dma_bind_set(npi_handle_t handle, fzc_dma_bind_t dma_bind)
760 {
761 	dma_bind_t	bind;
762 	int		status;
763 	uint8_t		fn, region, id, tn, rn;
764 
765 	fn = dma_bind.function_id;
766 	region = dma_bind.sub_vir_region;
767 	id = dma_bind.vir_index;
768 	tn = dma_bind.tx_channel;
769 	rn = dma_bind.rx_channel;
770 
771 	DMA_BIND_VADDR_VALIDATE(fn, region, id, status);
772 	if (status) {
773 		return (status);
774 	}
775 
776 	if (dma_bind.tx_bind) {
777 		DMA_BIND_TX_VALIDATE(tn, status);
778 		if (status) {
779 			return (status);
780 		}
781 	}
782 
783 	if (dma_bind.rx_bind) {
784 		DMA_BIND_RX_VALIDATE(rn, status);
785 		if (status) {
786 			return (status);
787 		}
788 	}
789 
790 	bind.value = 0;
791 	if (dma_bind.tx_bind) {
792 		bind.bits.ldw.tx_bind = 1;
793 		bind.bits.ldw.tx = tn;
794 	}
795 	if (dma_bind.rx_bind) {
796 		bind.bits.ldw.rx_bind = 1;
797 		bind.bits.ldw.rx = rn;
798 	}
799 
800 	NXGE_REG_WR64(handle, DMA_BIND_REG +
801 		DMA_BIND_REG_OFFSET(fn, rn, id), bind.value);
802 
803 	return (status);
804 }
805 
806 /*
807  * npi_fzc_ldg_num_set():
808  *	This function is called to set up a logical group number that
809  *	a logical device belongs to.
810  * Parameters:
811  *	handle		- NPI handle
812  *	ld		- logical device number (0 - 68)
813  *	ldg		- logical device group number (0 - 63)
814  * Return:
815  *	NPI_SUCCESS	-
816  *	Error:
817  *	NPI_FAILURE
818  *
819  */
820 
821 npi_status_t
822 npi_fzc_ldg_num_set(npi_handle_t handle, uint8_t ld, uint8_t ldg)
823 {
824 	ldg_num_t	gnum;
825 
826 	ASSERT(LD_VALID(ld));
827 	if (!LD_VALID(ld)) {
828 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
829 				    " npi_fzc_ldg_num_set"
830 				    "ld <0x%x>", ld));
831 		return (NPI_FAILURE | NPI_VIR_LD_INVALID(ld));
832 	}
833 
834 	ASSERT(LDG_VALID(ldg));
835 	if (!LDG_VALID(ldg)) {
836 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
837 				    " npi_fzc_ldg_num_set"
838 				    " ldg <0x%x>", ldg));
839 		return (NPI_FAILURE | NPI_VIR_LDG_INVALID(ld));
840 	}
841 
842 	gnum.value = 0;
843 	gnum.bits.ldw.num = ldg;
844 
845 	NXGE_REG_WR64(handle, LDG_NUM_REG + LD_NUM_OFFSET(ld),
846 		gnum.value);
847 
848 	return (NPI_SUCCESS);
849 }
850 
851 /*
852  * npi_fzc_ldg_num_get():
853  *	This function is called to get the logical device group that
854  *	a logical device belongs to.
855  * Parameters:
856  *	handle		- NPI handle
857  *	ld		- logical device number (0 - 68)
858  *	*ldg_p		- pointer to store its group number.
859  * Return:
860  *	NPI_SUCCESS	-
861  *	Error:
862  *	NPI_FAILURE
863  */
864 
865 npi_status_t
866 npi_fzc_ldg_num_get(npi_handle_t handle, uint8_t ld, uint8_t *ldg_p)
867 {
868 	uint64_t val;
869 
870 	ASSERT(LD_VALID(ld));
871 	if (!LD_VALID(ld)) {
872 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
873 				    " npi_fzc_ldg_num_get"
874 				    " Invalid Input:",
875 				    " ld <0x%x>", ld));
876 		return (NPI_FAILURE | NPI_VIR_LD_INVALID(ld));
877 	}
878 
879 	NXGE_REG_RD64(handle, LDG_NUM_REG + LD_NUM_OFFSET(ld), &val);
880 
881 	*ldg_p = (uint8_t)(val & LDG_NUM_NUM_MASK);
882 
883 	return (NPI_SUCCESS);
884 }
885 
886 /*
887  * npi_ldsv_ldfs_get():
888  *	This function is called to get device state vectors.
889  * Parameters:
890  *	handle		- NPI handle
891  *	ldg		- logical device group (0 - 63)
892  *	*ldf_p		- pointer to store ldf0 and ldf1 flag bits.
893  * Return:
894  *	NPI_SUCCESS	-
895  *	Error:
896  *	NPI_FAILURE
897  */
898 
899 npi_status_t
900 npi_ldsv_ldfs_get(npi_handle_t handle, uint8_t ldg, uint64_t *vector0_p,
901 	uint64_t *vector1_p, uint64_t *vector2_p)
902 {
903 	int	status;
904 
905 	if ((status = npi_ldsv_get(handle, ldg, VECTOR0, vector0_p))) {
906 		return (status);
907 	}
908 	if ((status = npi_ldsv_get(handle, ldg, VECTOR1, vector1_p))) {
909 		return (status);
910 	}
911 	if ((status = npi_ldsv_get(handle, ldg, VECTOR2, vector2_p))) {
912 		return (status);
913 	}
914 
915 	return (NPI_SUCCESS);
916 }
917 
918 /*
919  * npi_ldsv_get():
920  *	This function is called to get device state vectors.
921  * Parameters:
922  *	handle		- NPI handle
923  *	ldg		- logical device group (0 - 63)
924  *	ldf_type	- either LDF0 (0) or LDF1 (1)
925  *	vector		- vector type (0, 1 or 2)
926  *	*ldf_p		- pointer to store its flag bits.
927  * Return:
928  *	NPI_SUCCESS	-
929  *	Error:
930  *	NPI_FAILURE
931  */
932 
933 npi_status_t
934 npi_ldsv_get(npi_handle_t handle, uint8_t ldg, ldsv_type_t vector,
935 	uint64_t *ldf_p)
936 {
937 	uint64_t		offset;
938 
939 	ASSERT(LDG_VALID(ldg));
940 	if (!LDG_VALID(ldg)) {
941 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
942 				    " npi_ldsv_get"
943 				    " Invalid Input "
944 				    " ldg <0x%x>", ldg));
945 		return (NPI_FAILURE | NPI_VIR_LDG_INVALID(ldg));
946 	}
947 
948 	switch (vector) {
949 	case VECTOR0:
950 		offset = LDSV0_REG + LDSV_OFFSET(ldg);
951 		break;
952 
953 	case VECTOR1:
954 		offset = LDSV1_REG + LDSV_OFFSET(ldg);
955 		break;
956 
957 	case VECTOR2:
958 		offset = LDSV2_REG + LDSV_OFFSET(ldg);
959 		break;
960 
961 	default:
962 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
963 				    " npi_ldsv_get"
964 				    " Invalid Input: "
965 				    " ldsv type <0x%x>", vector));
966 		return (NPI_FAILURE | NPI_VIR_LDSV_INVALID(vector));
967 	}
968 
969 	NXGE_REG_RD64(handle, offset, ldf_p);
970 
971 	return (NPI_SUCCESS);
972 }
973 
974 /*
975  * npi_ldsv_ld_get():
976  *	This function is called to get the flag bit value of a device.
977  * Parameters:
978  *	handle		- NPI handle
979  *	ldg		- logical device group (0 - 63)
980  *	ld		- logical device (0 - 68)
981  *	ldf_type	- either LDF0 (0) or LDF1 (1)
982  *	vector		- vector type (0, 1 or 2)
983  *	*ldf_p		- pointer to store its flag bits.
984  * Return:
985  *	NPI_SUCCESS	-
986  *	Error:
987  *	NPI_FAILURE
988  */
989 
990 npi_status_t
991 npi_ldsv_ld_get(npi_handle_t handle, uint8_t ldg, uint8_t ld,
992 	ldsv_type_t vector, ldf_type_t ldf_type, boolean_t *flag_p)
993 {
994 	uint64_t		sv;
995 	uint64_t		offset;
996 
997 	ASSERT(LDG_VALID(ldg));
998 	if (!LDG_VALID(ldg)) {
999 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1000 				    " npi_ldsv_ld_get"
1001 				    " Invalid Input: "
1002 				    " ldg <0x%x>", ldg));
1003 		return (NPI_FAILURE | NPI_VIR_LDG_INVALID(ldg));
1004 	}
1005 	ASSERT((LD_VALID(ld)) &&	\
1006 		((vector != VECTOR2) || (ld >= NXGE_MAC_LD_START)));
1007 	if (!LD_VALID(ld)) {
1008 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1009 				    " npi_ldsv_ld_get Invalid Input: "
1010 				    " ld <9x%x>", ld));
1011 		return (NPI_FAILURE | NPI_VIR_LD_INVALID(ld));
1012 	} else if (vector == VECTOR2 && ld < NXGE_MAC_LD_START) {
1013 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1014 				    " npi_ldsv_ld_get Invalid Input:"
1015 				    " ld-vector2 <0x%x>", ld));
1016 		return (NPI_FAILURE | NPI_VIR_LD_INVALID(ld));
1017 	}
1018 
1019 	switch (vector) {
1020 	case VECTOR0:
1021 		offset = LDSV0_REG + LDSV_OFFSET(ldg);
1022 		break;
1023 
1024 	case VECTOR1:
1025 		offset = LDSV1_REG + LDSV_OFFSET(ldg);
1026 		break;
1027 
1028 	case VECTOR2:
1029 		offset = LDSV2_REG + LDSV_OFFSET(ldg);
1030 
1031 	default:
1032 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL, "npi_ldsv_get"
1033 			"ldsv", vector));
1034 		return (NPI_FAILURE | NPI_VIR_LDSV_INVALID(vector));
1035 	}
1036 
1037 	NXGE_REG_RD64(handle, offset, &sv);
1038 	if (vector != VECTOR2) {
1039 		*flag_p = ((sv >> ld) & LDSV_MASK_ALL);
1040 	} else {
1041 		if (ldf_type) {
1042 			*flag_p = (((sv >> LDSV2_LDF1_SHIFT) >>
1043 				(ld - NXGE_MAC_LD_START)) & LDSV_MASK_ALL);
1044 		} else {
1045 			*flag_p = (((sv >> LDSV2_LDF0_SHIFT) >>
1046 				(ld - NXGE_MAC_LD_START)) & LDSV_MASK_ALL);
1047 		}
1048 	}
1049 
1050 	return (NPI_SUCCESS);
1051 }
1052 
1053 /*
1054  * npi_ldsv_ld_ldf0_get():
1055  *	This function is called to get the ldf0 bit value of a device.
1056  * Parameters:
1057  *	handle		- NPI handle
1058  *	ldg		- logical device group (0 - 63)
1059  *	ld		- logical device (0 - 68)
1060  *	*ldf_p		- pointer to store its flag bits.
1061  * Return:
1062  *	NPI_SUCCESS	-
1063  *	Error:
1064  *	NPI_FAILURE
1065  */
1066 
1067 npi_status_t
1068 npi_ldsv_ld_ldf0_get(npi_handle_t handle, uint8_t ldg, uint8_t ld,
1069 	boolean_t *flag_p)
1070 {
1071 	ldsv_type_t vector;
1072 
1073 	if (ld >= NXGE_MAC_LD_START) {
1074 		vector = VECTOR2;
1075 	}
1076 
1077 	return (npi_ldsv_ld_get(handle, ldg, ld, vector, LDF0, flag_p));
1078 }
1079 
1080 /*
1081  * npi_ldsv_ld_ldf1_get():
1082  *	This function is called to get the ldf1 bit value of a device.
1083  * Parameters:
1084  *	handle		- NPI handle
1085  *	ldg		- logical device group (0 - 63)
1086  *	ld		- logical device (0 - 68)
1087  *	*ldf_p		- pointer to store its flag bits.
1088  * Return:
1089  *	NPI_SUCCESS	-
1090  *	Error:
1091  *	NPI_FAILURE
1092  */
1093 
1094 npi_status_t
1095 npi_ldsv_ld_ldf1_get(npi_handle_t handle, uint8_t ldg, uint8_t ld,
1096 		boolean_t *flag_p)
1097 {
1098 	ldsv_type_t vector;
1099 
1100 	if (ld >= NXGE_MAC_LD_START) {
1101 		vector = VECTOR2;
1102 	}
1103 
1104 	return (npi_ldsv_ld_get(handle, ldg, ld, vector, LDF1, flag_p));
1105 }
1106 
1107 /*
1108  * npi_intr_mask_set():
1109  *	This function is called to select the mask bits for both ldf0 and ldf1.
1110  * Parameters:
1111  *	handle		- NPI handle
1112  *	ld		- logical device (0 - 68)
1113  *	ldf_mask	- mask value to set (both ldf0 and ldf1).
1114  * Return:
1115  *	NPI_SUCCESS	-
1116  *	Error:
1117  *	NPI_FAILURE
1118  */
1119 
1120 npi_status_t
1121 npi_intr_mask_set(npi_handle_t handle, uint8_t ld, uint8_t ldf_mask)
1122 {
1123 	uint64_t		offset;
1124 
1125 	ASSERT(LD_VALID(ld));
1126 	if (!LD_VALID(ld)) {
1127 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1128 			    " npi_intr_mask_set ld", ld));
1129 		return (NPI_FAILURE | NPI_VIR_LD_INVALID(ld));
1130 	}
1131 
1132 	ldf_mask &= LD_IM0_MASK;
1133 	offset = LDSV_OFFSET_MASK(ld);
1134 
1135 	NPI_DEBUG_MSG((handle.function, NPI_VIR_CTL,
1136 		"npi_intr_mask_set: ld %d "
1137 		" offset 0x%0llx "
1138 		" mask 0x%x",
1139 		ld, offset, ldf_mask));
1140 
1141 	NXGE_REG_WR64(handle, offset, (uint64_t)ldf_mask);
1142 
1143 	return (NPI_SUCCESS);
1144 }
1145 
1146 /*
1147  * npi_intr_mask_get():
1148  *	This function is called to get the mask bits.
1149  * Parameters:
1150  *	handle		- NPI handle
1151  *	ld		- logical device (0 - 68)
1152  *	ldf_mask	- pointer to store mask bits info.
1153  * Return:
1154  *	NPI_SUCCESS	-
1155  *	Error:
1156  *	NPI_FAILURE
1157  */
1158 npi_status_t
1159 npi_intr_mask_get(npi_handle_t handle, uint8_t ld, uint8_t *ldf_mask_p)
1160 {
1161 	uint64_t		offset;
1162 	uint64_t		val;
1163 
1164 	ASSERT(LD_VALID(ld));
1165 	if (!LD_VALID(ld)) {
1166 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1167 			    " npi_intr_mask_get ld", ld));
1168 		return (NPI_FAILURE | NPI_VIR_LD_INVALID(ld));
1169 	}
1170 
1171 	offset = LDSV_OFFSET_MASK(ld);
1172 
1173 	NXGE_REG_RD64(handle, offset, &val);
1174 
1175 	*ldf_mask_p = (uint8_t)(val & LD_IM_MASK);
1176 
1177 	return (NPI_SUCCESS);
1178 }
1179 
1180 /*
1181  * npi_intr_ldg_mgmt_set():
1182  *	This function is called to set interrupt timer and arm bit.
1183  * Parameters:
1184  *	handle		- NPI handle
1185  *	ldg		- logical device group (0 - 63)
1186  *	arm		- B_TRUE (arm) B_FALSE (disable)
1187  * Return:
1188  *	NPI_SUCCESS	-
1189  *	Error:
1190  *	NPI_FAILURE
1191  */
1192 
1193 npi_status_t
1194 npi_intr_ldg_mgmt_set(npi_handle_t handle, uint8_t ldg, boolean_t arm,
1195 			uint8_t timer)
1196 {
1197 	ldgimgm_t		mgm;
1198 	uint64_t		val;
1199 
1200 	ASSERT((LDG_VALID(ldg)) && (LD_INTTIMER_VALID(timer)));
1201 	if (!LDG_VALID(ldg)) {
1202 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1203 				    " npi_intr_ldg_mgmt_set"
1204 				    " Invalid Input: "
1205 				    " ldg <0x%x>", ldg));
1206 		return (NPI_FAILURE | NPI_VIR_LDG_INVALID(ldg));
1207 	}
1208 	if (!LD_INTTIMER_VALID(timer)) {
1209 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1210 				    " npi_intr_ldg_mgmt_set Invalid Input"
1211 				    " timer <0x%x>", timer));
1212 		return (NPI_FAILURE | NPI_VIR_INTM_TM_INVALID(ldg));
1213 	}
1214 
1215 	if (arm) {
1216 		mgm.bits.ldw.arm = 1;
1217 	} else {
1218 		NXGE_REG_RD64(handle, LDGIMGN_REG + LDSV_OFFSET(ldg), &val);
1219 		mgm.value = val & LDGIMGM_ARM_MASK;
1220 	}
1221 
1222 	mgm.bits.ldw.timer = timer;
1223 	NXGE_REG_WR64(handle, LDGIMGN_REG + LDSV_OFFSET(ldg),
1224 		mgm.value);
1225 
1226 	NPI_DEBUG_MSG((handle.function, NPI_VIR_CTL,
1227 		" npi_intr_ldg_mgmt_set: ldg %d"
1228 		" reg offset 0x%x",
1229 		ldg, LDGIMGN_REG + LDSV_OFFSET(ldg)));
1230 
1231 	return (NPI_SUCCESS);
1232 }
1233 
1234 /*
1235  * npi_intr_ldg_mgmt_timer_get():
1236  *	This function is called to get the timer counter
1237  * Parameters:
1238  *	handle		- NPI handle
1239  *	ldg		- logical device group (0 - 63)
1240  *	timer_p		- pointer to store the timer counter.
1241  * Return:
1242  *	NPI_SUCCESS	-
1243  *	Error:
1244  *	NPI_FAILURE
1245  */
1246 
1247 npi_status_t
1248 npi_intr_ldg_mgmt_timer_get(npi_handle_t handle, uint8_t ldg, uint8_t *timer_p)
1249 {
1250 	uint64_t val;
1251 
1252 	ASSERT(LDG_VALID(ldg));
1253 	if (!LDG_VALID(ldg)) {
1254 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1255 				    " npi_intr_ldg_mgmt_timer_get"
1256 				    " Invalid Input: ldg <0x%x>", ldg));
1257 		return (NPI_FAILURE | NPI_VIR_LDG_INVALID(ldg));
1258 	}
1259 
1260 	NXGE_REG_RD64(handle, LDGIMGN_REG + LDSV_OFFSET(ldg), &val);
1261 
1262 	*timer_p = (uint8_t)(val & LDGIMGM_TIMER_MASK);
1263 
1264 	NPI_DEBUG_MSG((handle.function, NPI_VIR_CTL,
1265 		" npi_intr_ldg_mgmt_timer_get: ldg %d"
1266 		" reg offset 0x%x",
1267 		ldg, LDGIMGN_REG + LDSV_OFFSET(ldg)));
1268 
1269 	return (NPI_SUCCESS);
1270 }
1271 
1272 /*
1273  * npi_intr_ldg_mgmt_arm():
1274  *	This function is called to arm the group.
1275  * Parameters:
1276  *	handle		- NPI handle
1277  *	ldg		- logical device group (0 - 63)
1278  * Return:
1279  *	NPI_SUCCESS	-
1280  *	Error:
1281  *	NPI_FAILURE
1282  */
1283 
1284 npi_status_t
1285 npi_intr_ldg_mgmt_arm(npi_handle_t handle, uint8_t ldg)
1286 {
1287 	ldgimgm_t		mgm;
1288 
1289 	ASSERT(LDG_VALID(ldg));
1290 	if (!LDG_VALID(ldg)) {
1291 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1292 				    " npi_intr_ldg_mgmt_arm"
1293 				    " Invalid Input: ldg <0x%x>",
1294 				    ldg));
1295 		return (NPI_FAILURE | NPI_VIR_LDG_INVALID(ldg));
1296 	}
1297 
1298 	NXGE_REG_RD64(handle, (LDGIMGN_REG + LDSV_OFFSET(ldg)), &mgm.value);
1299 	mgm.bits.ldw.arm = 1;
1300 
1301 	NXGE_REG_WR64(handle, LDGIMGN_REG + LDSV_OFFSET(ldg),
1302 			mgm.value);
1303 	NPI_DEBUG_MSG((handle.function, NPI_VIR_CTL,
1304 		" npi_intr_ldg_mgmt_arm: ldg %d"
1305 		" reg offset 0x%x",
1306 		ldg, LDGIMGN_REG + LDSV_OFFSET(ldg)));
1307 
1308 	return (NPI_SUCCESS);
1309 }
1310 
1311 /*
1312  * npi_fzc_ldg_timer_res_set():
1313  *	This function is called to set the timer resolution.
1314  * Parameters:
1315  *	handle		- NPI handle
1316  *	res		- timer resolution (# of system clocks)
1317  * Return:
1318  *	NPI_SUCCESS	-
1319  *	Error:
1320  *	NPI_FAILURE
1321  */
1322 
1323 npi_status_t
1324 npi_fzc_ldg_timer_res_set(npi_handle_t handle, uint32_t res)
1325 {
1326 	ASSERT(res <= LDGTITMRES_RES_MASK);
1327 	if (res > LDGTITMRES_RES_MASK) {
1328 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1329 				    " npi_fzc_ldg_timer_res_set"
1330 				    " Invalid Input: res <0x%x>",
1331 				    res));
1332 		return (NPI_FAILURE | NPI_VIR_TM_RES_INVALID);
1333 	}
1334 
1335 	NXGE_REG_WR64(handle, LDGITMRES_REG, (res & LDGTITMRES_RES_MASK));
1336 
1337 	return (NPI_SUCCESS);
1338 }
1339 
1340 /*
1341  * npi_fzc_ldg_timer_res_get():
1342  *	This function is called to get the timer resolution.
1343  * Parameters:
1344  *	handle		- NPI handle
1345  *	res_p		- pointer to store the timer resolution.
1346  * Return:
1347  *	NPI_SUCCESS	-
1348  *	Error:
1349  *	NPI_FAILURE
1350  */
1351 
1352 npi_status_t
1353 npi_fzc_ldg_timer_res_get(npi_handle_t handle, uint8_t *res_p)
1354 {
1355 	uint64_t val;
1356 
1357 	NXGE_REG_RD64(handle, LDGITMRES_REG, &val);
1358 
1359 	*res_p = (uint8_t)(val & LDGIMGM_TIMER_MASK);
1360 
1361 	return (NPI_SUCCESS);
1362 }
1363 
1364 /*
1365  * npi_fzc_sid_set():
1366  *	This function is called to set the system interrupt data.
1367  * Parameters:
1368  *	handle		- NPI handle
1369  *	ldg		- logical group (0 - 63)
1370  *	sid		- NPI defined data to set
1371  * Return:
1372  *	NPI_SUCCESS	-
1373  *	Error:
1374  *	NPI_FAILURE
1375  */
1376 
1377 npi_status_t
1378 npi_fzc_sid_set(npi_handle_t handle, fzc_sid_t sid)
1379 {
1380 	sid_t		sd;
1381 
1382 	ASSERT(LDG_VALID(sid.ldg));
1383 	if (!LDG_VALID(sid.ldg)) {
1384 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1385 				    " npi_fzc_sid_set"
1386 				    " Invalid Input: ldg <0x%x>",
1387 				    sid.ldg));
1388 		return (NPI_FAILURE | NPI_VIR_LDG_INVALID(sid.ldg));
1389 	}
1390 	if (!sid.niu) {
1391 		ASSERT(FUNC_VALID(sid.func));
1392 		if (!FUNC_VALID(sid.func)) {
1393 			NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1394 					    " npi_fzc_sid_set"
1395 					    " Invalid Input: func <0x%x>",
1396 					    sid.func));
1397 			NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1398 				"invalid FUNC: npi_fzc_sid_set(%d)", sid.func));
1399 			return (NPI_FAILURE | NPI_VIR_FUNC_INVALID(sid.func));
1400 		}
1401 
1402 		ASSERT(SID_VECTOR_VALID(sid.vector));
1403 		if (!SID_VECTOR_VALID(sid.vector)) {
1404 			NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1405 					    " npi_fzc_sid_set"
1406 					    " Invalid Input: vector <0x%x>",
1407 					    sid.vector));
1408 			NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1409 				    " invalid VECTOR: npi_fzc_sid_set(%d)",
1410 				    sid.vector));
1411 			return (NPI_FAILURE |
1412 				NPI_VIR_SID_VEC_INVALID(sid.vector));
1413 		}
1414 	}
1415 	sd.value = 0;
1416 	if (!sid.niu) {
1417 		sd.bits.ldw.data = ((sid.func << SID_DATA_FUNCNUM_SHIFT) |
1418 				(sid.vector & SID_DATA_INTNUM_MASK));
1419 	}
1420 
1421 	NPI_DEBUG_MSG((handle.function, NPI_VIR_CTL,
1422 	    " npi_fzc_sid_set: group %d 0x%llx", sid.ldg, sd.value));
1423 
1424 	NXGE_REG_WR64(handle,  SID_REG + LDG_SID_OFFSET(sid.ldg), sd.value);
1425 
1426 	return (NPI_SUCCESS);
1427 }
1428 
1429 /*
1430  * npi_fzc_sid_get():
1431  *	This function is called to get the system interrupt data.
1432  * Parameters:
1433  *	handle		- NPI handle
1434  *	ldg		- logical group (0 - 63)
1435  *	sid_p		- NPI defined data to get
1436  * Return:
1437  *	NPI_SUCCESS	-
1438  *	Error:
1439  *	NPI_FAILURE
1440  */
1441 
1442 npi_status_t
1443 npi_fzc_sid_get(npi_handle_t handle, p_fzc_sid_t sid_p)
1444 {
1445 	sid_t		sd;
1446 
1447 	ASSERT(LDG_VALID(sid_p->ldg));
1448 	if (!LDG_VALID(sid_p->ldg)) {
1449 		NPI_ERROR_MSG((handle.function, NPI_ERR_CTL,
1450 				    " npi_fzc_sid_get"
1451 				    " Invalid Input: ldg <0x%x>",
1452 				    sid_p->ldg));
1453 		return (NPI_FAILURE | NPI_VIR_LDG_INVALID(sid_p->ldg));
1454 	}
1455 	NXGE_REG_RD64(handle, (SID_REG + LDG_SID_OFFSET(sid_p->ldg)),
1456 		&sd.value);
1457 	if (!sid_p->niu) {
1458 		sid_p->func = ((sd.bits.ldw.data & SID_DATA_FUNCNUM_MASK) >>
1459 			SID_DATA_FUNCNUM_SHIFT);
1460 		sid_p->vector = ((sd.bits.ldw.data & SID_DATA_INTNUM_MASK) >>
1461 			SID_DATA_INTNUM_SHIFT);
1462 	} else {
1463 		sid_p->vector = (sd.value & SID_DATA_MASK);
1464 	}
1465 
1466 	return (NPI_SUCCESS);
1467 }
1468 
1469 /*
1470  * npi_fzc_sys_err_mask_set():
1471  *	This function is called to mask/unmask the device error mask bits.
1472  *
1473  * Parameters:
1474  *	handle		- NPI handle
1475  *	mask		- set bit mapped mask
1476  * Return:
1477  *	NPI_SUCCESS	-
1478  *	Error:
1479  *	NPI_FAILURE
1480  */
1481 
1482 npi_status_t
1483 npi_fzc_sys_err_mask_set(npi_handle_t handle, uint64_t mask)
1484 {
1485 	NXGE_REG_WR64(handle,  SYS_ERR_MASK_REG, mask);
1486 	return (NPI_SUCCESS);
1487 }
1488 
1489 /*
1490  * npi_fzc_sys_err_stat_get():
1491  *	This function is called to get the system error stats.
1492  *
1493  * Parameters:
1494  *	handle		- NPI handle
1495  *	err_stat	- sys_err_stat structure to hold stats.
1496  * Return:
1497  *	NPI_SUCCESS	-
1498  *	Error:
1499  *	NPI_FAILURE
1500  */
1501 
1502 npi_status_t
1503 npi_fzc_sys_err_stat_get(npi_handle_t handle, p_sys_err_stat_t statp)
1504 {
1505 	NXGE_REG_RD64(handle,  SYS_ERR_STAT_REG, &statp->value);
1506 	return (NPI_SUCCESS);
1507 }
1508 
1509 npi_status_t
1510 npi_fzc_rst_ctl_get(npi_handle_t handle, p_rst_ctl_t rstp)
1511 {
1512 	NXGE_REG_RD64(handle, RST_CTL_REG, &rstp->value);
1513 
1514 	return (NPI_SUCCESS);
1515 }
1516 
1517 /*
1518  * npi_fzc_mpc_get():
1519  *	This function is called to get the access mode.
1520  * Parameters:
1521  *	handle		- NPI handle
1522  * Return:
1523  *	NPI_SUCCESS	-
1524  *
1525  */
1526 
1527 npi_status_t
1528 npi_fzc_rst_ctl_reset_mac(npi_handle_t handle, uint8_t port)
1529 {
1530 	rst_ctl_t 		rst;
1531 
1532 	rst.value = 0;
1533 	NXGE_REG_RD64(handle, RST_CTL_REG, &rst.value);
1534 	rst.value |= (1 << (RST_CTL_MAC_RST0_SHIFT + port));
1535 	NXGE_REG_WR64(handle, RST_CTL_REG, rst.value);
1536 
1537 	return (NPI_SUCCESS);
1538 }
1539