|
|
1.1 root 1: /*
2: * Copyright (c) 1999 Apple Computer, Inc. All rights reserved.
3: *
4: * @APPLE_LICENSE_HEADER_START@
5: *
6: * Portions Copyright (c) 1999 Apple Computer, Inc. All Rights
7: * Reserved. This file contains Original Code and/or Modifications of
8: * Original Code as defined in and that are subject to the Apple Public
9: * Source License Version 1.1 (the "License"). You may not use this file
10: * except in compliance with the License. Please obtain a copy of the
11: * License at http://www.apple.com/publicsource and read it before using
12: * this file.
13: *
14: * The Original Code and all software distributed under the License are
15: * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
16: * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
17: * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
18: * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT. Please see the
19: * License for the specific language governing rights and limitations
20: * under the License.
21: *
22: * @APPLE_LICENSE_HEADER_END@
23: */
24:
25: /* Copyright (c) 1997 Apple Computer, Inc. All rights reserved.
26: *
27: * PowerSurgeMB.c
28: *
29: * 20-May-97 Simon Douglas
30: * Created.
31: */
32:
33: #include <mach/mach_types.h>
34: #include <machdep/ppc/proc_reg.h>
35: #include <machdep/ppc/powermac.h>
36: #import <driverkit/IODevice.h>
37: #include "busses.h"
38: #import <bsd/dev/ppc/drvPMU/pmu.h>
39: #import <bsd/dev/ppc/drvPMU/pmupriv.h>
40: #import <bsd/dev/ppc/drvPMU/pmumisc.h>
41:
42:
43: // seconds between 1904 (Mac) & 1970 (UNIX) - many.
44: #define JAN11970 0x7c25b080
45: // MacOS xpram var for local secs from GMT
46: #define MACTIMEZONE 0xec
47:
48: #define printf kprintf
49:
50: void MBCallback(id unused, UInt32 refnum, UInt32 length, UInt8* buffer);
51: void wait_for_callback(void);
52:
53: thread_t our_thread;
54: id ApplePMUId; // loaded driver
55:
56:
57: IOReturn
58: cuda_time_of_day( unsigned int * secs, int set )
59: {
60: unsigned int newTime;
61:
62: kprintf("cuda_time_of_day: ApplePMUId = %08x, secs = %08x, *secs = %08x, set = %08x\n",
63: ApplePMUId, secs, *secs, set);
64:
65: if ( set == 0 ) {
66: if ( ApplePMUId == NULL ) {
67: *secs = JAN11970;
68: } else {
69: [ApplePMUId getRealTimeClock:(UInt8 *)&newTime :0 :0 :MBCallback];
70: wait_for_callback();
71:
72: *secs = newTime;
73: kprintf("newTime =%x\n", newTime);
74: }
75: } else {
76: if ( ApplePMUId != NULL ) {
77: newTime = *secs;
78:
79: [ApplePMUId setRealTimeClock:(UInt8 *)&newTime :0 :0 :MBCallback];
80: wait_for_callback();
81: }
82: }
83:
84: return 0;
85: }
86:
87:
88: void
89: cuda_restart(int powerOff)
90: {
91: unsigned char commandBuffer[4] = {'M', 'A', 'T', 'T'};
92: unsigned char inputBuffer[1];
93:
94: kprintf("cuda_restart\n");
95:
96: if ( ApplePMUId == NULL ) {
97: kprintf("cuda_restart, no PMU driver\n");
98: } else {
99: if( powerOff ) {
100: [ApplePMUId sendMiscCommand:kPMUPmgrPWRoff :4 :commandBuffer :inputBuffer :0 :0 :MBCallback];
101: } else {
102: [ApplePMUId sendMiscCommand:kPMUresetCPU :0 :NULL :NULL :0 :0 :MBCallback];
103: }
104: wait_for_callback();
105: }
106: }
107:
108: void PowerSurgeSendIIC( unsigned char iicAddr, unsigned char iicReg, unsigned char iicData)
109: {
110: #if 0 //No adb_send() in adb.c any more
111: adb_request_t cmd;
112:
113: adb_init_request(&cmd);
114: cmd.a_cmd.a_header[0] = ADB_PACKET_PSEUDO;
115: cmd.a_cmd.a_header[1] = ADB_PSEUDOCMD_GET_SET_IIC;
116: cmd.a_cmd.a_header[2] = iicAddr;
117: cmd.a_cmd.a_header[3] = iicReg;
118: cmd.a_cmd.a_header[4] = iicData;
119: cmd.a_cmd.a_hcount = 5;
120: adb_send(&cmd, TRUE);
121: #endif
122: UInt8 buffer[5] = { 1,
123: 0x22, //ADB_PSEUDOCMD_GET_SET_IIC in adb.h
124: iicAddr,
125: iicReg,
126: iicData};
127:
128: if ( ApplePMUId != NULL ) { //A.W. combined from Titan C
129: // old, Simon says is buggy [ApplePMUId CudaMisc:buffer:5:NULL:0:NULL];
130: [ApplePMUId CudaMisc:buffer:5:(UInt32)current_thread() : 0: MBCallback];
131:
132: wait_for_callback();
133: }
134:
135: }
136:
137: // Can't be used anymore...
138: #if 0
139: enum {
140: kXPRAMNVPartition = 0x1300,
141: kNameRegistryNVPartition = 0x1400,
142: kOpenFirmwareNVPartition = 0x1800,
143: };
144: #endif
145:
146: IOReturn
147: ReadNVRAM( unsigned int offset, unsigned int length, unsigned char * buffer )
148: {
149: volatile unsigned char *nvAddrReg =
150: (volatile unsigned char *) (POWERMAC_IO(PCI_NVRAM_ADDR_PHYS));
151: volatile unsigned char *nvDataReg =
152: (volatile unsigned char *) (POWERMAC_IO(PCI_NVRAM_DATA_PHYS));
153: int i;
154:
155: if( offset + length > 0x2000 )
156: return( IO_R_UNSUPPORTED);
157:
158: if (HasPMU()) {
159: // This is a powerbook
160: if (ApplePMUId == NULL) {
161: for ( i = 0; i < length; i++ ) {
162: buffer[i] = 0;
163: }
164: } else {
165: [ApplePMUId readNVRAM: offset: length: buffer: 0: 0: MBCallback];
166: wait_for_callback();
167: }
168: } else {
169: // This is a desktop mac
170: if (IsPowerSurge()) {
171: for( i = 0; i < length; i++) {
172: *nvAddrReg = (0xff & ((offset + i) >> 5));
173: eieio();
174: buffer[i] = *(nvDataReg + 16 * ((offset + i) & 0x1f));
175: eieio();
176: }
177: } else {
178: for (i = 0; i < length; i++) {
179: buffer[i] = nvAddrReg[(offset + i) * 16];
180: }
181: }
182: }
183:
184: return 0;
185: }
186:
187: IOReturn
188: WriteNVRAM( unsigned int offset, unsigned int length, unsigned char * buffer )
189: {
190: volatile unsigned char *nvAddrReg =
191: (volatile unsigned char *) (POWERMAC_IO(PCI_NVRAM_ADDR_PHYS));
192: volatile unsigned char *nvDataReg =
193: (volatile unsigned char *) (POWERMAC_IO(PCI_NVRAM_DATA_PHYS));
194: int i;
195:
196: if( offset + length > 0x2000 )
197: return( IO_R_UNSUPPORTED);
198:
199: if (HasPMU()) {
200: // This is a powerbook
201: if (ApplePMUId == NULL) {
202: } else {
203: [ApplePMUId writeNVRAM: offset: length: buffer: 0: 0: MBCallback];
204: wait_for_callback();
205: }
206: } else {
207: // This is a desktop mac
208: if (IsPowerSurge()) {
209: for( i = 0; i < length; i++) {
210: *nvAddrReg = (0xff & ((offset + i) >> 5));
211: eieio();
212: *(nvDataReg + 16 * ((offset + i) & 0x1f)) = buffer[i];
213: eieio();
214: }
215: } else {
216: for( i = 0; i < length; i++) {
217: nvAddrReg[(offset + i) * 16] = buffer[i];
218: }
219: }
220: }
221:
222: return 0;
223: }
224:
225:
226: int
227: GetMacOSTimeZone( void )
228: {
229: int macZone;
230: IOReturn err;
231:
232: err = ReadNVRAM( NVRAM_XPRAM_Offset + MACTIMEZONE, 4,
233: (unsigned char *)&macZone);
234:
235: printf( " macZone: %x",macZone );
236:
237: if( err == 0) {
238: if( macZone & 0x00800000)
239: macZone |= 0xff000000; // sign ext 24->32
240: else
241: macZone &= 0x00ffffff; // sign ext 24->32
242: } else
243: macZone = 0;
244: return macZone;
245: }
246:
247: unsigned int
248: get_unix_time_of_day( void )
249: {
250: int secs, macZone;
251: int err;
252:
253: err = cuda_time_of_day( &secs, FALSE );
254: /* printf( "TOD secs: %x,",secs ); */
255: secs -= (JAN11970 + GetMacOSTimeZone());
256: /* printf( " = Mac OS X Server: %x\n",secs ); */
257: return( secs );
258: }
259:
260: void
261: set_unix_time_of_day( unsigned int unixSecs )
262: {
263: int secs, macZone;
264: int err;
265:
266: /* printf( "Mac OS X Server: %x,", unixSecs ); */
267: secs = unixSecs + JAN11970 + GetMacOSTimeZone();
268: /* printf( " = TOD secs: %x\n",secs ); */
269: err = cuda_time_of_day( &secs, TRUE );
270: return;
271: }
272:
273: void MBCallback(id unused, UInt32 refnum, UInt32 length, UInt8* buffer)
274: {
275: clear_wait(our_thread,0,FALSE);
276: }
277:
278:
279: // We have sent a command to the PMU driver. Sleep until it has sent the
280: // command to the PMU.
281: void wait_for_callback(void)
282: {
283: our_thread = current_thread();
284: assert_wait(our_thread, FALSE);
285: thread_block();
286: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.