xref: /onnv-gate/usr/src/uts/sun4v/os/mach_ddi_impl.c (revision 11596:e9010337bcd3)
10Sstevel@tonic-gate /*
20Sstevel@tonic-gate  * CDDL HEADER START
30Sstevel@tonic-gate  *
40Sstevel@tonic-gate  * The contents of this file are subject to the terms of the
5*11596SJason.Beloro@Sun.COM  * Common Development and Distribution License (the "License").
6*11596SJason.Beloro@Sun.COM  * You may not use this file except in compliance with the License.
70Sstevel@tonic-gate  *
80Sstevel@tonic-gate  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
90Sstevel@tonic-gate  * or http://www.opensolaris.org/os/licensing.
100Sstevel@tonic-gate  * See the License for the specific language governing permissions
110Sstevel@tonic-gate  * and limitations under the License.
120Sstevel@tonic-gate  *
130Sstevel@tonic-gate  * When distributing Covered Code, include this CDDL HEADER in each
140Sstevel@tonic-gate  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
150Sstevel@tonic-gate  * If applicable, add the following below this CDDL HEADER, with the
160Sstevel@tonic-gate  * fields enclosed by brackets "[]" replaced with your own identifying
170Sstevel@tonic-gate  * information: Portions Copyright [yyyy] [name of copyright owner]
180Sstevel@tonic-gate  *
190Sstevel@tonic-gate  * CDDL HEADER END
200Sstevel@tonic-gate  */
210Sstevel@tonic-gate /*
22*11596SJason.Beloro@Sun.COM  * Copyright 2010 Sun Microsystems, Inc.  All rights reserved.
230Sstevel@tonic-gate  * Use is subject to license terms.
240Sstevel@tonic-gate  */
250Sstevel@tonic-gate 
260Sstevel@tonic-gate /*
270Sstevel@tonic-gate  * sun4u specific DDI implementation
280Sstevel@tonic-gate  */
290Sstevel@tonic-gate #include <sys/bootconf.h>
300Sstevel@tonic-gate #include <sys/conf.h>
310Sstevel@tonic-gate #include <sys/machsystm.h>
320Sstevel@tonic-gate #include <sys/idprom.h>
330Sstevel@tonic-gate #include <sys/promif.h>
340Sstevel@tonic-gate 
350Sstevel@tonic-gate 
360Sstevel@tonic-gate /*
370Sstevel@tonic-gate  * Favored drivers of this implementation
380Sstevel@tonic-gate  * architecture.  These drivers MUST be present for
390Sstevel@tonic-gate  * the system to boot at all.
400Sstevel@tonic-gate  */
410Sstevel@tonic-gate char *impl_module_list[] = {
420Sstevel@tonic-gate 	"rootnex",
430Sstevel@tonic-gate 	"options",
440Sstevel@tonic-gate 	"sad",		/* Referenced via init_tbl[] */
450Sstevel@tonic-gate 	"pseudo",
460Sstevel@tonic-gate 	"clone",
470Sstevel@tonic-gate 	"scsi_vhci",
480Sstevel@tonic-gate 	(char *)0
490Sstevel@tonic-gate };
500Sstevel@tonic-gate 
510Sstevel@tonic-gate /*
520Sstevel@tonic-gate  * Check the status of the device node passed as an argument.
530Sstevel@tonic-gate  *
540Sstevel@tonic-gate  *	if ((status is OKAY) || (status is DISABLED))
550Sstevel@tonic-gate  *		return DDI_SUCCESS
560Sstevel@tonic-gate  *	else
570Sstevel@tonic-gate  *		print a warning and return DDI_FAILURE
580Sstevel@tonic-gate  */
590Sstevel@tonic-gate /*ARGSUSED*/
600Sstevel@tonic-gate int
check_status(int id,char * buf,dev_info_t * parent)610Sstevel@tonic-gate check_status(int id, char *buf, dev_info_t *parent)
620Sstevel@tonic-gate {
630Sstevel@tonic-gate 	char status_buf[64];
640Sstevel@tonic-gate 	extern int status_okay(int, char *, int);
650Sstevel@tonic-gate 
660Sstevel@tonic-gate 	/*
670Sstevel@tonic-gate 	 * is the status okay?
680Sstevel@tonic-gate 	 */
690Sstevel@tonic-gate 	if (status_okay(id, status_buf, sizeof (status_buf)))
700Sstevel@tonic-gate 		return (DDI_SUCCESS);
710Sstevel@tonic-gate 
720Sstevel@tonic-gate 	return (DDI_FAILURE);
730Sstevel@tonic-gate }
74*11596SJason.Beloro@Sun.COM 
75*11596SJason.Beloro@Sun.COM /*
76*11596SJason.Beloro@Sun.COM  * For Devices which are assigned to another logical domain, the
77*11596SJason.Beloro@Sun.COM  * firmware modifies the various PCI properties so that no
78*11596SJason.Beloro@Sun.COM  * driver will attach in the case where the OS instances does not
79*11596SJason.Beloro@Sun.COM  * support ldoms direct I/O.  Since we do not support it, we can
80*11596SJason.Beloro@Sun.COM  * restore those properties to their expected values.
81*11596SJason.Beloro@Sun.COM  * See FWARC/2009/535.
82*11596SJason.Beloro@Sun.COM  */
83*11596SJason.Beloro@Sun.COM /*ARGSUSED*/
84*11596SJason.Beloro@Sun.COM void
translate_devid(dev_info_t * dip)85*11596SJason.Beloro@Sun.COM translate_devid(dev_info_t *dip)
86*11596SJason.Beloro@Sun.COM {
87*11596SJason.Beloro@Sun.COM 	int devid, venid, ssid, ssvid, rev, class_code;
88*11596SJason.Beloro@Sun.COM 	char *new_compat[7];
89*11596SJason.Beloro@Sun.COM 	int i;
90*11596SJason.Beloro@Sun.COM 	int compat_entry_length = 30;
91*11596SJason.Beloro@Sun.COM 	int ncompat = 7;
92*11596SJason.Beloro@Sun.COM 
93*11596SJason.Beloro@Sun.COM 	if ((devid = ddi_prop_get_int(DDI_DEV_T_ANY, dip, DDI_PROP_DONTPASS,
94*11596SJason.Beloro@Sun.COM 	    "real-device-id", -1)) == -1)
95*11596SJason.Beloro@Sun.COM 		return;
96*11596SJason.Beloro@Sun.COM 	if ((venid = ddi_prop_get_int(DDI_DEV_T_ANY, dip, DDI_PROP_DONTPASS,
97*11596SJason.Beloro@Sun.COM 	    "real-vendor-id", -1)) == -1)
98*11596SJason.Beloro@Sun.COM 		return;
99*11596SJason.Beloro@Sun.COM 
100*11596SJason.Beloro@Sun.COM 	(void) ddi_prop_update_int(DDI_DEV_T_NONE, dip, "device-id", devid);
101*11596SJason.Beloro@Sun.COM 	(void) ddi_prop_update_int(DDI_DEV_T_NONE, dip, "vendor-id", venid);
102*11596SJason.Beloro@Sun.COM 
103*11596SJason.Beloro@Sun.COM 	class_code = ddi_prop_get_int(DDI_DEV_T_ANY, dip, DDI_PROP_DONTPASS,
104*11596SJason.Beloro@Sun.COM 	    "real-class-code", 0);
105*11596SJason.Beloro@Sun.COM 	(void) ddi_prop_update_int(DDI_DEV_T_NONE, dip, "class-clode",
106*11596SJason.Beloro@Sun.COM 	    class_code);
107*11596SJason.Beloro@Sun.COM 
108*11596SJason.Beloro@Sun.COM 	ssvid = ddi_prop_get_int(DDI_DEV_T_ANY, dip, DDI_PROP_DONTPASS,
109*11596SJason.Beloro@Sun.COM 	    "real-subsystem-vendor-id", -1);
110*11596SJason.Beloro@Sun.COM 	if (ssvid != -1)
111*11596SJason.Beloro@Sun.COM 		(void) ddi_prop_update_int(DDI_DEV_T_NONE, dip,
112*11596SJason.Beloro@Sun.COM 		    "subsystem-vendor-id", ssvid);
113*11596SJason.Beloro@Sun.COM 
114*11596SJason.Beloro@Sun.COM 	ssid = ddi_prop_get_int(DDI_DEV_T_ANY, dip, DDI_PROP_DONTPASS,
115*11596SJason.Beloro@Sun.COM 	    "real-subsystem-id", -1);
116*11596SJason.Beloro@Sun.COM 	if (ssid != -1)
117*11596SJason.Beloro@Sun.COM 		(void) ddi_prop_update_int(DDI_DEV_T_NONE, dip, "subsystem-id",
118*11596SJason.Beloro@Sun.COM 		    ssid);
119*11596SJason.Beloro@Sun.COM 
120*11596SJason.Beloro@Sun.COM 	rev = ddi_prop_get_int(DDI_DEV_T_ANY, dip, DDI_PROP_DONTPASS,
121*11596SJason.Beloro@Sun.COM 	    "real-revision-id", 0);
122*11596SJason.Beloro@Sun.COM 	(void) ddi_prop_update_int(DDI_DEV_T_NONE, dip, "revision-id", rev);
123*11596SJason.Beloro@Sun.COM 
124*11596SJason.Beloro@Sun.COM 	for (i = 0; i < ncompat; ++i) {
125*11596SJason.Beloro@Sun.COM 		new_compat[i] = kmem_zalloc(compat_entry_length, KM_NOSLEEP);
126*11596SJason.Beloro@Sun.COM 		if (new_compat[i] == NULL) {
127*11596SJason.Beloro@Sun.COM 			cmn_err(CE_WARN, "translate_devid: kmem_alloc "
128*11596SJason.Beloro@Sun.COM 			    "failed\n");
129*11596SJason.Beloro@Sun.COM 			ncompat = i;
130*11596SJason.Beloro@Sun.COM 			goto cleanup;
131*11596SJason.Beloro@Sun.COM 		}
132*11596SJason.Beloro@Sun.COM 	}
133*11596SJason.Beloro@Sun.COM 
134*11596SJason.Beloro@Sun.COM 	(void) sprintf(new_compat[0], "pciex%x,%x.%x.%x.%x",
135*11596SJason.Beloro@Sun.COM 	    venid, devid, ssvid, ssid, rev);
136*11596SJason.Beloro@Sun.COM 	(void) sprintf(new_compat[1], "pciex%x,%x.%x.%x",
137*11596SJason.Beloro@Sun.COM 	    venid, devid, ssvid, ssid);
138*11596SJason.Beloro@Sun.COM 	(void) sprintf(new_compat[2], "pciex%x,%x.%x", venid, devid, rev);
139*11596SJason.Beloro@Sun.COM 	(void) sprintf(new_compat[3], "pciex%x,%x", venid, devid);
140*11596SJason.Beloro@Sun.COM 	(void) sprintf(new_compat[4], "pciexclass,%06x", class_code);
141*11596SJason.Beloro@Sun.COM 	(void) sprintf(new_compat[5], "pciexclass,%04x", class_code >> 8);
142*11596SJason.Beloro@Sun.COM 	(void) sprintf(new_compat[6], "pci%x,%x", venid, devid);
143*11596SJason.Beloro@Sun.COM 
144*11596SJason.Beloro@Sun.COM 	(void) ddi_prop_update_string_array(DDI_DEV_T_NONE, dip, "compatible",
145*11596SJason.Beloro@Sun.COM 	    (char **)new_compat, 7);
146*11596SJason.Beloro@Sun.COM 
147*11596SJason.Beloro@Sun.COM cleanup:
148*11596SJason.Beloro@Sun.COM 	for (i = 0; i < ncompat; ++i)
149*11596SJason.Beloro@Sun.COM 		kmem_free(new_compat[i], compat_entry_length);
150*11596SJason.Beloro@Sun.COM 
151*11596SJason.Beloro@Sun.COM 	(void) ddi_prop_update_int(DDI_DEV_T_NONE, dip, "ddi-assigned", 0);
152*11596SJason.Beloro@Sun.COM 	(void) ddi_prop_update_int(DDI_DEV_T_NONE, dip, DDI_NO_AUTODETACH, 1);
153*11596SJason.Beloro@Sun.COM }
154