|
|
1.1 ! root 1: /* ! 2: * Copyright (c) 1998-2000 Apple Computer, Inc. All rights reserved. ! 3: * ! 4: * @APPLE_LICENSE_HEADER_START@ ! 5: * ! 6: * The contents of this file constitute Original Code as defined in and ! 7: * are subject to the Apple Public Source License Version 1.1 (the ! 8: * "License"). You may not use this file except in compliance with the ! 9: * License. Please obtain a copy of the License at ! 10: * http://www.apple.com/publicsource and read it before using this file. ! 11: * ! 12: * This Original Code and all software distributed under the License are ! 13: * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER ! 14: * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, ! 15: * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, ! 16: * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT. Please see the ! 17: * License for the specific language governing rights and limitations ! 18: * under the License. ! 19: * ! 20: * @APPLE_LICENSE_HEADER_END@ ! 21: */ ! 22: /* ! 23: * Copyright (c) 1997 Apple Computer, Inc. ! 24: * ! 25: * ! 26: * HISTORY ! 27: * ! 28: * sdouglas 22 Oct 97 - first checked in. ! 29: * sdouglas 21 Jul 98 - start IOKit ! 30: * sdouglas 14 Dec 98 - start cpp. ! 31: */ ! 32: ! 33: ! 34: ! 35: #include <IOKit/IOLib.h> ! 36: #include <libkern/c++/OSContainers.h> ! 37: ! 38: extern "C" { ! 39: #include <pexpert/pexpert.h> ! 40: }; ! 41: ! 42: #include "IONDRV.h" ! 43: #include "IOPEFLoader.h" ! 44: ! 45: #define LOG if(1) kprintf ! 46: ! 47: #define USE_TREE_NDRVS 1 ! 48: #define USE_ROM_NDRVS 1 ! 49: ! 50: ! 51: /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ ! 52: ! 53: #define super OSObject ! 54: ! 55: OSDefineMetaClassAndStructors(IONDRV, OSObject) ! 56: ! 57: /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ ! 58: ! 59: IONDRV * IONDRV::instantiate( IOLogicalAddress container, ! 60: IOByteCount containerSize ) ! 61: { ! 62: OSStatus err = 1; ! 63: IONDRV * inst; ! 64: ! 65: inst = new IONDRV; ! 66: ! 67: if( inst) do { ! 68: if( false == inst->init()) ! 69: continue; ! 70: ! 71: err = PCodeOpen( (void *)container, containerSize, &inst->pcInst ); ! 72: if( err) ! 73: continue; ! 74: err = PCodeInstantiate( inst->pcInst ); ! 75: if( err) ! 76: continue; ! 77: ! 78: inst->getSymbol( "DoDriverIO", ! 79: (IOLogicalAddress *) &inst->fDoDriverIO ); ! 80: if( kIOReturnSuccess == inst->getSymbol( "TheDriverDescription", ! 81: (IOLogicalAddress *) &inst->theDriverDesc )) { ! 82: ! 83: char * name; ! 84: int plen; ! 85: ! 86: name = (char *) inst->theDriverDesc->driverOSRuntimeInfo.driverName; ! 87: plen = name[ 0 ]; ! 88: strncpy( name, name + 1, plen); ! 89: name[ plen ] = 0; ! 90: ! 91: kprintf("ndrv version %08x\n", ! 92: inst->theDriverDesc-> driverType.version); ! 93: } ! 94: ! 95: } while( false); ! 96: ! 97: if( inst && err) { ! 98: inst->release(); ! 99: inst = 0; ! 100: } ! 101: ! 102: return( inst ); ! 103: } ! 104: ! 105: void IONDRV::free( void ) ! 106: { ! 107: super::free(); ! 108: } ! 109: ! 110: IOReturn IONDRV::getSymbol( const char * symbolName, ! 111: IOLogicalAddress * address ) ! 112: { ! 113: OSStatus err; ! 114: ! 115: err = PCodeFindExport( pcInst, symbolName, ! 116: (LogicalAddress *)address, NULL ); ! 117: if( err) ! 118: *address = 0; ! 119: ! 120: return( err); ! 121: } ! 122: ! 123: #if 0 ! 124: if( (err = NDRVGetShimClass( ioDevice, instance, 0, classNames )) ! 125: ) continue; ! 126: err = [propTable createProperty:"AAPL,dk_Driver Name" flags:0 ! 127: value:classNames length:strlen( classNames) ]; ! 128: err = [propTable createProperty:"AAPL,dk_Server Name" flags:0 ! 129: value:classNames length:strlen( classNames) ]; ! 130: ! 131: OSStatus NDRVGetShimClass( id ioDevice, NDRVInstance instance, UInt32 serviceIndex, char * className ) ! 132: { ! 133: NDRVInstanceVars * ndrvInst = (NDRVInstanceVars *) instance; ! 134: OSStatus err; ! 135: static const char * driverDescProperty = "TheDriverDescription"; ! 136: static const char * frameBufferShim = "IONDRVFramebuffer"; ! 137: DriverDescription * desc; ! 138: UInt32 serviceType; ! 139: ! 140: className[ 0 ] = 0; ! 141: do { ! 142: err = PCodeFindExport( ndrvInst->pcInst, driverDescProperty, (IOLogicalAddress *)&desc, NULL ); ! 143: if( err) continue; ! 144: ! 145: if( desc->driverDescSignature != kTheDescriptionSignature) { ! 146: err = -1; ! 147: continue; ! 148: } ! 149: if( serviceIndex >= desc->driverServices.nServices) { ! 150: err = -1; ! 151: continue; ! 152: } ! 153: ! 154: serviceType = desc->driverServices.service[ serviceIndex ].serviceType; ! 155: switch( desc->driverServices.service[ serviceIndex ].serviceCategory) { ! 156: ! 157: case kServiceCategoryNdrvDriver: ! 158: if( serviceType == kNdrvTypeIsVideo) { ! 159: strcpy( className, frameBufferShim); ! 160: break; ! 161: } ! 162: default: ! 163: err = -1; ! 164: } ! 165: } while( false); ! 166: ! 167: return( err); ! 168: } ! 169: #endif ! 170: ! 171: ! 172: ! 173: IOReturn IONDRV::doDriverIO( UInt32 commandID, void * contents, ! 174: UInt32 commandCode, UInt32 commandKind ) ! 175: { ! 176: OSStatus err; ! 177: ! 178: if( 0 == fDoDriverIO) ! 179: return( kIOReturnUnsupported ); ! 180: ! 181: err = CallTVector( /*AddressSpaceID*/ 0, (void *)commandID, contents, ! 182: (void *)commandCode, (void *)commandKind, /*p6*/ 0, ! 183: fDoDriverIO ); ! 184: ! 185: #if 0 ! 186: if( err) { ! 187: UInt32 i; ! 188: static const char * commands[] = ! 189: { "kOpenCommand", "kCloseCommand", ! 190: "kReadCommand", "kWriteCommand", ! 191: "kControlCommand", "kStatusCommand", "kKillIOCommand", ! 192: "kInitializeCommand", "kFinalizeCommand", ! 193: "kReplaceCommand", "kSupersededCommand" }; ! 194: ! 195: LOG("Driver failed (%d) on %s : ", err, commands[ commandCode ] ); ! 196: ! 197: switch( commandCode) { ! 198: case kControlCommand: ! 199: case kStatusCommand: ! 200: LOG("%d : ", ((UInt16 *)contents)[ 0x1a / 2 ]); ! 201: contents = ((void **)contents)[ 0x1c / 4 ]; ! 202: for( i = 0; i<5; i++ ) ! 203: LOG("%08x, ", ((UInt32 *)contents)[i] ); ! 204: break; ! 205: } ! 206: LOG("\n"); ! 207: } ! 208: #endif ! 209: ! 210: return( err); ! 211: } ! 212: ! 213: ! 214: IONDRV * IONDRV::fromRegistryEntry( IORegistryEntry * regEntry ) ! 215: { ! 216: IOLogicalAddress pef = 0; ! 217: IOByteCount propSize = 0; ! 218: OSData * prop; ! 219: IONDRV * inst; ! 220: ! 221: inst = (IONDRV *) regEntry->getProperty("AAPL,ndrvInst"); ! 222: if( inst) { ! 223: inst->retain(); ! 224: return( inst ); ! 225: } ! 226: ! 227: // -- only enable the boot display unless mmon flag is set ! 228: #if 0 ! 229: int num; ! 230: prop = (OSData *) regEntry->getProperty( "AAPL,boot-display" ); ! 231: if( (0 == prop) && (!PE_parse_boot_arg("mmon", &num))) ! 232: return( 0 ); ! 233: #endif ! 234: // -- ! 235: ! 236: prop = (OSData *) regEntry->getProperty( "driver,AAPL,MacOS,PowerPC" ); ! 237: if( USE_TREE_NDRVS && prop) { ! 238: pef = (IOLogicalAddress) prop->getBytesNoCopy(); ! 239: propSize = prop->getLength(); ! 240: } ! 241: ! 242: // God awful hack: ! 243: // Some onboard devices don't have the ndrv in the tree. The booter ! 244: // can load & match PEF's but only from disk, not network boots. ! 245: ! 246: #if USE_ROM_NDRVS ! 247: if( !pef && (0 == strcmp( regEntry->getName(), "ATY,mach64_3DU")) ) { ! 248: ! 249: int * patch; ! 250: ! 251: patch = (int *) 0xffe88140; ! 252: propSize = 0x10a80; ! 253: ! 254: // Check ati PEF exists there ! 255: if( patch[ 0x1f0 / 4 ] == 'ATIU') { ! 256: ! 257: pef = (IOLogicalAddress) IOMalloc( propSize ); ! 258: bcopy( (void *) patch, (void *) pef, propSize ); ! 259: } ! 260: } ! 261: ! 262: if( !pef && (0 == strcmp( regEntry->getName(), "ATY,mach64_3DUPro")) ) { ! 263: ! 264: int * patch; ! 265: ! 266: patch = (int *) 0xffe99510; ! 267: propSize = 0x12008; ! 268: // Check ati PEF exists there ! 269: if( patch[ 0x1fc / 4 ] != 'ATIU') { ! 270: ! 271: // silk version ! 272: patch = (int *) 0xffe99550; ! 273: propSize = 0x12058; ! 274: if( patch[ 0x1fc / 4 ] != 'ATIU') ! 275: propSize = 0; ! 276: } ! 277: ! 278: if( propSize) { ! 279: pef = (IOLogicalAddress) IOMalloc( propSize ); ! 280: bcopy( (void *) patch, (void *) pef, propSize ); ! 281: } ! 282: } ! 283: ! 284: if( !pef && (0 == strcmp( regEntry->getName(), "control")) ) { ! 285: ! 286: #define ins(i,d,a,simm) ((i<<26)+(d<<21)+(a<<16)+simm) ! 287: int * patch; ! 288: ! 289: patch = (int *) 0xffe6bd50; ! 290: propSize = 0xac10; ! 291: ! 292: // Check control PEF exists there ! 293: if( patch[ 0x41ac / 4 ] == ins( 32, 3, 0, 0x544)) { // lwz r3,0x544(0) ! 294: ! 295: pef = (IOLogicalAddress) IOMalloc( propSize ); ! 296: bcopy( (void *) patch, (void *) pef, propSize ); ! 297: patch = (int *) pef; ! 298: // patch out low mem accesses ! 299: patch[ 0x8680 / 4 ] = ins( 14, 12, 0, 0); // addi r12,0,0x0 ! 300: patch[ 0x41ac / 4 ] = ins( 14, 3, 0, 0x544); // addi r3,0,0x544; ! 301: patch[ 0x8fa0 / 4 ] = ins( 14, 3, 0, 0x648); // addi r3,0,0x648; ! 302: } ! 303: } ! 304: #endif ! 305: ! 306: if( pef) { ! 307: kprintf( "pef = %08x, %08x\n", pef, propSize ); ! 308: inst = IONDRV::instantiate( pef, propSize ); ! 309: if( inst ) ! 310: regEntry->setProperty( "AAPL,ndrvInst", inst); ! 311: ! 312: } else ! 313: inst = 0; ! 314: ! 315: return( inst ); ! 316: } ! 317: ! 318: const char * IONDRV::driverName( void ) ! 319: { ! 320: return( (const char *) theDriverDesc->driverOSRuntimeInfo.driverName); ! 321: } ! 322: ! 323:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.