1/*
2 * Copyright (c) 2010 Apple Inc. All rights reserved.
3 *
4 * @APPLE_LICENSE_HEADER_START@
5 *
6 * This file contains Original Code and/or Modifications of Original Code
7 * as defined in and that are subject to the Apple Public Source License
8 * Version 2.0 (the 'License'). You may not use this file except in
9 * compliance with the License. Please obtain a copy of the License at
10 * http://www.opensource.apple.com/apsl/ and read it before using this
11 * file.
12 *
13 * The Original Code and all software distributed under the License are
14 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
15 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
16 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
18 * Please see the License for the specific language governing rights and
19 * limitations under the License.
20 *
21 * @APPLE_LICENSE_HEADER_END@
22 */
23
24									ISOCHRONOUS COMPONENTS REFERENCE v1.0 3/16/2001
25									(INITIAL DOCUMENTATION - SUBJECT TO CHANGE)
26
27
28Header Files: IsochronousDataHandler.h, DeviceControl.h
29Framework:	 DVComponentGlue
30
31
32
33
34
35Component Types for Isoch Components
36------------------------------------
37
38	#define kIDHComponentType 	'ihlr'		/* Component type*/
39	#define	kIDHSubtypeDV		'dv  '		/* Subtype for DV (over FireWire)*/
40
41
42
43Data Types for Isoch Components
44-------------------------------
45
46The callback function prototype:
47
48	typedef OSStatus (*IDHNotificationProc)(IDHGenericEvent *event, void *userData);
49
50	FieldDecriptions:
51
52	event - a IDHGenericEvent that is returned from the Isoch component. If this is an IDHRead() or
53			IDHWrite() notification function, then 'event' is the address of the IDHParameterBlock
54			that was passed to the IDHRead()/IDHWrite() call.
55
56	userData - If this is an IDHRead() or IDHWrite() notification function, the userData returned will
57	           be the 'refCon' field of the IDHParameterBlock.	Otherwise, it will be the value specified
58	           in the IDHNewNotification() function.
59
60
61
62The parameter block passed to IDHRead() and IDHWrite():
63
64	struct IDHParameterBlock {
65		UInt32 					reserved1;			/* reserved by Apple */
66		UInt16 					reserved2;			/* reserved by Apple */
67		void *					buffer;				/* buffer used in read/write operation */
68		ByteCount 				requestedCount;		/* bytes required to read/write */
69		ByteCount 				actualCount;		/* actual bytes read/written */
70		IDHNotificationProc 	completionProc;		/* called after read/write complete */
71		void *					refCon;				/* user specified data */
72		OSErr 					result;				/* result of read/write */
73	};
74
75	Field Descriptions
76
77	reserved1, reserved2 - reserved by Apple
78
79	buffer - can contain an address of a user supplied buffer or 'nil'.
80		 In reads: if 'buffer' is supplied, the data is read into the buffer
81
82		           if 'buffer' is 'nil', a buffer address is returned in the completion proc
83		           and the client has control of the buffer until it is released by
84		           the IDHReleaseBuffer() function. NOTE: The buffer will remain valid for
85				   an indeterminate amount of time. The client should USE the buffer ASAP to
86				   guarantee data integrity
87
88		 In writes: If 'buffer' is supplied, the data from the buffer is written to the
89		            isoch device.
90
91		            If 'buffer' is 'nil', a buffer address is supplied to the client on
92		            callback. The client then writes his data into the buffer and returns
93		            control to the IDH component. The data is then written to the device.
94
95	requestedCount - contains the number of bytes requested to read or write.
96
97	actualCount - the actual number of bytes read or written from/to the device.
98
99	completionProc - the routine that is called after read or write completion. If the completionProc
100					 parameter is set to 'nil', the function becomes synchronous and does not return
101					 until the read/write is complete. It is NOT possible to have a synchronous write/ 'nil'
102					 buffer operation.
103
104	refCon - user data that is returned to the completion proc.
105
106	result - result of IDHRead()/IDHWrite() operation.
107
108
109Error Codes (see functions for actual meanings)
110-----------------------------------------------
111
112	#define	kIDHErrDeviceDisconnected	-14101
113	#define	kIDHErrInvalidDeviceID		-14102
114	#define	kIDHErrDeviceInUse			-14104
115	#define	kIDHErrDeviceNotOpened		-14105
116	#define	kIDHErrDeviceReadError		-14107
117	#define	kIDHErrDeviceWriteError		-14108
118	#define	kIDHErrDeviceNotConfigured	-14109
119	#define	kIDHErrDeviceList			-14110
120	#define	kIDHErrCompletionPending	-14111
121	#define	kIDHErrDeviceTimeout		-14112
122	#define	kIDHErrInvalidIndex			-14113
123	#define	kIDHErrDeviceCantRead		-14114
124	#define	kIDHErrDeviceCantWrite		-14115
125
126
127Isochronous Component Atoms
128---------------------------
129
130	#define kIDHDeviceAtomType							'devc'	/* QTAtom - contains the description for a device */
131	#define	kIDHDeviceIDType							'dvid'	/* UInt32 - contains the device ID referenced in notification events */
132	#define kIDHIsochServiceAtomType					'isoc'	/* QTAtom - contains the isoch configs for a device */
133	#define kIDHIsochModeAtomType						'mode'	/* QTAtom - contains isoch configuration atoms */
134	#define kIDHIsochVersionAtomType					'iver'	/* UInt32 - contains the version of the isoch component */
135	#define kIDHUseCMPAtomType	 						'ucmp'	/* UInt32 - true when using CMP */
136	#define kIDHUniqueIDType							'unid'	/* variable size - contains a unique ID associated with device */
137	#define kIDHNameAtomType							'name'	/* Str255 - contains the name of the device */
138	#define kIDHIsochMediaType							'av  '	/* OSType - kIDHSoundMediaAtomType or kIDHVideoMediaAtomType */
139	#define kIDHDataTypeAtomType						'dtyp'	/* OSType - a configuration identifier */
140	#define kIDHDefaultIOType							'dfio'	/* UInt32 - set for default read or write config */
141	#define kIDHDataSizeAtomType						'dsiz'	/* UInt32 - the size of a frame of data */
142	#define kIDHDataBufferSizeAtomType					'dbuf'	/* UInt32 - the size of a packet of data*/
143	#define kIDHDataIntervalAtomType					'intv'	/* float - frame rate i.e. 29.97fps */
144	#define kIDHDataIODirectionAtomType					'ddir'	/* long - I/O direction associated with the device
145	    															kIDHDataTypeIsInput	is 1
146																	kIDHDataTypeIsOutput is 2
147																	kIDHDataTypeIsInputAndOutput is 4 */
148	#define kIDHSoundChannelCountAtomType 				'ccnt'	/* long - number of audio channels */
149	#define kIDHSoundSampleSizeAtomType					'ssiz'	/* long - number of bytes per sample of audio */
150	#define kIDHSoundSampleRateAtomType					'srat'	/* Fixed - audio sample rate */
151	#define kIDHVideoDimensionsAtomType					'dimn'	/* IDHDimension - pixel dimension of video */
152	#define kIDHVideoResolutionAtomType					'resl'	/* IDHResolution - DPI resolution */
153	#define kIDHVideoRefreshRateAtomType 				'refr'	/* Fixed - video refresh rate */
154	#define kIDHVideoPixelTypeAtomType					'pixl'	/* OSType - Quicktime pixel type */
155	#define kIDHVideoDecompressorTypeAtomType 			'dety'	/* OSType - Quicktime decompressor type */
156	#define kIDHVideoDecompressorComponentAtomType 		'cmpt'	/* Component - Quicktime decompressor */
157
158	Atom Layout
159	-----------
160	deviceList - QTAtomContainer
161		kIDHIsochVersionAtomType (r)
162		kIDHUseCMPAtomType (r/w)
163		kIDHDeviceAtomType (r)
164			kIDHDeviceIDType (r)
165			kIDHUniqueIDType (r)
166			kIDHNameAtomType (r/w)
167			kIDHDefaultIOType (r/w)
168			kIDHIsochServiceAtomType (r)
169				kIDHIsochModeAtomType (r)
170					kIDHDataTypeAtomType (r)
171					kIDHDataSizeAtomType (r)
172					kIDHDataBufferSizeAtomType		(r)
173					kIDHDataBufferSizeAtomType		(r)
174					kIDHDataIntervalAtomType		(r)
175					kIDHDataIODirectionAtomType		(r)
176					kIDHSoundChannelCountAtomType	(r)
177					kIDHSoundSampleSizeAtomType		(r)
178					kIDHSoundSampleRateAtomType		(r)
179				kIDHIsochModeAtomType	 (r)
180					kIDHDataTypeAtomType			(r)
181					kIDHDataSizeAtomType			(r)
182					kIDHDataBufferSizeAtomType		(r)
183					kIDHDataBufferSizeAtomType		(r)
184					kIDHDataIntervalAtomType		(r)
185					kIDHDataIODirectionAtomType		(r)
186					kIDHVideoDimensionsAtomType		(r)
187					kIDHVideoResolutionAtomType		(r)
188					kIDHVideoRefreshRateAtomType	(r)
189					kIDHVideoPixelTypeAtomType		(r)
190					kIDHVideoDecompressorTypeAtomType	(r)
191					kIDHVideoDecompressorComponentAtomType	(r)
192		kIDHDeviceAtomType
193					...
194
195	Note: (r) - read only, (r/w) - read/write
196
197
198Device Status Structure
199
200	struct IDHDeviceStatus {
201		UInt32 							version;				/* version of structure */
202		Boolean 						physicallyConnected;	/* device is connected and active */
203		Boolean 						readEnabled;			/* device has been enabled for read */
204		Boolean 						writeEnabled;			/* device has been enabled for writing */
205		Boolean 						exclusiveAccess;		/* a client has opened device for exclusive access */
206		UInt32 							currentBandwidth;		/* ??? */
207		UInt32 							currentChannel;			/* ??? */
208		PsuedoID 						localNodeID;			/* the ID associated with this device */
209		SInt16 							inputStandard;			/* ntscIn is 0 or palIn is 1 */
210		Boolean 						deviceActive;			/* device is being used by another client */
211	};
212
213
214
215Notification Structures
216
217
218	struct IDHEventHeader {
219		IDHDeviceID 					deviceID;					/* a unique device ID */
220		IDHNotificationID 				notificationID;				/* notification ID associated this callback */
221		IDHEvent 						event;						/* The event */
222	};
223
224	struct IDHGenericEvent {
225		IDHEventHeader 					eventHeader;				/* as described above */
226		UInt32 							pad[4];
227	};
228
229	struct IDHDeviceConnectionEvent {
230		IDHEventHeader 					eventHeader;
231	};
232
233	struct IDHDeviceIOEnableEvent {
234		IDHEventHeader 					eventHeader;
235	};
236
237
238Notification Events
239
240	#define kIDHEventInvalid			0,
241	#define kIDHEventDeviceAdded		1L << 0						/* Uses IDHDeviceConnectionEvent*/
242	#define kIDHEventDeviceRemoved		1L << 1						/* Uses IDHDeviceConnectionEvent*/
243	#define kIDHEventDeviceChanged		1L << 2						/* Uses ????*/
244	#define kIDHEventReadEnabled		1L << 3						/* Uses IDHDeviceIOEnableEvent*/
245	#define kIDHEventReserved1			1L << 4						/* Reserved for future use*/
246	#define kIDHEventReadDisabled		1L << 5						/* Uses IDHDeviceIOEnableEvent*/
247	#define kIDHEventWriteEnabled		1L << 6						/* Uses IDHDeviceIOEnableEvent*/
248	#define kIDHEventReserved2			1L << 7						/* Reserved for future use*/
249	#define kIDHEventWriteDisabled		1L << 8						/* Uses IDHDeviceIOEnableEvent*/
250	#define kIDHEventEveryEvent			(long)0xFFFFFFFF
251
252
253
254
255									Isochronous Component Functions
256									===============================
257
258Getting device information and choosing a device
259
260IDHGetDeviceList
261----------------
262
263	The IDHGetDeviceList function returns an atom list of the devices that are currently active.
264
265	pascal ComponentResult IDHGetDeviceList( ComponentInstance idh, QTAtomContainer *deviceList)
266
267	idh - Specifies the IDH component for operation. You can obtain this identifier from the
268		  ComponentManager's OpenComponent() function.
269
270	deviceList - An atom container that describes each of the devices that support this isoch component.
271	             The atom structure is defined above. The user must free this atom container using
272	             QTRemoveChildren() and QTDisposeAtomContainer() when finished.
273
274	Result Codes:
275		Quicktime error codes
276
277IDHUpdateDeviceList
278-------------------
279
280	The IDHUpdateDeviceList function allows the client to change certain atoms within the internal atom list.
281
282	pascal ComponentResult IDHUpdateDeviceList( ComponentInstance idh, QTAtomContainer *deviceList)
283
284	idh - Specifies the IDH component for operation. You can obtain this identifier from the
285		  ComponentManager's OpenComponent() function.
286
287	deviceList - An atom container that was returned from IDHGetDeviceList(). The client has modified one
288				 or more atoms identified as (r/w).
289
290	Result Codes:
291		kIDHErrDeviceList		The device list is either stale or corrupt. Please IDHGetDeviceList().
292		Quicktime error codes
293
294IDHSetDeviceConfiguration
295-------------------------
296
297	The IDHSetDeviceConfiguration function allows the user to choose a specific configuration of a device
298	for reads or writes. The configuration structure is defined in the atom description above.
299
300	pascal ComponentResult IDHSetDeviceConfiguration( ComponentInstance idh, const QTAtomSpec *configurationID)
301
302	idh - Specifies the IDH component for operation. You can obtain this identifier from the
303		  ComponentManager's OpenComponent() function.
304
305	configurationID - Specifies the requested configuration. The user passes an QTAtomSpec which is
306	                  an atom container/ kIDHIsochModeAtomType atom pair. NOTE: The user must NOT dispose
307	                  of the device list (requested by IDHGetDeviceList()) until he is through with this
308	                  configuration.
309
310	Result Codes:
311		kIDHErrDeviceInUse		Another device has already been opened. Please IDHCloseDevice().
312		kIDHErrDeviceList		The device list is either stale or corrupt. Please IDHGetDeviceList().
313		kIDHErrInvalidDeviceID	Internal Error
314		kAlreadyEnabledErr		Device control has already been enabled on this device
315		kNotEnabledErr			Device control is not enabled
316
317IDHGetDeviceConfiguration
318-------------------------
319
320	The IDHGetDeviceConfiguration function returns the configuration that the client set using the
321	IDHSetDeviceConfiguration() call.
322
323	pascal ComponentResult IDHGetDeviceConfiguration( ComponentInstance idh, QTAtomSpec *configurationID)
324
325	idh - Specifies the IDH component for operation. You can obtain this identifier from the
326		  ComponentManager's OpenComponent() function.
327
328	configurationID - Contains the previously specified configuration. The function returns an QTAtomSpec
329					  which is an atom container/ kIDHIsochModeAtomType atom pair. NOTE: The user must NOT
330					  dispose the device list (requested by IDHGetDeviceList()) until he is through with this
331	                  configuration.
332
333	Result Codes:
334		kIDHErrDeviceNotConfigured	A device has not already been selected using IDHSetDeviceConfiguration()
335
336
337Opening and closing a device
338
339IDHOpenDevice
340-------------
341
342	The IDHOpenDevice function opens the currently configured device.
343
344	pascal ComponentResult IDHOpenDevice( ComponentInstance idh, UInt32 permissions)
345
346	idh - Specifies the IDH component for operation. You can obtain this identifier from the
347		  ComponentManager's OpenComponent() function.
348
349	permissions - The user specifies a combination of the following flags when opening a device.
350
351		kIDHOpenForReadTransactions	- Indicates that the device will be opened for reads. The value of
352		this flag is 1. One or more clients can open a device for reads unless a client specifies
353		the	kIDHOpenWithExclusiveAccess flag.
354
355		kIDHOpenForWriteTransactions - Indicates that the device will be opened for writes. The value of
356		this flag is 0x2. Note: Only one client can open a device for writes.
357
358		kIDHOpenWithExclusiveAccess	- Indicates that the device cannot be opened by another client. The
359		value of this flag is 0x4.
360
361	Result Codes:
362		kIDHErrDeviceNotConfigured	A device has not already been selected using IDHSetDeviceConfiguration()
363		kIDHErrInvalidDeviceID		Internal Error
364		kIDHErrDeviceInUse			Device has been exclusively opened by another client. Or it has already been
365									in another state.
366		kIDHErrInvalidIndex			Internal Error
367
368IDHCloseDevice
369--------------
370
371	The IDHCloseDevice function closes the previously opened IDH device.
372
373	pascal ComponentResult IDHCloseDevice( ComponentInstance idh)
374
375	idh - Specifies the IDH component for operation. You can obtain this identifier from the
376		  ComponentManager's OpenComponent() function.
377
378	Result Codes:
379		kIDHErrDeviceNotConfigured	A device has not already been selected using IDHSetDeviceConfiguration()
380		kIDHErrInvalidDeviceID		Internal Error
381		kIDHErrDeviceNotOpened		A device has not been opened
382
383
384Device I/O
385
386IDHRead
387-------
388
389	The IDHRead function reads data from the currently opened device configuration.
390
391	pascal ComponentResult IDHRead( ComponentInstance idh, IDHParameterBlock *pb)
392
393	idh - Specifies the IDH component for operation. You can obtain this identifier from the
394		  ComponentManager's OpenComponent() function.
395
396	pb - Specifies the address of a IDHParameterBlock structure. Each of the fields are described in detail
397	     in a previous section. The user should keep the IDHParameterBlock around until the completion routine
398	     is called.   NOTE: On a 'nil' buffer read, the buffer will remain valid for an indeterminate
399		 amount of time. The client should USE the buffer ASAP to guarantee data integrity.
400
401	Result Codes:
402		kIDHErrDeviceNotConfigured	A device has not already been selected using IDHSetDeviceConfiguration()
403		kIDHErrInvalidDeviceID		Internal Error
404		kIDHErrDeviceTimeout		Timeout on synchronous read
405
406
407IDHWrite
408--------
409
410	The IDHWrite function writes data to the currently opened device configuration.
411
412	pascal ComponentResult IDHWrite( ComponentInstance idh, IDHParameterBlock *pb)
413
414	idh - Specifies the IDH component for operation. You can obtain this identifier from the
415		  ComponentManager's OpenComponent() function.
416
417	pb - Specifies the address of a IDHParameterBlock structure. Each of the fields are described in detail
418	     in a previous section. The user should keep the IDHParameterBlock around until the completion routine
419	     is called.
420
421	Result Codes:
422		kIDHErrDeviceNotConfigured	A device has not already been selected using IDHSetDeviceConfiguration()
423		kIDHErrInvalidDeviceID		Internal Error
424		kIDHErrDeviceTimeout		Timeout on synchronous read
425
426IDHReleaseBuffer
427----------------
428
429	The IDHReleaseBuffer function releases a buffer returned from an IDHRead() request where
430	the client specified a 'nil' buffer.
431
432	pascal ComponentResult IDHReleaseBuffer( ComponentInstance idh, IDHParameterBlock *pb)
433
434	idh - Specifies the IDH component for operation. You can obtain this identifier from the
435		  ComponentManager's OpenComponent() function.
436
437	pb - Specifies the address of the IDHParameterBlock structure that was originally passed into
438		 IDHRead() function.  NOTE: The buffer will remain valid for an indeterminate amount of time.
439		 The client should USE the buffer ASAP to guarantee data integrity.
440
441	Result Codes:
442		kIDHErrDeviceNotConfigured	A device has not already been selected using IDHSetDeviceConfiguration()
443		kIDHErrInvalidDeviceID		Internal Error
444
445IDHCancelPendingIO
446------------------
447
448	The IDHCancelPendingIO function cancels any outstanding IDHRead() or IDHWrite() requests. This
449	should be called prior to closing a device.
450
451	pascal ComponentResult IDHCancelPendingIO( ComponentInstance idh, IDHParameterBlock *pb)
452
453	idh - Specifies the IDH component for operation. You can obtain this identifier from the
454		  ComponentManager's OpenComponent() function.
455
456	pb - Specifies the address of the IDHParameterBlock structure that was originally passed into
457		 IDHRead() or IDHWrite() function.
458
459	Result Codes:
460		Macintosh errors
461
462
463Getting device status
464
465IDHGetDeviceStatus
466------------------
467
468	The IDHGetDeviceStatus function gets the device status from the specified device configuration.
469
470	pascal ComponentResult IDHGetDeviceStatus( ComponentInstance idh, const QTAtomSpec *configurationID,
471								 IDHDeviceStatus *status)
472
473	idh - Specifies the IDH component for operation. You can obtain this identifier from the
474		  ComponentManager's OpenComponent() function.
475
476	configurationID - The user passes an QTAtomSpec which is an atom container/ kIDHIsochModeAtomType atom
477					  pair. NOTE: The user must NOT dispose of the device list (requested by IDHGetDeviceList())
478					  until he is through with this configuration.
479
480	status - The address of a IDHDeviceStatus structure. The specified device status will be returned. Each
481			 of the status fields are described in detail above.
482
483	Result Codes:
484		kIDHErrDeviceList		The device list is either stale or corrupt. Please IDHGetDeviceList().
485		kIDHErrInvalidDeviceID	Internal Error
486
487
488
489Device Notification
490
491IDHNewNotification
492------------------
493
494	The IDHNewNotification function creates a notification ID which is used to initiate client notification
495	based on device events.
496
497	pascal ComponentResult IDHNewNotification(	ComponentInstance idh, IDHDeviceID deviceID,
498												IDHNotificationProc notificationProc, void *userData,
499												IDHNotificationID *notificationID)
500
501	idh - Specifies the IDH component for operation. You can obtain this identifier from the
502		  ComponentManager's OpenComponent() function.
503
504	deviceID -	the value of a devices kIDHDeviceIDType atom or kIDHDeviceIDEveryDevice.
505
506	notificationProc - the client function that is called when a particular event has taken place
507
508	userData - the client specified data returned to the client notificationProc.
509
510	notificationID - this parameter is returned to the client and used in other IDH functions.
511
512	Result Codes:
513		Macintosh errors
514
515IDHNotifyMeWhen
516---------------
517
518	The IDHNotifyMeWhen function actually enables the notification process. When one of the client specified
519	events occur, the client will be notified through his notification function. NOTE: This function is
520	a one shot. The function must be called again after the event(s) have occured to re-enable the
521	notification.
522
523	pascal ComponentResult IDHNotifyMeWhen( ComponentInstance idh, IDHNotificationID notificationID,
524							IDHEvent events)
525
526
527	idh - Specifies the IDH component for operation. You can obtain this identifier from the
528		  ComponentManager's OpenComponent() function.
529
530	notificationID - this parameter is obtained by calling IDHNewNotification.
531
532	events - one or more flags that the client uses to specify the device events of interest
533		kIDHEventDeviceAdded - Indicates that a new device has been added to the computer. The value of this
534							   flag is 1.
535
536		kIDHEventDeviceRemoved - Indicates that a device has been removed from the computer. The value of this
537								 flag is 2.
538
539		kIDHEventDeviceChanged - Indicates that a device is ???. The value of this flag is 4.
540
541		kIDHEventReadEnabled - Indicates that a device has been enabled for read. The value of this flag
542							   is 8.
543
544		kIDHEventReadDisabled - Indicates that a device has been disabled for read. The value of this flag
545								is 32.
546
547		kIDHEventWriteEnabled - Indicates that a device has been enabled for write. The value of this flag
548								is 64.
549
550		kIDHEventWriteDisabled - Indicates that a device has been disabled for write. The value of this flag
551								 is 256.
552
553	Result Codes:
554		Macintosh Errors
555
556
557IDHCancelNotification
558---------------------
559
560	The IDHCancelNotification function cancels an outstanding IDHNotifyMeWhen() request. This function
561	should be called prior to exiting to avoid spurious calls to the client callback.
562
563	pascal ComponentResult IDHCancelNotification( ComponentInstance idh, IDHNotificationID	notificationID)
564
565	idh - Specifies the IDH component for operation. You can obtain this identifier from the
566		  ComponentManager's OpenComponent() function.
567
568	notificationID - this parameter is obtained by calling IDHNewNotification() and used in IDHNotifyMeWhen().
569
570	Result Codes:
571		Macintosh Errors
572
573IDHDisposeNotification
574----------------------
575
576	The IDHDisposeNotification function releases the resources associated with the IDHNotificationID. This
577	function should be called before closing the isoch component.
578
579	pascal ComponentResult IDHDisposeNotification( ComponentInstance idh, IDHNotificationID notificationID)
580
581	idh - Specifies the IDH component for operation. You can obtain this identifier from the
582		  ComponentManager's OpenComponent() function.
583
584	notificationID - this parameter is obtained by calling IDHNewNotification().
585
586	Result Codes:
587		Macintosh Errors
588
589
590
591Other functions
592
593IDHGetDeviceClock
594-----------------
595
596	The IDHGetDeviceClock function returns a bus specific clock component used in audio/video
597	synchronization. The client should read the Quicktime documentation for information about
598	a Clock Component. The Clock component is used in other Quicktime functions such as video out.
599
600	pascal ComponentResult IDHGetDeviceClock( ComponentInstance idh, Component *clock)
601
602	idh - Specifies the IDH component for operation. You can obtain this identifier from the
603		  ComponentManager's OpenComponent() function.
604
605	clock - returns the Clock component associated with this IDH component.
606
607	Result Codes:
608		kIDHErrDeviceNotConfigured	A device has not already been selected using IDHSetDeviceConfiguration()
609
610IDHGetDeviceControl
611-------------------
612
613	The IDHGetDeviceControl function returns an instance to a device control component associated with
614	the device that was most recently set with IDHSetDeviceConfiguration. See the device control component
615	documentation for more details.
616
617	pascal ComponentResult IDHGetDeviceControl( ComponentInstance idh, ComponentInstance *deviceControl)
618
619	idh - Specifies the IDH component for operation. You can obtain this identifier from the
620		  ComponentManager's OpenComponent() function.
621
622	deviceControl - returns an instance of a device control component.
623
624	Result Codes:
625		kIDHErrDeviceNotConfigured	A device has not already been selected using IDHSetDeviceConfiguration()
626		kIDHErrInvalidDeviceID		Internal Error
627
628
629                                    Device Control Component Reference
630                                    ==================================
631
632Component Types for Device Control Components
633------------------------------------
634
635	#define kDVCComponentType 	'devc'		/* Component type*/
636	#define	kDVCSubtypeDV		'fwdv'		/* Subtype for DV (over FireWire)*/
637
638
639
640Data Types for Device Control Components
641-------------------------------
642
643The parameter block passed to DeviceControlDoAVCTransaction():
644
645typedef UInt32 DCResponseHandler(UInt32 fwCommandObjectID, Ptr responseBuffer, UInt32 responseLength);
646struct DVCTransactionParams {
647    Ptr                             commandBufferPtr;			/* pointer to AVC command bytes */
648    UInt32                          commandLength;				/* command length in bytes */
649    Ptr                             responseBufferPtr;			/* pointer to buffer to store AVC response */
650    UInt32                          responseBufferSize;			/* response buffer size in bytes */
651    DCResponseHandler *             responseHandler;			/* Function to call when device sends response - IGNORED in X 1.0 */
652};
653typedef struct DVCTransactionParams     DVCTransactionParams;
654
655
656									Device Control Component Functions
657									===============================
658DeviceControlDoAVCTransaction
659-----------------------------
660
661    The DeviceControlDoAVCTransaction transaction sends an AV/C command to the device and returns the response sent by the device. 	Documentation on AV/C command and response formats is available from the 1394 Trade Association (www.1394TA.org)
662
663    ComponentResult DeviceControlDoAVCTransaction(ComponentInstance instance, DVCTransactionParams * params)
664
665    instance - specifies the device control component for operation. Obtained from IDHGetDeviceControl().
666    params - parameter block for call.
667
668											SAMPLE CODE
669											===========
670
671
672		NOTE - The isoch component requires QT 4.0 headers and libraries.
673
674		Opening a DV isoch component
675		----------------------------
676
677		ComponentDescription compDesc;
678		Component isochComponent;
679		ComponentInstance isochInstance;
680
681		compDesc.componentType 			= kIDHComponentType;
682		compDesc.componentSubType 		= kIDHSubtypeDV;
683		compDesc.componentManufacturer 	= 0;
684		compDesc.componentFlags 		= 0;
685		compDesc.componentFlagsMask 	= kAnyComponentFlagsMask;
686
687		isochComponent = FindNextComponent( nil, &compDesc);
688		if( isochComponent == nil)
689			goto error;
690
691		isochInstance = OpenComponent( isochComponent);
692		if( isochInstance == nil)
693			goto error;
694
695
696		Finding the first video device in the list
697		------------------------------------------
698
699		QTAtomContainer deviceList;
700		short nDVDevices, i, j, nConfigs;
701		QTAtom deviceAtom, isochAtom;
702		QTAtomSpec currentIsochConfig;
703
704		err = IDHGetDeviceList( isochInstance, &deviceList);
705		if( err != noErr)
706			goto err;
707
708		nDVDevices = QTCountChildrenOfType( deviceList, kParentAtomIsContainer, kIDHDeviceAtomType);
709
710		for( i=0; i<nDVDevices; ++i)
711		{
712			QTAtom deviceAtom, isochAtom;
713			int nConfigs;
714
715			// get the atom to this device
716			deviceAtom = QTFindChildByIndex( deviceList, kParentAtomIsContainer, kIDHDeviceAtomType, i + 1, nil);
717			if( deviceAtom == nil)
718				goto error;
719
720			// find the isoch characteristics for this device
721			isochAtom = QTFindChildByIndex( deviceList, deviceAtom, kIDHIsochServiceAtomType, 1, nil);
722			if( isochAtom == nil)
723				goto error;
724
725			// how many configs exist for this device
726			nConfigs = QTCountChildrenOfType( deviceList, isochAtom, kIDHIsochModeAtomType);
727
728			currentIsochConfig.atom = nil;	// start with no selected config
729
730			// process each config
731			for( j=0; j<nConfigs; ++j)
732			{
733				OSType mediaType;
734				long size;
735				QTAtom configAtom, mediaAtom;
736
737				// get this configs atom
738				configAtom = QTFindChildByIndex( deviceList, isochAtom, kIDHIsochModeAtomType, j + 1, nil);
739				if( configAtom == nil)
740					goto error;
741
742				// find the media type atom
743				mediaAtom = QTFindChildByIndex( deviceList, configAtom, kIDHIsochMediaType, 1, nil);
744				if( mediaAtom == nil)
745					goto error;
746
747				QTLockContainer( deviceList);
748
749				// get the value of the mediaType atom
750				QTCopyAtomDataToPtr( deviceList, mediaAtom, true, sizeof( mediaType), &mediaType, &size);
751
752				QTUnlockContainer( deviceList);
753
754				// is this config an video config?
755				if( mediaType == kIDHVideoMediaAtomType)	// found video device
756				{
757					currentIsochConfig.container = deviceList;	// save this config
758					currentIsochConfig.atom = configAtom;
759					break;
760				}
761			}
762
763			if( currentIsochConfig.atom != nil)	// did we find a video config?
764				break;
765		}
766
767		if( currentIsochConfig.atom == nil)	// no good configs found
768			goto error;
769
770		Setting a configuration and opening a device for reading
771		--------------------------------------------------------
772
773		// set isoch to use this config
774		err = IDHSetDeviceConfiguration( isochInstance, &currentIsochConfig);
775		if( err != noErr)
776			goto error;
777
778		// open the DV device
779		err = IDHOpenDevice( isochInstance, kIDHOpenForReadTransactions);
780		if( err != noErr)
781			goto Exit);
782
783		Reading from a device (client supplies buffer)
784		----------------------------------------------
785
786		// we are doing isoch reads with only one buffer at a time
787		isochParamBlock.buffer 			= myBuffer;
788		isochParamBlock.requestedCount	= 120000;	// NTSC buffer size
789		isochParamBlock.actualCount 	= 0;
790		isochParamBlock.completionProc 	= DVIsochComponentReadCallback;
791		isochParamBlock.refCon		 	= iGlobals;
792
793		err = IDHRead( isochInstance, &isochParamBlock);
794		if( err != noErr)
795			goto error;
796
797		Callback from read request (client supplies buffer)
798		---------------------------------------------------
799
800		// called when a new isoch read is received
801		OSStatus DVIsochComponentReadCallback( IDHGenericEvent *eventRecord, void *userData)
802		{
803			OSErr 					result = noErr;
804			ComponentInstancePtr	iGlobals = userData;
805			IDHParameterBlock		*pb = (IDHParameterBlock *) eventRecord;
806
807			// fill out structure
808			pb->buffer 			= myBuffer;
809			pb->requestedCount	= 120000;
810			pb->actualCount 	= 0;
811			pb->completionProc 	= DVIsochComponentReadCallback;
812			pb->refCon		 	= iGlobals;
813
814			// do another read
815			result = IDHRead( isochInstance, pb);
816			if( result != noErr)
817				goto error;
818
819		error:
820			return result;
821		}
822
823		Reading from a device (isoch component supplies buffer)
824		-------------------------------------------------------
825
826		// we are doing isoch reads with only one buffer at a time
827		isochParamBlock.buffer 			= nil;
828		isochParamBlock.requestedCount	= 120000;	// NTSC buffer size
829		isochParamBlock.actualCount 	= 0;
830		isochParamBlock.completionProc 	= DVIsochComponentReadCallback;
831		isochParamBlock.refCon		 	= iGlobals;
832
833		err = IDHRead( isochInstance, &isochParamBlock);
834		if( err != noErr)
835			goto error;
836
837		Callback from read request (isoch component supplies buffer)
838		------------------------------------------------------------
839
840		// called when a new isoch read is received
841		OSStatus DVIsochComponentReadCallback( IDHGenericEvent *eventRecord, void *userData)
842		{
843			OSErr 					result = noErr;
844			ComponentInstancePtr	iGlobals = userData;
845			IDHParameterBlock		*pb = (IDHParameterBlock *) eventRecord;
846
847			WorkOnData( pb->buffer, pb->actualCount);
848
849			result = IDHReleaseBuffer( isochInstance, pb);
850			if( result != noErr)
851				goto error;
852
853			// fill out structure
854			pb->buffer 			= nil;
855			pb->requestedCount	= 120000;
856			pb->actualCount 	= 0;
857			pb->completionProc 	= DVIsochComponentReadCallback;
858			pb->refCon		 	= iGlobals;
859
860			// do another read
861			result = IDHRead( isochInstance, pb);
862			if( result != noErr)
863				goto error;
864
865		error:
866			return result;
867		}
868
869		Writing to device (client supplies the buffer)
870		----------------------------------------------
871
872		// we are doing isoch reads with only one buffer at a time
873		isochParamBlock.buffer 			= myBuffer;
874		isochParamBlock.requestedCount	= 120000;	// NTSC buffer size
875		isochParamBlock.actualCount 	= 0;
876		isochParamBlock.completionProc 	= DVIsochComponentWriteCallback;
877		isochParamBlock.refCon		 	= iGlobals;
878
879		err = IDHWrite( isochInstance, &isochParamBlock);
880		if( err != noErr)
881			goto error;
882
883		Callback from write request (client supplies the buffer)
884		--------------------------------------------------------
885
886		// called when a new isoch read is received
887		OSStatus DVIsochComponentWriteCallback( IDHGenericEvent *eventRecord, void *userData)
888		{
889			OSErr 					result = noErr;
890			ComponentInstancePtr	iGlobals = userData;
891			IDHParameterBlock		*pb = (IDHParameterBlock *) eventRecord;
892
893			// fill out structure
894			isochParamBlock.buffer 			= myBuffer;
895			isochParamBlock.requestedCount	= 120000;	// NTSC buffer size
896			isochParamBlock.actualCount 	= 0;
897			isochParamBlock.completionProc 	= DVIsochComponentWriteCallback;
898			isochParamBlock.refCon		 	= iGlobals;
899
900			// do another read
901			result = IDHWrite( isochInstance, pb);
902			if( result != noErr)
903				goto error;
904
905		error:
906			return result;
907		}
908
909		Writing to device (isoch component supplies the buffer)
910		-------------------------------------------------------
911
912		// we are doing isoch reads with only one buffer at a time
913		isochParamBlock.buffer 			= nil;
914		isochParamBlock.requestedCount	= 120000;	// NTSC buffer size
915		isochParamBlock.actualCount 	= 0;
916		isochParamBlock.completionProc 	= DVIsochComponentWriteCallback;
917		isochParamBlock.refCon		 	= iGlobals;
918
919		err = IDHWrite( isochInstance, &isochParamBlock);
920		if( err != noErr)
921			goto error;
922
923		Callback from write request (isoch component supplies the buffer)
924		-----------------------------------------------------------------
925
926		// called when a new isoch read is received
927		OSStatus DVIsochComponentWriteCallback( IDHGenericEvent *eventRecord, void *userData)
928		{
929			OSErr 					result = noErr;
930			ComponentInstancePtr	iGlobals = userData;
931			IDHParameterBlock		*pb = (IDHParameterBlock *) eventRecord;
932
933			BlockMove( myBuffer, pb->buffer, 120000);
934
935			// fill out structure
936			isochParamBlock.buffer 			= nil;
937			isochParamBlock.requestedCount	= 120000;	// NTSC buffer size
938			isochParamBlock.actualCount 	= 0;
939			isochParamBlock.completionProc 	= DVIsochComponentWriteCallback;
940			isochParamBlock.refCon		 	= iGlobals;
941
942			// do another read
943			result = IDHWrite( isochInstance, pb);
944			if( result != noErr)
945				goto error;
946
947		error:
948			return result;
949		}
950
951		Closing down the isoch device
952		-----------------------------
953
954		result = IDHCancelPendingIO( isochInstance, &isochParamBlock);
955
956		result = IDHCloseDevice( isochInstance);
957
958		CloseComponent( isochInstance);	// close isoch component
959
960
961		Writing a device control command to a device
962		--------------------------------------------
963
964		ComponentInstance deviceControlInstance;
965
966		result = IDHGetDeviceControl( isochInstance, &deviceControlInstance);
967		if( result != noErr)
968			goto error;
969
970		result = DeviceControlDoAVCTransaction( deviceControlInstance, (DVCTransactionParams *) pParams);
971		if( result != noErr)
972			goto error;
973
974
975		Setting up notification for a device being enabled for reads
976		------------------------------------------------------------
977		deviceNotificationID = 0;
978		result = IDHNewNotification( isochInstance, kIDHDeviceIDEveryDevice, DVDeviceCallback,
979					(void *) iGlobals, &deviceNotificationID);
980		if( result != noErr)
981			goto error;
982
983		result = IDHNotifyMeWhen( isochInstance, deviceNotificationID, kIDHEventReadEnabled);
984		if( result != noErr)
985			goto error;
986
987
988		Getting called on a notification event
989		--------------------------------------
990		OSStatus DVDeviceCallback( IDHGenericEvent *event, void *userData)
991		{
992			switch( event->eventHeader.event)
993			{
994				case kIDHEventReadEnabled:
995					deviceHasBeenReadEnabled( event);
996					break;
997			}
998		}
999