1/*
2 * Copyright (c) 1998-2001 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#include "IOFireWireAVCProtocolUserClient.h"
23#include <IOKit/avc/IOFireWireAVCConsts.h>
24#include <IOKit/firewire/IOFireWireNub.h>
25#include <IOKit/firewire/IOFireWireBus.h>
26#include <IOKit/firewire/IOFWAddressSpace.h>
27#include <IOKit/avc/IOFireWirePCRSpace.h>
28#include <IOKit/avc/IOFireWireAVCTargetSpace.h>
29
30#if FIRELOG
31#import <IOKit/firewire/FireLog.h>
32#define FIRELOG_MSG(x) FireLog x
33#else
34#define FIRELOG_MSG(x) do {} while (0)
35#endif
36
37// Structure for keeping track of allocated plugs
38struct PlugInfo {
39    IOFireWireAVCProtocolUserClient *fClient;
40    UInt32 fPlug;
41    OSAsyncReference64 fCallbackInfo;
42    uint64_t fUserRefcon;	// Store here so CFPlugin doesn't have to track this
43};
44
45OSDefineMetaClassAndStructors(IOFireWireAVCProtocolUserClient, IOUserClient)
46
47//////////////////////////////////////////////////////
48// IOFireWireAVCUserClient::externalMethod
49//////////////////////////////////////////////////////
50IOReturn IOFireWireAVCProtocolUserClient::externalMethod( uint32_t selector,
51														IOExternalMethodArguments * arguments,
52														IOExternalMethodDispatch * dispatch,
53														OSObject * target,
54														void * reference)
55{
56	IOReturn result = kIOReturnBadArgument;
57
58	FIRELOG_MSG(("IOFireWireAVCProtocolUserClient::externalMethod (this=0x%08X), selector=0x%08X\n",this,selector));
59
60	// Dispatch the method call
61	switch (selector)
62	{
63		case kIOFWAVCProtocolUserClientSendAVCResponse:
64			result = sendAVCResponse(arguments->scalarInput[0],arguments->scalarInput[1], (const char*)arguments->structureInput, arguments->structureInputSize);
65			break;
66
67		case kIOFWAVCProtocolUserClientFreeInputPlug:
68			result = freeInputPlug(arguments->scalarInput[0]);
69			break;
70
71		case kIOFWAVCProtocolUserClientReadInputPlug:
72			result = readInputPlug((UInt32) arguments->scalarInput[0], arguments->scalarOutput);
73			break;
74
75		case kIOFWAVCProtocolUserClientUpdateInputPlug:
76			result = updateInputPlug(arguments->scalarInput[0],arguments->scalarInput[1],arguments->scalarInput[2]);
77			break;
78
79		case kIOFWAVCProtocolUserClientFreeOutputPlug:
80			result = freeOutputPlug(arguments->scalarInput[0]);
81			break;
82
83		case kIOFWAVCProtocolUserClientReadOutputPlug:
84			result = readOutputPlug((UInt32) arguments->scalarInput[0], arguments->scalarOutput);
85			break;
86
87		case kIOFWAVCProtocolUserClientUpdateOutputPlug:
88			result = updateOutputPlug(arguments->scalarInput[0],arguments->scalarInput[1],arguments->scalarInput[2]);
89			break;
90
91		case kIOFWAVCProtocolUserClientReadOutputMasterPlug:
92			result = readOutputMasterPlug(arguments->scalarOutput);
93			break;
94
95		case kIOFWAVCProtocolUserClientUpdateOutputMasterPlug:
96			result = updateOutputMasterPlug(arguments->scalarInput[0],arguments->scalarInput[1]);
97			break;
98
99		case kIOFWAVCProtocolUserClientReadInputMasterPlug:
100			result = readInputMasterPlug(arguments->scalarOutput);
101			break;
102
103		case kIOFWAVCProtocolUserClientUpdateInputMasterPlug:
104			result = updateInputMasterPlug(arguments->scalarInput[0],arguments->scalarInput[1]);
105			break;
106
107		case kIOFWAVCProtocolUserClientPublishAVCUnitDirectory:
108			result = publishAVCUnitDirectory();
109			break;
110
111		case kIOFWAVCProtocolUserClientSetSubunitPlugSignalFormat:
112			result = setSubunitPlugSignalFormat(arguments->scalarInput[0],(IOFWAVCPlugTypes)arguments->scalarInput[1],arguments->scalarInput[2],arguments->scalarInput[3]);
113			break;
114
115		case kIOFWAVCProtocolUserClientGetSubunitPlugSignalFormat:
116			result = getSubunitPlugSignalFormat(arguments->scalarInput[0],(IOFWAVCPlugTypes)arguments->scalarInput[1],arguments->scalarInput[2],arguments->scalarOutput);
117			break;
118
119		case kIOFWAVCProtocolUserClientConnectTargetPlugs:
120			result = connectTargetPlugs((AVCConnectTargetPlugsInParams *) arguments->structureInput, (AVCConnectTargetPlugsOutParams *) arguments->structureOutput);
121			break;
122
123		case kIOFWAVCProtocolUserClientDisconnectTargetPlugs:
124			result = disconnectTargetPlugs(arguments->scalarInput[0],
125										(IOFWAVCPlugTypes)arguments->scalarInput[1],
126										arguments->scalarInput[2],
127										arguments->scalarInput[3],
128										(IOFWAVCPlugTypes)arguments->scalarInput[4],
129										arguments->scalarInput[5]);
130			break;
131
132		case kIOFWAVCProtocolUserClientGetTargetPlugConnection:
133			result = getTargetPlugConnection((AVCGetTargetPlugConnectionInParams *) arguments->structureInput,
134											(AVCGetTargetPlugConnectionOutParams *) arguments->structureOutput);
135			break;
136
137		case kIOFWAVCProtocolUserClientAVCRequestNotHandled:
138			result = AVCRequestNotHandled(arguments->scalarInput[0],
139										arguments->scalarInput[1],
140										(IOFWSpeed)arguments->scalarInput[2],
141										arguments->scalarInput[3],
142										(const char *)arguments->structureInput,
143										arguments->structureInputSize);
144			break;
145
146		case kIOFWAVCProtocolUserClientAllocateInputPlug:
147			result = allocateInputPlug(arguments->asyncReference, arguments->scalarInput[0], arguments->scalarOutput);
148			break;
149
150		case kIOFWAVCProtocolUserClientAllocateOutputPlug:
151			result = allocateOutputPlug(arguments->asyncReference, arguments->scalarInput[0], arguments->scalarOutput);
152			break;
153
154		case kIOFWAVCProtocolUserClientInstallAVCCommandHandler:
155			result = installAVCCommandHandler(arguments->asyncReference, arguments->scalarInput[0], arguments->scalarInput[1],arguments->scalarInput[2],arguments->scalarInput[3]);
156			break;
157
158		case kIOFWAVCProtocolUserClientAddSubunit:
159			result = addSubunit(arguments->asyncReference,
160								arguments->scalarInput[0],
161								arguments->scalarInput[1],
162								arguments->scalarInput[2],
163								arguments->scalarInput[3],
164								arguments->scalarInput[4],
165								arguments->scalarOutput);
166			break;
167
168		case kIOFWAVCProtocolUserClientSetAVCRequestCallback: // No longer supported!
169			result = kIOReturnUnsupported;
170			break;
171
172		default:
173			// None of the above!
174			break;
175	};
176
177	return result;
178}
179
180
181
182void IOFireWireAVCProtocolUserClient::forwardPlugWrite(void *refcon, UInt16 nodeID, UInt32 plug, UInt32 oldVal, UInt32 newVal)
183{
184    OSData *data = (OSData *)refcon;
185    const PlugInfo *info = (const PlugInfo *)(data->getBytesNoCopy());
186    io_user_reference_t args[kMaxAsyncArgs];
187    UInt32 generation;
188    UInt16 localID;
189
190    FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::forwardPlugWrite\n"));
191
192    // fill out return parameters
193    info->fClient->fDevice->getNodeIDGeneration(generation, localID);
194    args[0] = info->fUserRefcon;
195    args[1] = generation;
196    args[2] = ((UInt32)nodeID);
197    args[3] = plug;
198    args[4] = oldVal;
199    args[5] = newVal;
200    info->fClient->sendAsyncResult64( ((PlugInfo *)info)->fCallbackInfo, kIOReturnSuccess, args, 6 );
201}
202
203void IOFireWireAVCProtocolUserClient::avcTargetCommandHandler(const AVCCommandHandlerInfo *pCmdInfo,
204															  UInt32 generation,
205															  UInt16 nodeID,
206															  const void *command,
207															  UInt32 cmdLen,
208															  IOFWSpeed &speed,
209															  UInt32 handlerSearchIndex)
210{
211    io_user_reference_t args[kMaxAsyncArgs];
212	OSAsyncReference64 asyncRef;
213	UInt8 *src;
214	UInt8 *dst;
215	UInt32 copyLen;
216	UInt32 i;
217	UInt32 thisCopyLen;
218	UInt8 *thisLoopStartSrc;
219
220    FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::avcTargetCommandHandler\n"));
221
222	bcopy(pCmdInfo->asyncRef, asyncRef, sizeof(OSAsyncReference64));
223
224	args[0] = 0;		// Initial call
225	args[2] = generation;
226	args[3] = ((UInt32)nodeID);
227	args[4] = cmdLen;
228	args[5] = pCmdInfo->userCallBack;
229	args[6] = pCmdInfo->userRefCon;
230	args[7] = speed;
231	args[8] = handlerSearchIndex;
232
233	src = (UInt8*)command;
234	dst = (UInt8 *)(args+9);
235
236#if __BIG_ENDIAN__
237	dst += 4;
238#endif
239
240	copyLen = cmdLen;
241	if(copyLen > (kMaxAsyncArgs - 9)*4)
242		copyLen =  (kMaxAsyncArgs - 9)*4;
243
244	i = copyLen;
245	while (i > 0)
246	{
247		thisCopyLen = (i < 4) ? i : 4;
248		bcopy(src, dst, thisCopyLen);
249		i -= thisCopyLen;
250		src += 4;
251		dst += 8;
252	}
253
254	args[1] = copyLen;
255	pCmdInfo->userClient->sendAsyncResult64( asyncRef, kIOReturnSuccess,
256					  args, 9+(copyLen+4-1)/4 );
257	cmdLen -= copyLen;
258
259	// Send rest of packet if necessary
260	while(cmdLen) {
261		copyLen = cmdLen;
262		dst = (UInt8 *)(args+2);
263
264#if __BIG_ENDIAN__
265		dst += 4;
266#endif
267
268		if(copyLen > (kMaxAsyncArgs - 2)*4)
269			copyLen =  (kMaxAsyncArgs - 2)*4;
270
271		i = copyLen;
272		thisLoopStartSrc = src;
273		while (i > 0)
274		{
275			thisCopyLen = (i < 4) ? i : 4;
276			bcopy(src, dst, thisCopyLen);
277			i -= thisCopyLen;
278			src += 4;
279			dst += 8;
280		}
281
282		args[0] = (thisLoopStartSrc - (const UInt8*)command);	// Bit being sent
283		args[1] = copyLen;
284		pCmdInfo->userClient->sendAsyncResult64( asyncRef, kIOReturnSuccess,
285					   args, 2+(copyLen+4-1)/4 );
286		cmdLen -= copyLen;
287	}
288}
289
290void IOFireWireAVCProtocolUserClient::avcSubunitPlugHandler(const AVCSubunitInfo *pSubunitInfo,
291															IOFWAVCSubunitPlugMessages plugMessage,
292															IOFWAVCPlugTypes plugType,
293															UInt32 plugNum,
294															UInt32 messageParams,
295															UInt32 generation,
296															UInt16 nodeID)
297{
298    io_user_reference_t args[kMaxAsyncArgs];
299	OSAsyncReference64 asyncRef;
300
301	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::avcSubunitPlugHandler\n"));
302
303	bcopy(pSubunitInfo->asyncRef, asyncRef, sizeof(OSAsyncReference64));
304
305	args[0] = pSubunitInfo->subunitTypeAndID;
306	args[1] = plugType;
307	args[2] = plugNum;
308	args[3] = plugMessage;
309	args[4] = messageParams;
310	args[5] = pSubunitInfo->userCallBack;
311	args[6] = pSubunitInfo->userRefCon;
312	args[7] = generation;
313	args[8] = ((UInt32)nodeID);
314
315	pSubunitInfo->userClient->sendAsyncResult64( asyncRef, kIOReturnSuccess,
316										args, 9);
317}
318
319void IOFireWireAVCProtocolUserClient::free()
320{
321    FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::free (%p)\n",this));
322
323    if(fInputPlugs) {
324        OSData *data;
325        while(data = OSDynamicCast(OSData, fInputPlugs->getAnyObject())) {
326             const PlugInfo *info = (const PlugInfo *)(data->getBytesNoCopy());
327             fPCRSpace->freeInputPlug(info->fPlug);
328             fInputPlugs->removeObject(data);
329        }
330        fInputPlugs->release();
331    }
332    if(fOutputPlugs) {
333        OSData *data;
334        while(data = OSDynamicCast(OSData, fOutputPlugs->getAnyObject())) {
335             const PlugInfo *info = (const PlugInfo *)(data->getBytesNoCopy());
336             fPCRSpace->freeOutputPlug(info->fPlug);
337             fOutputPlugs->removeObject(data);
338        }
339        fOutputPlugs->release();
340    }
341    if(fPCRSpace) {
342        fPCRSpace->deactivate();
343        fPCRSpace->release();
344    }
345    if(fAVCTargetSpace) {
346        fAVCTargetSpace->deactivateWithUserClient(this);
347        fAVCTargetSpace->release();
348    }
349
350    IOUserClient::free();
351}
352
353bool IOFireWireAVCProtocolUserClient::start(IOService *provider)
354{
355	OSObject *prop;
356    IOFireWireNub *device;
357
358    FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::start (%p)\n", this));
359
360	device = OSDynamicCast(IOFireWireNub, provider->getProvider());
361    if(!device)
362        return false;
363
364    fBus = device->getBus();
365    fDevice = device;
366
367    // Copy over matching properties from FireWire Unit
368    prop = device->getProperty(gFireWire_GUID);
369    if(prop)
370        setProperty(gFireWire_GUID, prop);
371
372    fInputPlugs = OSSet::withCapacity(1);
373    fOutputPlugs = OSSet::withCapacity(1);
374
375    if(!fInputPlugs || !fOutputPlugs)
376        return false;
377
378    fPCRSpace = IOFireWirePCRSpace::getPCRAddressSpace(fDevice->getBus());
379    if(!fPCRSpace)
380        return false;
381    fPCRSpace->activate();
382
383    fAVCTargetSpace = IOFireWireAVCTargetSpace::getAVCTargetSpace(fDevice->getController());
384    if(!fAVCTargetSpace)
385        return false;
386    fAVCTargetSpace->activateWithUserClient(this);
387
388	// Enable the communication between the PCR space and the Target space objects
389	fPCRSpace->setAVCTargetSpacePointer(fAVCTargetSpace);
390
391    registerService();
392
393    return true;
394}
395
396IOReturn IOFireWireAVCProtocolUserClient::newUserClient( task_t owningTask, void * securityID,
397                                    UInt32 type,  OSDictionary * properties,
398                                    IOUserClient ** handler )
399{
400    FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::newUserClient (%p)\n", this));
401
402	if(fStarted)
403        return kIOReturnStillOpen;
404    retain();
405    *handler = this;
406    fStarted = true;
407    fTask = owningTask;
408
409	// Allow Rosetta based apps access to this user-client
410	if (properties)
411	{
412		properties->setObject("IOUserClientCrossEndianCompatible", kOSBooleanTrue);
413		setProperty("IOUserClientCrossEndianCompatible", kOSBooleanTrue);
414	}
415
416    return kIOReturnSuccess;
417}
418
419// clientClose / clientDied
420//
421//
422
423IOReturn IOFireWireAVCProtocolUserClient::clientClose( void )
424{
425    FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::clientClose (%p)\n", this));
426
427	fStarted = false;
428
429	getProvider()->terminate( kIOServiceRequired );
430
431	return kIOReturnSuccess;
432}
433
434IOReturn IOFireWireAVCProtocolUserClient::clientDied( void )
435{
436    FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::clientDied (%p)\n", this));
437
438    return clientClose();
439}
440
441/**
442 ** Matching methods
443 **/
444bool IOFireWireAVCProtocolUserClient::matchPropertyTable(OSDictionary * table)
445{
446    FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::matchPropertyTable (%p)\n", this));
447
448	//
449    // If the service object wishes to compare some of its properties in its
450    // property table against the supplied matching dictionary,
451    // it should do so in this method and return truth on success.
452    //
453    if (!IOService::matchPropertyTable(table))  return false;
454
455    // We return success if the following expression is true -- individual
456    // comparisions evaluate to truth if the named property is not present
457    // in the supplied matching dictionary.
458
459    bool res = compareProperty(table, gFireWire_GUID);
460    return res;
461}
462
463IOReturn
464IOFireWireAVCProtocolUserClient::sendAVCResponse(UInt32 generation, UInt16 nodeID, const char *buffer, UInt32 size)
465{
466	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::sendAVCResponse (%p)\n", this));
467
468	IOMemoryDescriptor *desc = NULL;
469    IOFWWriteCommand *cmd = NULL;
470    IOReturn status;
471    do {
472        desc = IOMemoryDescriptor::withAddress((void *)buffer,size, kIODirectionOutIn);
473        if(!desc) {
474            status = kIOReturnNoMemory;
475            break;
476        }
477
478		status = desc->prepare();
479		if( status != kIOReturnSuccess )
480		{
481			break;
482		}
483
484        cmd = new IOFWWriteCommand;
485        if(!cmd) {
486            status = kIOReturnNoMemory;
487            break;
488        }
489        if(!cmd->initAll(fDevice->getController(), generation,
490            FWAddress(kCSRRegisterSpaceBaseAddressHi, kFCPResponseAddress, nodeID),
491            desc, NULL, NULL)) {
492            status = kIOReturnNoMemory;
493            break;
494        }
495        status = cmd->submit();
496    } while (false);
497    if(cmd)
498        cmd->release();
499    if(desc)
500        desc->release();
501    return status;
502}
503
504IOReturn
505IOFireWireAVCProtocolUserClient::allocateInputPlug(io_user_reference_t *asyncRef, uint64_t userRefcon, uint64_t *plugPtr)
506{
507    IOReturn status;
508    PlugInfo info;
509    OSData *data;
510
511	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::allocateInputPlug (%p)\n", this));
512
513    data = OSData::withCapacity(sizeof(info));
514    if(!data)
515        return kIOReturnNoMemory;
516    do {
517        info.fPlug = 0x1234;	// Impossible plug
518        status = fPCRSpace->allocateInputPlug(data, forwardPlugWrite, info.fPlug);
519        if(status != kIOReturnSuccess)
520            break;
521        bcopy(asyncRef, info.fCallbackInfo, sizeof(OSAsyncReference64));
522        info.fUserRefcon = userRefcon;
523        info.fClient = this;
524        if(!data->appendBytes(&info, sizeof(info))) {
525            status = kIOReturnNoMemory;
526            break;
527        }
528        if(!fInputPlugs->setObject(data)) {
529            status = kIOReturnNoMemory;
530            break;
531        }
532        *plugPtr = info.fPlug;
533        status = kIOReturnSuccess;
534    } while (false);
535    data->release();	// Either in set or need to clean up.
536    if(status != kIOReturnSuccess && info.fPlug != 0x1234)
537        fPCRSpace->freeInputPlug(info.fPlug);
538    return status;
539}
540
541IOReturn
542IOFireWireAVCProtocolUserClient::allocateOutputPlug(io_user_reference_t *asyncRef, uint64_t userRefcon, uint64_t *plugPtr)
543{
544    IOReturn status;
545    PlugInfo info;
546    OSData *data;
547
548	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::allocateOutputPlug (%p)\n", this));
549
550    data = OSData::withCapacity(sizeof(info));
551    if(!data)
552        return kIOReturnNoMemory;
553    do {
554        info.fPlug = 0x1234;	// Impossible plug
555        status = fPCRSpace->allocateOutputPlug(data, forwardPlugWrite, info.fPlug);
556        if(status != kIOReturnSuccess)
557            break;
558        bcopy(asyncRef, info.fCallbackInfo, sizeof(OSAsyncReference64));
559        info.fUserRefcon = userRefcon;
560        info.fClient = this;
561        if(!data->appendBytes(&info, sizeof(info))) {
562            status = kIOReturnNoMemory;
563            break;
564        }
565        if(!fOutputPlugs->setObject(data)) {
566            status = kIOReturnNoMemory;
567            break;
568        }
569        *plugPtr = info.fPlug;
570        status = kIOReturnSuccess;
571    } while (false);
572    data->release();	// Either in set or need to clean up.
573    if(status != kIOReturnSuccess && info.fPlug != 0x1234)
574        fPCRSpace->freeOutputPlug(info.fPlug);
575    return status;
576}
577
578IOReturn IOFireWireAVCProtocolUserClient::freeInputPlug(UInt32 plug)
579{
580    OSIterator *plugIterator;
581
582	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::freeInputPlug (%p)\n", this));
583
584    plugIterator = OSCollectionIterator::withCollection(fInputPlugs);
585    if( plugIterator) {
586        OSData * data;
587        while( (data = (OSData *)plugIterator->getNextObject())) {
588            const PlugInfo *info = (const PlugInfo *)(data->getBytesNoCopy());
589            if(info->fPlug == plug) {
590                fPCRSpace->freeInputPlug(info->fPlug);
591                fInputPlugs->removeObject(data);
592            }
593        }
594        plugIterator->release();
595    }
596
597    return kIOReturnSuccess;
598}
599
600IOReturn IOFireWireAVCProtocolUserClient::freeOutputPlug(UInt32 plug)
601{
602    OSIterator *plugIterator;
603
604	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::freeOutputPlug (%p)\n", this));
605
606    plugIterator = OSCollectionIterator::withCollection(fOutputPlugs);
607    if( plugIterator) {
608        OSData * data;
609        while( (data = (OSData *)plugIterator->getNextObject())) {
610            const PlugInfo *info = (const PlugInfo *)(data->getBytesNoCopy());
611            if(info->fPlug == plug) {
612                fPCRSpace->freeOutputPlug(info->fPlug);
613                fInputPlugs->removeObject(data);
614            }
615        }
616        plugIterator->release();
617    }
618
619    return kIOReturnSuccess;
620}
621
622IOReturn IOFireWireAVCProtocolUserClient::readInputPlug(UInt32 plug, uint64_t *valPtr)
623{
624	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::readInputPlug (%p)\n", this));
625
626	if(plug > 30)
627        return kIOReturnBadArgument;
628
629    *valPtr = fPCRSpace->readInputPlug(plug);
630    return kIOReturnSuccess;
631}
632
633IOReturn IOFireWireAVCProtocolUserClient::updateInputPlug(UInt32 plug, UInt32 oldVal, UInt32 newVal)
634{
635	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::updateInputPlug (%p)\n", this));
636
637    if(plug > 30)
638        return kIOReturnBadArgument;
639
640    return fPCRSpace->updateInputPlug(plug, oldVal, newVal);
641}
642
643IOReturn IOFireWireAVCProtocolUserClient::readOutputPlug(UInt32 plug, uint64_t *valPtr)
644{
645	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::readOutputPlug (%p)\n",this));
646
647    if(plug > 30)
648        return kIOReturnBadArgument;
649
650    *valPtr = fPCRSpace->readOutputPlug(plug);
651    return kIOReturnSuccess;
652}
653
654IOReturn IOFireWireAVCProtocolUserClient::updateOutputPlug(UInt32 plug, UInt32 oldVal, UInt32 newVal)
655{
656	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::updateOutputPlug (%p)\n", this));
657
658    if(plug > 30)
659        return kIOReturnBadArgument;
660
661    return fPCRSpace->updateOutputPlug(plug, oldVal, newVal);
662}
663
664IOReturn IOFireWireAVCProtocolUserClient::readOutputMasterPlug(uint64_t *valPtr)
665{
666	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::readOutputMasterPlug (%p)\n",this));
667
668    *valPtr = fPCRSpace->readOutputMasterPlug();
669    return kIOReturnSuccess;
670}
671
672IOReturn IOFireWireAVCProtocolUserClient::updateOutputMasterPlug(UInt32 oldVal, UInt32 newVal)
673{
674	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::updateOutputMasterPlug (%p)\n", this));
675
676    return fPCRSpace->updateOutputMasterPlug(oldVal, newVal);
677}
678
679IOReturn IOFireWireAVCProtocolUserClient::readInputMasterPlug(uint64_t *valPtr)
680{
681	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::readInputMasterPlug (%p)\n", this));
682
683    *valPtr = fPCRSpace->readInputMasterPlug();
684    return kIOReturnSuccess;
685}
686
687IOReturn IOFireWireAVCProtocolUserClient::updateInputMasterPlug(UInt32 oldVal, UInt32 newVal)
688{
689	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::updateInputMasterPlug (%p)\n", this));
690
691    return fPCRSpace->updateInputMasterPlug(oldVal, newVal);
692}
693
694IOReturn IOFireWireAVCProtocolUserClient::publishAVCUnitDirectory(void)
695{
696	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::publishAVCUnitDirectory (%p)\n", this));
697
698	return fAVCTargetSpace->publishAVCUnitDirectory();
699}
700
701IOReturn IOFireWireAVCProtocolUserClient::installAVCCommandHandler(io_user_reference_t *asyncRef, uint64_t subUnitTypeAndID, uint64_t opCode, uint64_t callback, uint64_t refCon)
702{
703	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::installAVCCommandHandler (%p)\n", this));
704
705	return fAVCTargetSpace->installAVCCommandHandler(this, avcTargetCommandHandler, asyncRef, subUnitTypeAndID, opCode, callback, refCon);
706}
707
708IOReturn IOFireWireAVCProtocolUserClient::addSubunit(io_user_reference_t *asyncRef,
709													 uint64_t subunitType,
710													 uint64_t numSourcePlugs,
711													 uint64_t numDestPlugs,
712													 uint64_t callBack,
713													 uint64_t refCon,
714													 uint64_t *subUnitTypeAndID)
715{
716    IOReturn res = kIOReturnSuccess;
717	UInt32 subUnitID = 0x00;
718
719	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::addSubunit (%p)\n", this));
720
721	res = fAVCTargetSpace->addSubunit(this,
722								   avcSubunitPlugHandler,
723								   asyncRef,
724								   subunitType,
725								   numSourcePlugs,
726								   numDestPlugs,
727								   callBack,
728								   refCon,
729								   &subUnitID);
730	if (res == kIOReturnSuccess)
731		*subUnitTypeAndID = subUnitID;
732
733    return res;
734}
735
736IOReturn IOFireWireAVCProtocolUserClient::setSubunitPlugSignalFormat(UInt32 subunitTypeAndID,
737																	 IOFWAVCPlugTypes plugType,
738																	 UInt32 plugNum,
739																	 UInt32 signalFormat)
740{
741	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::setSubunitPlugSignalFormat (%p)\n", this));
742
743	return fAVCTargetSpace->setSubunitPlugSignalFormat(this,subunitTypeAndID, plugType, plugNum, signalFormat);
744}
745
746IOReturn IOFireWireAVCProtocolUserClient::getSubunitPlugSignalFormat(UInt32 subunitTypeAndID,
747											IOFWAVCPlugTypes plugType,
748											UInt32 plugNum,
749											uint64_t *pSignalFormat)
750{
751	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::getSubunitPlugSignalFormat (%p)\n", this));
752
753	UInt32 signalFormat;
754	IOReturn status;
755
756	status = fAVCTargetSpace->getSubunitPlugSignalFormat(this,subunitTypeAndID, plugType, plugNum, &signalFormat);
757
758	*pSignalFormat = signalFormat;
759
760	return status;
761}
762
763IOReturn IOFireWireAVCProtocolUserClient::connectTargetPlugs(AVCConnectTargetPlugsInParams *inParams,
764															 AVCConnectTargetPlugsOutParams *outParams)
765{
766	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::connectTargetPlugs (%p)\n", this));
767
768	return fAVCTargetSpace->connectTargetPlugs(this,inParams,outParams);
769}
770
771IOReturn IOFireWireAVCProtocolUserClient::disconnectTargetPlugs(UInt32 sourceSubunitTypeAndID,
772									   IOFWAVCPlugTypes sourcePlugType,
773									   UInt32 sourcePlugNum,
774									   UInt32 destSubunitTypeAndID,
775									   IOFWAVCPlugTypes destPlugType,
776									   UInt32 destPlugNum)
777{
778	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::disconnectTargetPlugs (%p)\n", this));
779
780	return fAVCTargetSpace->disconnectTargetPlugs(this,
781											   sourceSubunitTypeAndID,
782											   sourcePlugType,
783											   sourcePlugNum,
784											   destSubunitTypeAndID,
785											   destPlugType,
786											   destPlugNum);
787}
788
789IOReturn IOFireWireAVCProtocolUserClient::getTargetPlugConnection(AVCGetTargetPlugConnectionInParams *inParams,
790																  AVCGetTargetPlugConnectionOutParams *outParams)
791{
792	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::getTargetPlugConnection (%p)\n", this));
793
794	return fAVCTargetSpace->getTargetPlugConnection(this,inParams,outParams);
795}
796
797IOReturn IOFireWireAVCProtocolUserClient::AVCRequestNotHandled(UInt32 generation,
798									  UInt16 nodeID,
799									  IOFWSpeed speed,
800									  UInt32 handlerSearchIndex,
801									  const char *pCmdBuf,
802									  UInt32 cmdLen)
803{
804	FIRELOG_MSG(( "IOFireWireAVCProtocolUserClient::AVCRequestNotHandled (%p)\n", this));
805
806	fAVCTargetSpace->findAVCRequestHandler(this,
807							 generation,
808							 nodeID,
809							 speed,
810							 handlerSearchIndex,
811							 pCmdBuf,
812							 cmdLen);
813
814	return kIOReturnSuccess;
815}
816
817
818