4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License, Version 1.0 only
6 * (the "License"). You may not use this file except in compliance
9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10 * or http://www.opensolaris.org/os/licensing.
11 * See the License for the specific language governing permissions
12 * and limitations under the License.
14 * When distributing Covered Code, include this CDDL HEADER in each
15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16 * If applicable, add the following below this CDDL HEADER, with the
17 * fields enclosed by brackets "[]" replaced with your own identifying
18 * information: Portions Copyright [yyyy] [name of copyright owner]
23 * Copyright 2004 Sun Microsystems, Inc. All rights reserved.
24 * Use is subject to license terms.
27 #pragma ident "%Z%%M% %I% %E% SMI"
29 #include <sys/param.h>
30 #include <sys/systm.h>
31 #include <sys/sysmacros.h>
32 #include <sys/sunddi.h>
33 #include <sys/esunddi.h>
34 #include <sys/sunndi.h>
37 #include <sys/platform_module.h>
38 #include <sys/errno.h>
40 #include <sys/sunldi.h>
43 #define SHARED_PCF8584_PATH "/pci@8,700000/ebus@5/i2c@1,2e/nvram@0,a0"
44 static dev_info_t
*shared_pcf8584_dip
;
45 static kmutex_t excal_pcf8584_mutex
;
47 int (*p2get_mem_unum
)(int, uint64_t, char *, int, int *);
50 * Excalibur fan information
52 typedef struct xcalfan_info
{
58 static xcalfan_info_t xcalfans
[] = {
59 {"/pci@8,700000/ebus@5/i2c@1,30/fan-control@0,48:2", 63, NULL
},
60 {"/pci@8,700000/ebus@5/i2c@1,30/fan-control@0,48:0", 63, NULL
},
61 {"/pci@8,700000/ebus@5/i2c@1,30/fan-control@0,48:4", 31, NULL
}
64 #define NFANS (sizeof (xcalfans) / sizeof (xcalfans[0]))
67 startup_platform(void)
69 mutex_init(&excal_pcf8584_mutex
, NULL
, NULL
, NULL
);
73 set_platform_tsb_spares()
79 set_platform_defaults(void)
84 load_platform_drivers(void)
91 static char *boot_time_drivers
[] = {
102 for (drv
= boot_time_drivers
; *drv
; drv
++) {
103 if ((i_ddi_attach_hw_nodes(*drv
) != DDI_SUCCESS
) &&
104 (strcmp(*drv
, "us") != 0))
106 * It is OK if 'us' driver doesn't load. It's
107 * not available in Core cluster.
109 cmn_err(CE_WARN
, "Failed to install \"%s\" driver.",
114 * mc-us3 must stay loaded for plat_get_mem_unum()
116 (void) ddi_hold_driver(ddi_name_to_major("mc-us3"));
119 * Figure out which pcf8584_dip is shared with OBP for the nvram
120 * device, so the lock can be acquired.
122 * This should really be done elsewhere, like startup_platform, but
123 * that runs before the devinfo tree is setup with configure().
124 * So it is here until there is a better place.
126 dip
= e_ddi_hold_devi_by_path(SHARED_PCF8584_PATH
, 0);
129 shared_pcf8584_dip
= ddi_get_parent(dip
);
131 ndi_hold_devi(shared_pcf8584_dip
);
134 li
= ldi_ident_from_anon();
135 for (i
= 0; i
< NFANS
; ++i
) {
136 err
= ldi_open_by_name(xcalfans
[i
].pathname
,
137 FWRITE
, kcred
, &xcalfans
[i
].lh
, li
);
140 cmn_err(CE_WARN
, "plat_fan_blast: "
141 "Failed to get fan device handle for %s",
142 xcalfans
[i
].pathname
);
146 ldi_ident_release(li
);
151 plat_cpu_poweron(struct cpu
*cp
)
153 return (ENOTSUP
); /* not supported on this platform */
158 plat_cpu_poweroff(struct cpu
*cp
)
160 return (ENOTSUP
); /* not supported on this platform */
165 plat_freelist_process(int mnode
)
169 char *platform_module_list
[] = {
170 "schppm", /* must attach before xcalppm */
177 plat_tod_fault(enum tod_fault_type tod_bad
)
183 plat_get_mem_unum(int synd_code
, uint64_t flt_addr
, int flt_bus_id
,
184 int flt_in_memory
, ushort_t flt_status
, char *buf
, int buflen
, int *lenp
)
186 if (flt_in_memory
&& (p2get_mem_unum
!= NULL
))
187 return (p2get_mem_unum(synd_code
, P2ALIGN(flt_addr
, 8),
194 plat_get_cpu_unum(int cpuid
, char *buf
, int buflen
, int *lenp
)
196 if (snprintf(buf
, buflen
, "Slot %d", cpuid
) >= buflen
) {
205 * Unfortunately, excal's BBC pcf8584 controller is used by both OBP
206 * and the OS's i2c drivers. The 'eeprom' command executes
207 * OBP code to handle property requests. If eeprom didn't do this, or if the
208 * controllers were partitioned so that all devices on a given controller were
209 * driven by either OBP or the OS, this wouldn't be necessary.
211 * Note that getprop doesn't have the same issue as it reads from cached
216 * Common locking enter code
219 plat_setprop_enter(void)
221 mutex_enter(&excal_pcf8584_mutex
);
225 * Common locking exit code
228 plat_setprop_exit(void)
230 mutex_exit(&excal_pcf8584_mutex
);
234 * Called by pcf8584 driver
237 plat_shared_i2c_enter(dev_info_t
*dip
)
239 if (dip
== shared_pcf8584_dip
) {
240 plat_setprop_enter();
245 * Called by pcf8584 driver
248 plat_shared_i2c_exit(dev_info_t
*dip
)
250 if (dip
== shared_pcf8584_dip
) {
256 * Set platform fans to maximum speed
267 for (i
= 0; i
< NFANS
; ++i
) {
268 fv
= xcalfans
[i
].val8
;
269 bzero(&uio
, sizeof (uio
));
270 bzero(&iov
, sizeof (iov
));
272 iov
.iov_len
= sizeof (fv
);
276 uio
.uio_segflg
= UIO_SYSSPACE
;
277 uio
.uio_resid
= sizeof (fv
);
279 err
= ldi_write(xcalfans
[i
].lh
, &uio
, kcred
);
282 cmn_err(CE_WARN
, "!plat_fan_blast: Cannot "
283 "write %d to %s now, try again later.",
284 xcalfans
[i
].val8
, xcalfans
[i
].pathname
);
286 cmn_err(CE_WARN
, "plat_fan_blast: "
287 "Error %d while writing %d to %s.", err
,
288 xcalfans
[i
].val8
, xcalfans
[i
].pathname
);