1/*
2 * Copyright (c) 1998-2002 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) 1999-2002 Apple Computer, Inc.  All rights reserved.
24 *
25 * HISTORY
26 *
27 */
28
29#ifndef _IOKIT_IOFIREWIRECONTROLLER_H
30#define _IOKIT_IOFIREWIRECONTROLLER_H
31
32#ifndef FIREWIREPRIVATE
33#warning Please do not include this file. Include IOFireWireBus.h instead.
34#endif
35
36#include <IOKit/IOEventSource.h>
37#include <IOKit/firewire/IOFireWireBus.h>
38#include <IOKit/firewire/IOFireWireFamilyCommon.h>
39#include <IOKit/firewire/IOFireWireIRMAllocation.h>
40#include <IOKit/firewire/IOFWPHYPacketListener.h>
41#include <IOKit/firewire/IOFireWireMultiIsochReceive.h>
42
43class OSData;
44class IOWorkLoop;
45class IOEventSource;
46class IOFWQEventSource;
47class IOTimerEventSource;
48class IOMemoryDescriptor;
49class IOFireWireController;
50class IOFWAddressSpace;
51class IOFWPseudoAddressSpace;
52class IOFireWireNub;
53class IOFireWireDevice;
54class IOFireWireDeviceAux;
55class IOFireWireUnit;
56class IODCLProgram;
57class IOLocalConfigDirectory;
58class IOFireWireLink;
59class IOFireWireSBP2ORB;
60class IOFireWireSBP2Login;
61class IOFireWireROMCache;
62class IOFireWireLocalNode;
63class IOFWWorkLoop;
64class IOFireWireIRM;
65class IOFireWirePowerManager;
66class IOFWSimplePhysicalAddressSpace;
67class IOFWSimpleContiguousPhysicalAddressSpace;
68class IOFWAsyncStreamReceiver;
69class IOFWAsyncStreamListener;
70class IOFWUserVectorCommand;
71class IOFWAsyncPHYCommand;
72class IOFWPHYPacketListener;
73class IOFWUserPHYPacketListener;
74
75#if FIRELOGCORE
76class IOFireLog;
77class IOFireLogPublisher;
78#endif
79
80const UInt32 kMaxWaitForValidSelfID = 20; // Still invalid SelfID after 20 retries
81
82// Phy packet defs.
83
84enum
85{
86	kFWPhyPacketID					= FWBitRange (0, 1),
87	kFWPhyPacketIDPhase				= FWBitRangePhase (0, 1),
88
89	kFWPhyPacketPhyID				= FWBitRange (2, 7),
90	kFWPhyPacketPhyIDPhase			= FWBitRangePhase (2, 7)
91};
92
93enum
94{
95	kSelfIDPacketSize				= 8,
96	kMaxSelfIDs						= 4	// SelfID 0,1,3,8
97};
98
99enum
100{
101	kFWConfigurationPacketID		= 0,
102	kFWLinkOnPacketID				= 1,
103	kFWSelfIDPacketID				= 2
104};
105
106enum
107{
108	kFWPhyConfigurationR					= FW_BIT(8),
109	kFWPhyConfigurationT					= FW_BIT(9),
110	kFWPhyConfigurationGapCnt				= FWBitRange (10, 15),
111	kFWPhyConfigurationGapCntPhase			= FWBitRangePhase (10, 15)
112};
113
114enum
115{
116	kFWSelfIDPortStatusChild				= 3,
117	kFWSelfIDPortStatusParent				= 2,
118	kFWSelfIDPortStatusNotConnected			= 1,
119	kFWSelfIDPortStatusNotPresent			= 0,
120
121	kFWSelfIDNoPower						= 0,
122	kFWSelfIDSelfPowered15W					= 1,
123	kFWSelfIDSelfPowered30W					= 2,
124	kFWSelfIDSelfPowered45W					= 3,
125	kFWSelfIDBusPowered1W					= 4,
126	kFWSelfIDBusPowered3W					= 5,
127	kFWSelfIDBusPowered6W					= 6,
128	kFWSelfIDBusPowered10W					= 7,
129
130	kFWSelfIDPhyID							= kFWPhyPacketPhyID,//zzz do we need or want this?
131	kFWSelfIDPhyIDPhase						= kFWPhyPacketPhyIDPhase,
132	kFWSelfIDM								= FW_BIT(31),
133
134	kFWSelfID0L								= FW_BIT(9),
135	kFWSelfID0GapCnt						= FWBitRange (10, 15),
136	kFWSelfID0GapCntPhase					= FWBitRangePhase (10, 15),
137	kFWSelfID0SP							= FWBitRange (16, 17),
138	kFWSelfID0SPPhase						= FWBitRangePhase (16, 17),
139	kFWSelfID0Del							= FWBitRange (18, 19),
140	kFWSelfID0DelPhase						= FWBitRangePhase (18, 19),
141	kFWSelfID0C								= FW_BIT(20),
142	kFWSelfID0Pwr							= FWBitRange (21, 23),
143	kFWSelfID0PwrPhase						= FWBitRangePhase (21, 23),
144	kFWSelfID0P0							= FWBitRange (24, 25),
145	kFWSelfID0P0Phase						= FWBitRangePhase (24, 25),
146	kFWSelfID0P1							= FWBitRange (26, 27),
147	kFWSelfID0P1Phase						= FWBitRangePhase (26, 27),
148	kFWSelfID0P2							= FWBitRange (28, 29),
149	kFWSelfID0P2Phase						= FWBitRangePhase (28, 29),
150	kFWSelfID0I								= FW_BIT(30),
151
152	kFWSelfIDPacketType						= FW_BIT(8),
153	kFWSelfIDNN								= FWBitRange (9, 11),
154	kFWSelfIDNNPhase						= FWBitRangePhase (9, 11),
155	kFWSelfIDNPa							= FWBitRange (14, 15),
156	kFWSelfIDNPaPhase						= FWBitRangePhase (14, 15),
157	kFWSelfIDNPb							= FWBitRange (16, 17),
158	kFWSelfIDNPbPhase						= FWBitRangePhase (16, 17),
159	kFWSelfIDNPc							= FWBitRange (18, 19),
160	kFWSelfIDNPcPhase						= FWBitRangePhase (18, 19),
161	kFWSelfIDNPd							= FWBitRange (20, 21),
162	kFWSelfIDNPdPhase						= FWBitRangePhase (20, 21),
163	kFWSelfIDNPe							= FWBitRange (22, 23),
164	kFWSelfIDNPePhase						= FWBitRangePhase (22, 23),
165	kFWSelfIDNPf							= FWBitRange (24, 25),
166	kFWSelfIDNPfPhase						= FWBitRangePhase (24, 25),
167	kFWSelfIDNPg							= FWBitRange (26, 27),
168	kFWSelfIDNPgPhase						= FWBitRangePhase (26, 27),
169	kFWSelfIDNPh							= FWBitRange (28, 29),
170	kFWSelfIDNPhPhase						= FWBitRangePhase (28, 29),
171	kFWSelfIDMore							= FW_BIT(31)
172};
173
174// Primary packet defs.
175enum
176{
177	kFWPacketTCode							= FWBitRange (24, 27),
178	kFWPacketTCodePhase						= FWBitRangePhase (24, 27)
179};
180
181
182enum
183{
184	kFWAsynchSpd							= FWBitRange (14, 15),
185	kFWAsynchSpdPhase						= FWBitRangePhase (14, 15),
186
187	kFWAsynchTLabel							= FWBitRange (16, 21),
188	kFWAsynchTLabelPhase					= FWBitRangePhase (16, 21),
189	kFWAsynchTTotal 						= ((0xffffffff & kFWAsynchTLabel) >> kFWAsynchTLabelPhase)+1,
190	kFWAsynchRt								= FWBitRange (22, 23),
191	kFWAsynchRtPhase						= FWBitRangePhase (22, 23),
192	kFWAsynchNew							= 0,
193	kFWAsynchRetryA							= 2,
194	kTIAsycnhRetryB							= 3,
195
196	kFWAsynchPriority						= FWBitRange (28, 31),
197	kFWAsynchPriorityPhase					= FWBitRangePhase (28, 31),
198
199	kFWAsynchDestinationID					= FWBitRange (0, 15),
200	kFWAsynchDestinationIDPhase				= FWBitRangePhase (0, 15),
201
202	kFWAsynchSourceID						= FWBitRange (0, 15),
203	kFWAsynchSourceIDPhase					= FWBitRangePhase (0, 15),
204
205	kFWAsynchDestinationOffsetHigh			= FWBitRange (16, 31),
206	kFWAsynchDestinationOffsetHighPhase		= FWBitRangePhase (16, 31),
207
208	kFWAsynchDestinationOffsetLow			= FWBitRange (0, 31),
209	kFWAsynchDestinationOffsetLowPhase		= FWBitRangePhase (0, 31),
210
211	kFWAsynchDataLength						= FWBitRange (0, 15),
212	kFWAsynchDataLengthPhase				= FWBitRangePhase (0, 15),
213
214	kFWAsynchExtendedTCode					= FWBitRange (16, 31),
215	kFWAsynchExtendedTCodePhase				= FWBitRangePhase (16, 31),
216
217	kFWAsynchAckSent						= FWBitRange (28, 31),
218	kFWAsynchAckSentPhase					= FWBitRangePhase (28, 31),
219
220	kFWAsynchRCode							= FWBitRange (16, 19),
221	kFWAsynchRCodePhase						= FWBitRangePhase (16, 19)
222};
223
224enum
225{
226	kFWTCodeWriteQuadlet					= 0,
227	kFWTCodeWriteBlock						= 1,
228	kFWTCodeWriteResponse					= 2,
229	kFWTCodeReadQuadlet						= 4,
230	kFWTCodeReadBlock						= 5,
231	kFWTCodeReadQuadletResponse				= 6,
232	kFWTCodeReadBlockResponse				= 7,
233	kFWTCodeCycleStart						= 8,
234	kFWTCodeLock							= 9,
235	kFWTCodeIsochronousBlock				= 10,
236	kFWTCodeLockResponse					= 11,
237	kFWTCodePHYPacket						= 14
238};
239
240enum
241{
242	kFWExtendedTCodeMaskSwap				= 1,
243	kFWExtendedTCodeCompareSwap				= 2,
244	kFWExtendedTCodeFetchAdd				= 3,
245	kFWExtendedTCodeLittleAdd				= 4,
246	kFWExtendedTCodeBoundedAdd				= 5,
247	kFWExtendedTCodeWrapAdd					= 6,
248	kFWExtendedTCodeVendorDependent			= 7
249};
250
251// debug boot-arg constants
252enum
253{
254	kFWDebugIgnoreNodeNone					= 0xFFFFFFFF
255};
256
257struct AsyncPendingTrans {
258    IOFWAsyncCommand *	fHandler;
259    IOFWCommand *		fAltHandler;
260    int			fTCode;
261    bool		fInUse;
262};
263
264struct IOFWNodeScan {
265    IOFireWireController 	*	fControl;
266    FWAddress					fAddr;
267    UInt32						fBuf[5];	// Enough for bus info block
268    UInt32 					*	fSelfIDs;
269    int							fNumSelfIDs;
270    int							fROMSize;
271    int							fRead;
272    IOFWReadQuadCommand 	* 	fCmd;
273	IOFWCompareAndSwapCommand * fLockCmd;
274	UInt32						generation;
275    UInt32						fIRMBitBucketOld;
276    UInt32						fIRMBitBucketNew;
277    bool						fIRMisBad;
278    bool						speedChecking;
279    bool						fContenderNeedsChecking;
280    bool						fIRMCheckingRead;
281    bool						fIRMCheckingLock;
282	int							fRetriesBumped;
283	bool						fMustNotBeRoot;
284};
285
286
287typedef struct IOFWDuplicateGUIDStruct IOFWDuplicateGUIDRec;
288struct IOFWDuplicateGUIDStruct
289 {
290	IOFWDuplicateGUIDRec		* 	fNextGUID;
291	CSRNodeUniqueID				fGUID;
292	UInt32						fLastGenSeen;
293};
294
295
296// IOFireWireDuplicateGUIDList
297//
298// A little class for keeping track of GUIDs which where we have observed 2 nodes with
299// the same GUID
300
301class IOFireWireDuplicateGUIDList : public OSObject
302{
303    OSDeclareDefaultStructors(IOFireWireDuplicateGUIDList);
304
305private:
306    IOFWDuplicateGUIDRec		* 	fFirstGUID;
307
308protected:
309    virtual void free();
310
311public:
312
313	static IOFireWireDuplicateGUIDList * create( void );
314
315	void addDuplicateGUID( CSRNodeUniqueID guid, UInt32 gen );
316	void removeDuplicateGUID( CSRNodeUniqueID guid );
317
318	bool findDuplicateGUID( CSRNodeUniqueID guid, UInt32 gen );
319
320};
321
322#define kMaxPendingTransfers kFWAsynchTTotal
323
324class IOFireWireController;
325
326#pragma mark -
327
328/*!
329	@class IOFireWireControllerAux
330*/
331
332class IOFireWireControllerAux : public IOFireWireBusAux
333{
334    OSDeclareDefaultStructors(IOFireWireControllerAux)
335
336	friend class IOFireWireController;
337
338protected:
339
340	IOFireWireController * 		fPrimary;
341
342	UInt8						fMaxRec;
343
344	UInt8						fPadding;
345	UInt16						fPadding2;
346
347	IOFWUserObjectExporter *	fSessionRefExporter;
348
349	/*!
350		@struct ExpansionData
351		@discussion This structure will be used to expand the capablilties of the class in the future.
352    */
353
354    struct ExpansionData { };
355
356	/*!
357		@var reserved
358		Reserved for future use.  (Internal use only)
359	*/
360
361	ExpansionData * reserved;
362
363    virtual bool 									init (
364																IOFireWireController * 	primary );
365	virtual	void 									free ();
366	virtual IOFWDCLPool *							createDCLPool ( unsigned capacity ) const ;
367	virtual UInt8									getMaxRec( void );
368
369	virtual UInt64 getFireWirePhysicalAddressMask( void );
370	virtual UInt32 getFireWirePhysicalAddressBits( void );
371	virtual UInt64 getFireWirePhysicalBufferMask( void );
372	virtual UInt32 getFireWirePhysicalBufferBits( void );
373
374	virtual IOFWSimpleContiguousPhysicalAddressSpace * createSimpleContiguousPhysicalAddressSpace( vm_size_t size, IODirection direction );
375	virtual IOFWSimplePhysicalAddressSpace * createSimplePhysicalAddressSpace( vm_size_t size, IODirection direction );
376
377	virtual IOFWUserObjectExporter * getSessionRefExporter( void );
378
379private:
380    OSMetaClassDeclareReservedUnused(IOFireWireControllerAux, 0);
381    OSMetaClassDeclareReservedUnused(IOFireWireControllerAux, 1);
382    OSMetaClassDeclareReservedUnused(IOFireWireControllerAux, 2);
383    OSMetaClassDeclareReservedUnused(IOFireWireControllerAux, 3);
384    OSMetaClassDeclareReservedUnused(IOFireWireControllerAux, 4);
385    OSMetaClassDeclareReservedUnused(IOFireWireControllerAux, 5);
386    OSMetaClassDeclareReservedUnused(IOFireWireControllerAux, 6);
387    OSMetaClassDeclareReservedUnused(IOFireWireControllerAux, 7);
388
389};
390
391
392#pragma mark -
393
394/*! @class IOFireWireController
395*/
396class IOFireWireController : public IOFireWireBus
397{
398    OSDeclareAbstractStructors(IOFireWireController)
399
400protected:
401    enum busState {
402        kStarting = 0,
403		kAsleep,			// Link off, zzzzzz
404		kWaitingBusReset,
405        kWaitingSelfIDs,	// Bus has been reset, no selfIDs yet
406        kWaitingScan,		// Got selfIDs, waiting a bit before hitting lame devices
407        kScanning,			// Reading node ROMs
408        kWaitingPrune,		// Read all ROMs, pausing before pruning missing devices
409        kRunning,			// Normal happy state,
410		kWaitingBusResetStart	// bus reset is desired, but not yet sent to the fwim
411    };
412
413	enum ResetState
414	{
415		kResetStateResetting,
416		kResetStateDisabled,
417		kResetStateArbitrated
418	};
419
420	enum
421	{
422		kDisablePhysicalAccess 	= (1 << 0)
423	};
424
425    struct timeoutQ: public IOFWCmdQ
426    {
427        IOTimerEventSource *fTimer;
428        virtual void headChanged(IOFWCommand *oldHead);
429        void busReset();
430    };
431
432    struct pendingQ: public IOFWCmdQ
433    {
434        IOFWQEventSource *fSource;
435        virtual void headChanged(IOFWCommand *oldHead);
436    };
437
438    friend class IOFireWireLink;
439	friend class IOFireWireDevice;
440	friend class IOFireWireDeviceAux;
441	friend class IOFWAddressSpace;
442	friend class IOFWAddressSpaceAux;
443    friend class IOFWPseudoAddressSpace;
444    friend class IOFireWireSBP2ORB;
445	friend class IOFireWireSBP2Login;
446	friend class IOFWLocalIsochPort;
447	friend class IOFWCommand;
448    friend class IOFireWireUnit;
449	friend class IOFireWirePCRSpace;
450    friend class IOFireWireROMCache;
451    friend class IOFWAsyncStreamCommand;
452	friend class IOFireWireAVCLocalUnit;
453	friend class IOFireWireAVCUnit;
454    friend class IOFireWireAVCCommand;
455	friend class IOFireWirePowerManager;
456	friend class IOFWWriteQuadCommand;
457	friend class IOFWWriteCommand;
458	friend class IOFWCompareAndSwapCommand;
459	friend class IOFWAsyncCommand;
460	friend class IOFireWireAVCTargetSpace;
461	friend class AppleFWOHCI;
462	friend class IOFireWireNub;
463	friend class IOFWAsyncStreamListener;
464	friend class IOFireWireLocalNode;
465	friend class IOFireWireIRMAllocation;
466	friend class IOFWUserVectorCommand;
467	friend class IOFWAsyncPHYCommand;
468	friend class IOFWUserPHYPacketListener;
469	friend class IOFWAsyncStreamReceiver;
470
471#if FIRELOGCORE
472	friend class IOFireLog;
473#endif
474
475    IOFireWireLink *			fFWIM;
476    IOFWWorkLoop *				fWorkLoop;
477    IOTimerEventSource *		fTimer;
478    OSSet *						fLocalAddresses;	// Collection of local adress spaces
479    OSIterator *				fSpaceIterator;		// Iterator over local addr spaces
480
481    OSSet *						fAllocatedChannels;	// Need to be informed of bus resets
482    OSIterator *				fAllocChannelIterator;	// Iterator over channels
483
484	OSSet *						fIRMAllocations;	// Need to be informed of bus resets
485    OSIterator *				fIRMAllocationsIterator;	// Iterator over channels
486	OSSet *						fIRMAllocationsAllocated;	// Need to be informed of bus resets
487
488    // Bus management variables (although we aren't a FireWire Bus Manager...)
489    AbsoluteTime				fResetTime;		// Time of last reset
490    UInt32						fBusGeneration;		// ID of current bus topology.
491    UInt16						fLocalNodeID;		// ID of local node, ie. this computer
492    UInt16						fRootNodeID;		// ID of root, ie. highest node id in use.
493    UInt16						fIRMNodeID;		// ID of Isochronous resource manager, or kFWBadNodeID
494    bool						fBusMgr;		// true if at least one node is bus manager capable
495    IORegistryEntry *			fNodes[kFWMaxNodesPerBus];	// FireWire nodes on this bus
496    UInt32 *					fNodeIDs[kFWMaxNodesPerBus+1];	// Pointer to SelfID list for each node
497							// +1 so we know how many selfIDs the last node has
498
499    UInt32						fGapCount;		// What we think the gap count should be
500    //UInt8						fSpeedCodes[(kFWMaxNodesPerBus+1)*kFWMaxNodesPerBus];
501    UInt8						fSpeedVector[((kFWMaxNodesPerBus+1)*kFWMaxNodesPerBus)/2];
502						// Max speed between two nodes
503    busState					fBusState;		// Which state are we in?
504    int							fNumROMReads;		// Number of device ROMs we are still reading
505    // SelfIDs
506    int							fNumSelfIDs;		// Total number of SelfID packets
507    UInt32						fSelfIDs[kMaxSelfIDs*kFWMaxNodesPerBus];
508
509    // The local device's Config ROM
510    UInt32						fROMHeader[5];		// More or less fixed header and bus info block
511    IOLocalConfigDirectory *	fRootDir;		// Local Config ROM root directory.
512
513    // log base 2 of maximum packet size the FWIM can send/receive
514    // Normally calculated from bus info block.
515    int	fMaxSendLog;
516    int fMaxRecvLog;
517
518    IOFWAddressSpace *			fROMAddrSpace;
519    IOMemoryDescriptor *		fBadReadResponse;	// Send back easily identified bad data to out of range addrs.
520
521    // Array for outstanding requests (up to 64)
522    AsyncPendingTrans			fTrans[kMaxPendingTransfers];
523    int							fLastTrans;
524
525    // queue for executing commands that may timeout
526    timeoutQ					fTimeoutQ;
527
528    // queue for commands that can't execute yet
529    pendingQ					fPendingQ;
530
531    // queue for async commands interrupted by bus reset
532    IOFWCmdQ					fAfterResetHandledQ;
533
534    // Command to change bus state after a delay.
535    IOFWDelayCommand *			fDelayedStateChangeCmd;
536    bool						fDelayedStateChangeCmdNeedAbort;
537
538	UInt32						fDelayedPhyPacket;
539	bool						fBusResetScheduled;
540	ResetState					fBusResetState;
541	IOFWDelayCommand *			fBusResetStateChangeCmd;
542	UInt32						fBusResetDisabledCount;
543
544#if FIRELOGCORE
545    IOFireLogPublisher *		fFireLogPublisher;
546#else
547    void *						fFireLogPublisher;
548#endif
549
550    OSData *					fAllocatedAddresses;
551
552	UInt32						fDevicePruneDelay;
553
554	IOFWPhysicalAccessMode		fPhysicalAccessMode;
555	IOFWSecurityMode			fSecurityMode;
556	IONotifier *				fKeyswitchNotifier;
557
558	IOFireWireIRM *				fIRM;
559	IOFireWirePowerManager *	fBusPowerManager;
560
561	bool						fGapCountMismatch;
562
563	bool						fUseHalfSizePackets;
564	bool						fRequestedHalfSizePackets;
565
566	IOFWNodeScan *					fScans[kFWMaxNodesPerBus];
567	IOFireWireDuplicateGUIDList	*	fGUIDDups;
568
569	bool						fDelegateCycleMaster;
570	bool						fBadIRMsKnown;
571
572	UInt32						fPreviousGap;
573
574	UInt32						fOutOfTLabels;
575	UInt32						fOutOfTLabels10S;
576	UInt32						fOutOfTLabelsThreshold;
577
578#ifdef LEGACY_SHUTDOWN
579	IONotifier *				fPowerEventNotifier;
580#endif
581
582	bool						fStarted;
583
584	UInt32						fIOCriticalSectionCount;
585	UInt32						fHubPort;
586	UInt32						fDebugIgnoreNode;
587
588	OSSet *						fLocalAsyncStreamReceivers;
589    OSIterator *				fAsyncStreamReceiverIterator;
590
591	bool						fInstantiated;
592
593	IOReturn					fStartStatus;
594	UInt32						fWaitingForSelfID;
595
596	UInt32						fForcedRootNodeID;
597	bool						fNodeMustBeRootFlag;
598	bool						fNodeMustNotBeRootFlag;
599
600	UInt32						fForcedGapCount;
601	bool						fForcedGapFlag;
602
603	OSSet *						fPHYPacketListeners;
604 	OSIterator *				fPHYPacketListenersIterator;
605
606	bool						fDSLimited;
607
608	IONotifier *				fConsoleLockNotifier;
609	IOFireWireLocalNode *       fLocalNode;
610
611/*! @struct ExpansionData
612    @discussion This structure will be used to expand the capablilties of the class in the future.
613    */
614    struct ExpansionData { };
615
616/*! @var reserved
617    Reserved for future use.  (Internal use only)  */
618    ExpansionData *reserved;
619
620    static void clockTick(OSObject *, IOTimerEventSource *);
621    static void readROMGlue(void *refcon, IOReturn status,
622			IOFireWireNub *device, IOFWCommand *fwCmd);
623    static void delayedStateChange(void *refcon, IOReturn status,
624                                    IOFireWireBus *bus, IOFWBusCommand *fwCmd);
625
626    virtual void processBusReset();
627    virtual void processSelfIDs(UInt32 *IDs, int numIDs, UInt32 *ownIDs, int numOwnIDs);
628    virtual void processTimeout(IOTimerEventSource *src);
629    virtual void processRcvPacket( UInt32 *data, int numQuads, IOFWSpeed speed );
630    virtual void processWriteRequest(UInt16 sourceID, UInt32 tlabel,
631				UInt32 *hdr, void *buf, int len, IOFWSpeed speed);
632    virtual void processLockRequest(UInt16 sourceID, UInt32 tlabel,
633				UInt32 *hdr, void *buf, int len, IOFWSpeed speed);
634
635    // Process read from a local address, return rcode
636    virtual UInt32 doReadSpace(UInt16 nodeID, IOFWSpeed &speed, FWAddress addr, UInt32 len,
637                                      IOMemoryDescriptor **buf, IOByteCount * offset, IODMACommand **dma_command,
638                                      IOFWRequestRefCon refcon);
639
640    // Process write to a local address, return rcode
641    virtual UInt32 doWriteSpace(UInt16 nodeID, IOFWSpeed &speed, FWAddress addr, UInt32 len,
642                                const void *buf, IOFWRequestRefCon refcon);
643
644    // Process lock to a local address, return rcode
645    UInt32 doLockSpace(UInt16 nodeID, IOFWSpeed &speed, FWAddress addr, UInt32 inlen,
646                                             const UInt32 *newVal, UInt32 &outLen, UInt32 *oldVal,
647                                             UInt32 extType, IOFWRequestRefCon refcon);
648
649    virtual void updatePlane();
650    virtual void startBusScan();
651
652    // Called when all devices on bus have been examined
653    virtual void finishedBusScan();
654
655    virtual void buildTopology(bool doFWPlane);
656
657    virtual void readDeviceROM(IOFWNodeScan *refCon, IOReturn status);
658
659    virtual IOReturn UpdateROM();
660    virtual IOReturn allocAddress(IOFWAddressSpace *space);
661    virtual void freeAddress(IOFWAddressSpace *space);
662
663	IOFireWireBusAux * createAuxiliary( void );
664
665public:
666
667    // Initialization
668    virtual bool init(IOFireWireLink *fwim);
669    virtual void free();
670    virtual bool start(IOService *provider);
671    virtual void stop( IOService * provider );
672    virtual bool finalize( IOOptionBits options );
673    virtual bool requestTerminate( IOService * provider, IOOptionBits options );
674
675	// Power management
676    virtual IOReturn setPowerState ( unsigned long powerStateOrdinal, IOService* whatDevice );
677
678    // Implement IOService::getWorkLoop
679    virtual IOWorkLoop *getWorkLoop() const;
680
681    // Allocate struct for tracking a transaction
682    virtual AsyncPendingTrans *allocTrans(IOFWAsyncCommand *cmd=NULL);
683    virtual void freeTrans(AsyncPendingTrans *trans);
684
685    // Really public methods
686
687    virtual IOReturn getCycleTime(UInt32 &cycleTime);
688    virtual IOReturn getBusCycleTime(UInt32 &busTime, UInt32 &cycleTime);
689
690    // Methods to manipulate the local Config ROM
691    virtual IOReturn AddUnitDirectory(IOLocalConfigDirectory *unitDir);
692    virtual IOReturn RemoveUnitDirectory(IOLocalConfigDirectory *unitDir);
693
694    // Cause a bus reset
695    virtual IOReturn resetBus();
696
697    // Send async request packets
698    virtual IOReturn asyncRead(	UInt32 				generation,
699								UInt16 				nodeID,
700								UInt16 				addrHi,
701								UInt32 				addrLo,
702                                int 				speed,
703								int 				label,
704								int 				size,
705								IOFWAsyncCommand *	cmd );
706
707    virtual IOReturn asyncWrite(	UInt32 					generation,
708									UInt16 					nodeID,
709									UInt16 					addrHi,
710									UInt32 					addrLo,
711									int 					speed,
712									int 					label,
713									IOMemoryDescriptor *	buf,
714									IOByteCount 			offset,
715									int 					size,
716									IOFWAsyncCommand *		cmd );
717
718    /* DEPRECATED */ virtual IOReturn asyncWrite(	UInt32 				generation,
719	/* DEPRECATED */								UInt16 				nodeID,
720	/* DEPRECATED */								UInt16 				addrHi,
721	/* DEPRECATED */								UInt32 				addrLo,
722	/* DEPRECATED */								int 				speed,
723	/* DEPRECATED */								int 				label,
724	/* DEPRECATED */								void *				data,
725	/* DEPRECATED */								int 				size,
726	/* DEPRECATED */								IOFWAsyncCommand *	cmd );
727
728    /* DEPRECATED */ virtual IOReturn asyncLock(	UInt32 				generation,
729	/* DEPRECATED */								UInt16 				nodeID,
730	/* DEPRECATED */								UInt16 				addrHi,
731	/* DEPRECATED */								UInt32 				addrLo,
732	/* DEPRECATED */								int 				speed,
733	/* DEPRECATED */								int 				label,
734	/* DEPRECATED */								int 				type,
735	/* DEPRECATED */								void *				data,
736	/* DEPRECATED */								int 				size,
737	/* DEPRECATED */								IOFWAsyncCommand *	cmd);
738
739
740    // Send async read response packets
741    // useful for pseudo address spaces that require servicing outside the FireWire work loop.
742    virtual IOReturn asyncReadResponse(	UInt32 					generation,
743										UInt16 					nodeID,
744										int 					speed,
745										IOMemoryDescriptor *	buf,
746										IOByteCount 			offset,
747										int 					len,
748										IOFWRequestRefCon 		refcon );
749
750    virtual IOReturn asyncLockResponse( UInt32 					generation,
751										UInt16 					nodeID,
752										int 					speed,
753                                        IOMemoryDescriptor *	buf,
754										IOByteCount 			offset,
755										int 					len,
756                                        IOFWRequestRefCon 		refcon );
757
758    // Try to fix whatever might have caused the other device to not respond
759    virtual IOReturn handleAsyncTimeout(IOFWAsyncCommand *cmd);
760
761    // Convert a firewire nodeID into the IOFireWireDevice for it
762    virtual IOFireWireDevice * nodeIDtoDevice(UInt32 generation, UInt16 nodeID);
763
764    // Add/remove a channel from the list informed of bus resets
765    virtual void addAllocatedChannel(IOFWIsochChannel *channel);
766    virtual void removeAllocatedChannel(IOFWIsochChannel *channel);
767
768	// Add/remove a IRM allocation from the list informed of bus resets
769    virtual void addIRMAllocation(IOFireWireIRMAllocation *irmAllocation);
770    virtual void removeIRMAllocation(IOFireWireIRMAllocation *irmAllocation);
771
772    // Create an Isochronous Channel object
773    // doIRM = true => allocate channel and bandwith in Isochronous Resource Manager
774    // packetSize packet size (in bytes), used to calculate bandwidth needed.
775    virtual IOFWIsochChannel *createIsochChannel(
776	bool doIRM, UInt32 packetSize, IOFWSpeed prefSpeed,
777	FWIsochChannelForceStopNotificationProc stopProc=NULL,
778	void *stopRefCon=NULL);
779
780    // Create a local isochronous port to run the given DCL program
781    // if task is 0, the DCL program is for the kernel task,
782    // otherwise all DCL pointers are valid in the specified task.
783    // opcodes is also pointer valid in the specified task.
784    virtual IOFWLocalIsochPort *createLocalIsochPort(bool talking,
785        DCLCommand* opcodes, DCLTaskInfo *info = 0,
786	UInt32 startEvent = 0, UInt32 startState = 0, UInt32 startMask = 0);
787
788    // Execute specified function on workloop after specified delay
789    // Returned command is for delay, call it's cancel() function to cancel timeout.
790    virtual IOFWDelayCommand * createDelayedCmd(UInt32 uSecDelay, FWBusCallback func, void *refcon);
791
792    virtual IOFWPhysicalAddressSpace *createPhysicalAddressSpace(IOMemoryDescriptor *mem);
793    virtual IOFWPseudoAddressSpace *createPseudoAddressSpace(FWAddress *addr, UInt32 len,
794                                FWReadCallback reader, FWWriteCallback writer, void *refcon);
795
796    // Extract info about the async request
797    virtual bool isLockRequest(IOFWRequestRefCon refcon);
798    virtual bool isQuadRequest(IOFWRequestRefCon refcon);
799    virtual UInt32 getExtendedTCode(IOFWRequestRefCon refcon);
800
801    // Inline accessors for protected member variables
802    IOFWCmdQ &getTimeoutQ();
803	IOFWCmdQ &getPendingQ();
804    IOFWCmdQ &getAfterResetHandledQ();
805    IOFireWireLink * getLink() const;
806
807    IOLocalConfigDirectory *getRootDir() const;
808    bool checkGeneration(UInt32 gen) const;
809    UInt32 getGeneration() const;
810    UInt16 getLocalNodeID() const;
811    IOReturn getIRMNodeID(UInt32 &generation, UInt16 &id);
812
813    const AbsoluteTime * getResetTime() const;
814
815    IOFWSpeed FWSpeed(UInt16 nodeAddress) const;
816    IOFWSpeed FWSpeed(UInt16 nodeA, UInt16 nodeB) const;
817
818    // How big (as a power of two) can packets sent to/received from the node be?
819    virtual int maxPackLog(bool forSend, UInt16 nodeAddress) const;
820
821    // How big (as a power of two) can packets sent from A to B be?
822    virtual int maxPackLog(UInt16 nodeA, UInt16 nodeB) const;
823
824   // Force given node to be root (via root holdoff Phy packet)
825    virtual IOReturn makeRoot(UInt32 generation, UInt16 nodeID) ;
826
827    virtual IOFWPseudoAddressSpace *createInitialAddressSpace(UInt32 addressLo, UInt32 len,
828                                FWReadCallback reader, FWWriteCallback writer, void *refcon);
829
830    virtual IOFWAddressSpace *getAddressSpace(FWAddress address);
831
832    // Extract info about the async request - was the request ack'ed complete already?
833    virtual bool isCompleteRequest(IOFWRequestRefCon refcon);
834
835    // Are we currently scanning the bus?
836    bool scanningBus() const;
837
838protected:
839
840    void openGate();
841    void closeGate();
842
843protected:
844	virtual void doBusReset( void );
845	static void resetStateChange( void *refcon, IOReturn status,
846								   IOFireWireBus *bus, IOFWBusCommand *fwCmd);
847
848public:
849	virtual IOReturn disableSoftwareBusResets( void );
850	virtual void enableSoftwareBusResets( void );
851
852    virtual IOFWAsyncStreamCommand * createAsyncStreamCommand( UInt32 generation,
853    			UInt32 channel, UInt32 sync, UInt32 tag, IOMemoryDescriptor *hostMem,
854				UInt32 size, int speed,FWAsyncStreamCallback completion, void *refcon);
855
856	virtual	IOReturn asyncStreamWrite(UInt32 generation,
857                    int speed, int tag, int sync, int channel,
858                    IOMemoryDescriptor *buf, IOByteCount offset,
859                	int size, IOFWAsyncStreamCommand *cmd);
860
861protected:
862	bool inGate();
863
864    virtual IOReturn allocatePseudoAddress(FWAddress *addr, UInt32 lenDummy);
865    virtual void freePseudoAddress(FWAddress addr, UInt32 lenDummy);
866
867	virtual IORegistryEntry * createDummyRegistryEntry( IOFWNodeScan *scan );
868
869	static IOFireWireLocalNode * getLocalNode(IOFireWireController *control);
870
871	virtual void setPhysicalAccessMode( IOFWPhysicalAccessMode mode );
872	virtual IOFWPhysicalAccessMode getPhysicalAccessMode( void );
873	virtual void physicalAccessProcessBusReset( void );
874	virtual void setNodeIDPhysicalFilter( UInt16 nodeID, bool state );
875
876	virtual void initSecurity( void );
877	virtual void freeSecurity( void );
878	static bool serverKeyswitchCallback( void * target, void * refCon, IOService * service, IONotifier * notifier );
879	virtual void setSecurityMode( IOFWSecurityMode mode );
880	virtual IOFWSecurityMode getSecurityMode( void );
881
882	virtual IOReturn createTimeoutQ( void );
883	virtual void destroyTimeoutQ( void );
884	virtual IOReturn createPendingQ( void );
885	virtual void destroyPendingQ( void );
886
887	virtual UInt32 countNodeIDChildren( UInt16 nodeID, int hub_port = 0, int * hubChildRemainder = NULL, bool * hubParentFlag = NULL );
888
889public:
890	virtual UInt32 hopCount(UInt16 nodeAAddress, UInt16 nodeBAddress );
891	virtual UInt32 hopCount(UInt16 nodeAAddress );
892
893	virtual IOFireWirePowerManager * getBusPowerManager( void );
894
895protected:
896	virtual void handleARxReqIntComplete();
897
898    virtual IOReturn asyncLock(	UInt32 					generation,
899								UInt16 					nodeID,
900								UInt16 					addrHi,
901								UInt32 					addrLo,
902								int 					speed,
903								int 					label,
904								int 					type,
905								IOMemoryDescriptor *	buf,
906								IOByteCount 			offset,
907								int 					size,
908								IOFWAsyncCommand *		cmd );
909
910    virtual IOReturn asyncWrite(	UInt32 					generation,
911									UInt16 					nodeID,
912									UInt16 					addrHi,
913									UInt32 					addrLo,
914									int 					speed,
915									int 					label,
916									IOMemoryDescriptor *	buf,
917									IOByteCount 			offset,
918									int 					size,
919									IOFWAsyncCommand *		cmd,
920									IOFWWriteFlags 			flags );
921
922protected:
923	bool delayedStateCommandInUse() const;
924	void enterBusResetDisabledState( );
925
926	virtual UInt32 getPortNumberFromIndex( UInt16 index );
927
928    virtual bool checkForDuplicateGUID(IOFWNodeScan *scan, CSRNodeUniqueID *currentGUIDs );
929    virtual void updateDevice(IOFWNodeScan *scan );
930    virtual bool AssignCycleMaster();
931
932public:
933
934 	IOReturn clipMaxRec2K(Boolean clipMaxRec );
935	void setNodeSpeed( UInt16 nodeAddress, IOFWSpeed speed );
936	void useHalfSizePackets( void );
937	void disablePhyPortOnSleepForNodeID( UInt32 nodeID );
938
939	IOReturn handleAsyncCompletion( IOFWCommand *cmd, IOReturn status );
940	void processCycle64Int();
941
942#ifdef LEGACY_SHUTDOWN
943	static IOReturn systemShutDownHandler( void * target, void * refCon,
944                                    UInt32 messageType, IOService * service,
945                                    void * messageArgument, vm_size_t argSize );
946#else
947    virtual void systemWillShutdown( IOOptionBits specifier );
948#endif
949
950	IOReturn beginIOCriticalSection( void );
951	void endIOCriticalSection( void );
952
953protected:
954	IOReturn poweredStart( void );
955	void setNodeSpeed( UInt16 nodeA, UInt16 nodeB, UInt8 speed );
956	void setNodeSpeed( UInt16 nodeAddress, UInt8 speed );
957
958public:
959	bool isPhysicalAccessEnabledForNodeID( UInt16 nodeID );
960
961	// Allocate IRM bandwidth if the specified generation is the current FireWire generation.
962	IOReturn allocateIRMBandwidthInGeneration(UInt32 bandwidthUnits, UInt32 generation) ;
963
964	// Release IRM bandwidth if the specified generation is the current FireWire generation.
965	IOReturn releaseIRMBandwidthInGeneration(UInt32 bandwidthUnits, UInt32 generation) ;
966
967	// Allocate IRM channel if the specified generation is the current FireWire generation.
968	IOReturn allocateIRMChannelInGeneration(UInt8 isochChannel, UInt32 generation) ;
969
970	// Release IRM channel if the specified generation is the current FireWire generation.
971	IOReturn releaseIRMChannelInGeneration(UInt8 isochChannel, UInt32 generation) ;
972
973	// Create an IOFireWireIRMAllocation object which can be used to allocate isoch resources that are automatically reallocated after bus-resets!
974	IOFireWireIRMAllocation *createIRMAllocation(Boolean releaseIRMResourcesOnFree = true,
975												IOFireWireIRMAllocation::AllocationLostNotificationProc allocationLostProc = NULL,
976												void *pLostNotificationProcRefCon = NULL);
977
978	IOFWAsyncStreamListener *createAsyncStreamListener( UInt32	channel, FWAsyncStreamReceiveCallback proc, void *refcon );
979
980	void removeAsyncStreamListener( IOFWAsyncStreamListener *listener );
981
982	IOFWSpeed getBroadcastSpeed(){ return FWSpeed( fLocalNodeID ); };
983
984private:
985
986	IOFWAsyncStreamReceiver *allocAsyncStreamReceiver( UInt32 channel, FWAsyncStreamReceiveCallback proc, void *refcon );
987
988	IOFWAsyncStreamReceiver *getAsyncStreamReceiver( UInt32 channel );
989
990	void freeAllAsyncStreamReceiver();
991
992	void activateAsyncStreamReceivers();
993
994	void deactivateAsyncStreamReceivers();
995
996protected:
997	IOService *findKeyswitchDevice( void );
998	void suspendBus( void );
999
1000public:
1001	virtual IOReturn			asyncRead(	UInt32 				generation,
1002											UInt16 				nodeID,
1003											UInt16 				addrHi,
1004											UInt32 				addrLo,
1005											int 				speed,
1006											int 				label,
1007											int 				size,
1008											IOFWAsyncCommand *	cmd,
1009											IOFWReadFlags		flags );
1010
1011	void checkProgress( void );
1012
1013	void terminateDevice( IOFireWireDevice * device );
1014
1015	void nodeMustBeRoot( UInt32 nodeID );
1016
1017	void nodeMustNotBeRoot( UInt32 nodeID );
1018
1019	void setGapCount( UInt32	gapCount );
1020
1021	IOReturn asyncPHYPacket(	UInt32					generation,
1022								UInt32					data,
1023								UInt32					data2,
1024								IOFWAsyncPHYCommand *	cmd );
1025
1026    IOFWAsyncPHYCommand * createAsyncPHYCommand(	UInt32				generation,
1027													UInt32				data1,
1028													UInt32				data2,
1029													FWAsyncPHYCallback	completion,
1030													void *				refcon,
1031													bool				failOnReset );
1032
1033private:
1034	AsyncPendingTrans * allocTrans( IOFWAsyncCommand * cmd, IOFWCommand * altcmd );
1035
1036public:
1037
1038	IOReturn activatePHYPacketListener( IOFWPHYPacketListener * listener );
1039	void deactivatePHYPacketListener( IOFWPHYPacketListener * listener );
1040
1041	IOFWPHYPacketListener * createPHYPacketListener( FWPHYPacketCallback proc, void * refcon );
1042
1043private:
1044	void processPHYPacket( UInt32 data1, UInt32 data2 );
1045	void enterLoggingMode( void );
1046
1047public:
1048	IOReturn getCycleTimeAndUpTime( UInt32 &cycleTime, UInt64 &uptime );
1049
1050protected:
1051	void removeAsyncStreamReceiver( IOFWAsyncStreamReceiver *receiver );
1052
1053public:
1054
1055	// Create a multi-isoch-receive listener
1056	IOFireWireMultiIsochReceiveListener * createMultiIsochReceiveListener(UInt32 channel,
1057																		  FWMultiIsochReceiveListenerCallback callback,
1058																		  void *pCallbackRefCon,
1059																		  FWMultiIsochReceiveListenerParams *pListenerParams = NULL);
1060
1061	// Activate a multi-isoch-receive listener
1062	IOReturn activateMultiIsochReceiveListener(IOFireWireMultiIsochReceiveListener *pListener);
1063
1064	// Deactivate a multi-isoch-receive listener
1065	IOReturn deactivateMultiIsochReceiveListener(IOFireWireMultiIsochReceiveListener *pListener);
1066
1067	// Call for client to specify he is done with a multi-isoch receiver isoch packet
1068	void clientDoneWithMultiIsochReceivePacket(IOFireWireMultiIsochReceivePacket *pPacket);
1069
1070public:
1071    virtual IOFWAsyncStreamCommand * createAsyncStreamCommand( UInt32 generation,
1072    			UInt32 channel, UInt32 sync, UInt32 tag, IOMemoryDescriptor *hostMem,
1073				UInt32 size, int speed,FWAsyncStreamCallback completion, void *refcon, bool	failOnReset);
1074
1075private:
1076	void addToIRMAllocationSet(IOFireWireIRMAllocation *anObject);
1077	void removeFromIRMAllocationSet(IOFireWireIRMAllocation *anObject);
1078
1079	static IOReturn consoleLockInterestHandler( void * target, void * refCon,
1080									 UInt32 messageType, IOService * provider,
1081									 void * messageArgument, vm_size_t argSize );
1082
1083protected:
1084	OSMetaClassDeclareReservedUnused(IOFireWireController, 0);
1085    OSMetaClassDeclareReservedUnused(IOFireWireController, 1);
1086    OSMetaClassDeclareReservedUnused(IOFireWireController, 2);
1087    OSMetaClassDeclareReservedUnused(IOFireWireController, 3);
1088    OSMetaClassDeclareReservedUnused(IOFireWireController, 4);
1089    OSMetaClassDeclareReservedUnused(IOFireWireController, 5);
1090    OSMetaClassDeclareReservedUnused(IOFireWireController, 6);
1091    OSMetaClassDeclareReservedUnused(IOFireWireController, 7);
1092    OSMetaClassDeclareReservedUnused(IOFireWireController, 8);
1093
1094};
1095
1096#endif /* ! _IOKIT_IOFIREWIRECONTROLLER_H */
1097