IOFWAddressSpace.cpp [plain text]
#include <IOKit/firewire/IOFWAddressSpace.h>
#include <IOKit/firewire/IOFireWireController.h>
#include <IOKit/firewire/IOFireWireDevice.h>
#include "FWDebugging.h"
OSDefineMetaClassAndStructors(IOFWAddressSpaceAux, OSObject);
OSMetaClassDefineReservedUsed(IOFWAddressSpaceAux, 0); OSMetaClassDefineReservedUnused(IOFWAddressSpaceAux, 1);
OSMetaClassDefineReservedUnused(IOFWAddressSpaceAux, 2);
OSMetaClassDefineReservedUnused(IOFWAddressSpaceAux, 3);
OSMetaClassDefineReservedUnused(IOFWAddressSpaceAux, 4);
OSMetaClassDefineReservedUnused(IOFWAddressSpaceAux, 5);
OSMetaClassDefineReservedUnused(IOFWAddressSpaceAux, 6);
OSMetaClassDefineReservedUnused(IOFWAddressSpaceAux, 7);
OSMetaClassDefineReservedUnused(IOFWAddressSpaceAux, 8);
OSMetaClassDefineReservedUnused(IOFWAddressSpaceAux, 9);
#pragma mark -
bool IOFWAddressSpaceAux::init( IOFWAddressSpace * primary )
{
bool success = true;
if( !OSObject::init() )
success = false;
fExclusive = false;
if( success )
{
fPrimary = primary;
fControl = fPrimary->fControl;
fTrustedNodeSet = OSSet::withCapacity(1);
if( fTrustedNodeSet == NULL )
success = false;
}
if( success )
{
fTrustedNodeSetIterator = OSCollectionIterator::withCollection( fTrustedNodeSet );
if( fTrustedNodeSetIterator == NULL )
success = false;
}
if( !success )
{
if( fTrustedNodeSet != NULL )
{
fTrustedNodeSet->release();
fTrustedNodeSet = NULL;
}
if( fTrustedNodeSetIterator != NULL )
{
fTrustedNodeSetIterator->release();
fTrustedNodeSetIterator = NULL;
}
}
return success;
}
void IOFWAddressSpaceAux::free()
{
if( fTrustedNodeSet != NULL )
{
fTrustedNodeSet->release();
fTrustedNodeSet = NULL;
}
if( fTrustedNodeSetIterator != NULL )
{
fTrustedNodeSetIterator->release();
fTrustedNodeSetIterator = NULL;
}
OSObject::free();
}
bool IOFWAddressSpaceAux::isTrustedNode( UInt16 nodeID )
{
bool trusted = false;
#if 1
if( fControl->getSecurityMode() == kIOFWSecurityModeNormal )
trusted = true;
#endif
if( !trusted )
{
UInt16 localNodeID = fControl->getLocalNodeID();
if( nodeID == localNodeID || fTrustedNodeSet->getCount() == 0 )
trusted = true;
}
IOFireWireDevice * item = NULL;
fTrustedNodeSetIterator->reset();
while( !trusted && (item = (IOFireWireDevice *) fTrustedNodeSetIterator->getNextObject()) )
{
UInt32 generation = 0;
UInt16 deviceNodeID = 0;
item->getNodeIDGeneration( generation, deviceNodeID );
if( deviceNodeID == nodeID )
trusted = true;
}
return trusted;
}
void IOFWAddressSpaceAux::addTrustedNode( IOFireWireDevice * device )
{
fTrustedNodeSet->setObject( device );
}
void IOFWAddressSpaceAux::removeTrustedNode( IOFireWireDevice * device )
{
fTrustedNodeSet->removeObject( device );
}
void IOFWAddressSpaceAux::removeAllTrustedNodes( void )
{
fTrustedNodeSet->flushCollection();
}
bool IOFWAddressSpaceAux::isExclusive( void )
{
return fExclusive;
}
void IOFWAddressSpaceAux::setExclusive( bool exclusive )
{
fExclusive = exclusive;
}
bool IOFWAddressSpaceAux::intersects( IOFWAddressSpace * space )
{
return false;
}
#pragma mark -
OSDefineMetaClass( IOFWAddressSpace, OSObject )
OSDefineAbstractStructors(IOFWAddressSpace, OSObject)
bool IOFWAddressSpace::init(IOFireWireBus *bus)
{
bool success = true;
if( !OSObject::init() )
success = false;
if( success )
{
fControl = OSDynamicCast(IOFireWireController, bus);
if( fControl == NULL )
success = false;
}
if( success )
{
fIOFWAddressSpaceExpansion = (ExpansionData*) IOMalloc( sizeof(ExpansionData) );
if( fIOFWAddressSpaceExpansion == NULL )
success = false;
}
if( success )
{
bzero( fIOFWAddressSpaceExpansion, sizeof(ExpansionData) );
fIOFWAddressSpaceExpansion->fAuxiliary = createAuxiliary();
if( fIOFWAddressSpaceExpansion->fAuxiliary == NULL )
success = false;
}
if( !success )
{
if( fIOFWAddressSpaceExpansion->fAuxiliary != NULL )
{
fIOFWAddressSpaceExpansion->fAuxiliary->release();
fIOFWAddressSpaceExpansion->fAuxiliary = NULL;
}
if( fIOFWAddressSpaceExpansion != NULL )
{
IOFree ( fIOFWAddressSpaceExpansion, sizeof(ExpansionData) );
fIOFWAddressSpaceExpansion = NULL;
}
}
return success;
}
IOFWAddressSpaceAux * IOFWAddressSpace::createAuxiliary( void )
{
IOFWAddressSpaceAux * auxiliary;
auxiliary = new IOFWAddressSpaceAux;
if( auxiliary != NULL && !auxiliary->init(this) )
{
auxiliary->release();
auxiliary = NULL;
}
return auxiliary;
}
void IOFWAddressSpace::free()
{
if( fIOFWAddressSpaceExpansion != NULL )
{
if( fIOFWAddressSpaceExpansion->fAuxiliary != NULL )
{
fIOFWAddressSpaceExpansion->fAuxiliary->release();
fIOFWAddressSpaceExpansion->fAuxiliary = NULL;
}
IOFree ( fIOFWAddressSpaceExpansion, sizeof(ExpansionData) );
fIOFWAddressSpaceExpansion = NULL;
}
OSObject::free();
}
UInt32 IOFWAddressSpace::doLock(UInt16 nodeID, IOFWSpeed &speed, FWAddress addr, UInt32 inLen,
const UInt32 *newVal, UInt32 &outLen, UInt32 *oldVal, UInt32 type,
IOFWRequestRefCon refcon)
{
UInt32 ret = kFWResponseAddressError;
bool ok;
int size;
int i;
IOMemoryDescriptor *desc = NULL;
IOByteCount offset;
size = inLen/8; outLen = inLen/2;
ret = doRead(nodeID, speed, addr, size*4, &desc, &offset, refcon);
if(ret != kFWResponseComplete)
return ret;
desc->readBytes(offset, oldVal, size*4);
switch (type)
{
case kFWExtendedTCodeCompareSwap:
ok = true;
for(i=0; i<size; i++)
ok = ok && oldVal[i] == newVal[i];
if(ok)
ret = doWrite(nodeID, speed, addr, size*4, newVal+size, refcon);
break;
default:
ret = kFWResponseTypeError;
}
return ret;
}
IOReturn IOFWAddressSpace::activate()
{
return fControl->allocAddress(this);
}
void IOFWAddressSpace::deactivate()
{
fControl->freeAddress(this);
}
UInt32 IOFWAddressSpace::contains(FWAddress addr)
{
return 0;
}