1/*
2 * Copyright (c) 1998-2014 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#ifndef _IOKIT_IOAUDIOCONTROL_H
24#define _IOKIT_IOAUDIOCONTROL_H
25
26#include <IOKit/IOService.h>
27#include <AvailabilityMacros.h>
28#ifndef IOAUDIOFAMILY_SELF_BUILD
29#include <IOKit/audio/IOAudioEngine.h>
30#else
31#include "IOAudioEngine.h"
32#endif
33
34class IOAudioPort;
35class OSDictionary;
36class OSSet;
37class IOAudioUserClient;
38class IOAudioControlUserClient;
39class IOWorkLoop;
40class IOCommandGate;
41
42/*!
43 * @class IOAudioControl
44 * @abstract Represents any controllable attribute of an IOAudioDevice.
45 * @discussion An IOAudioControl instance may belong to one IOAudioPort.  Additionally, it may associated
46 *  with an IOAudioEngine as a default control for that IOAudioEngine.
47 *
48 *  When its value changes, it sends a notification to the CoreAudio.framework (HAL).  It also makes a call
49 *  to the ValueChangeHandler.
50 *
51 *  The base IOAudioControl class contains a type, a value and a channel ID representing the channel(s) which
52 *  the control acts on.  It may also contain a readable format for the name of the channel as well as a
53 *  control ID that can be used to identify unique controls.  Additionally it may contain a subType and a usage.
54 *  Each type has its own set of possible subTypes.  There currently four different control types defined:
55 *  kIOAudioControlTypeLevel, kIOAudioControlTypeToggle, kIOAudioControlTypeSelector.
56 *  Each one is represented by a subclass of IOAudioControl: IOAudioLevelControl, IOAudioToggleControl,
57 *  IOAudioSelectorControl.  The level control defines a range of allowed values and has
58 *  a defined subtype of kIOAudioLevelControlSubTypeVolume used to define a volume control.  The toggle control
59 *  allows for a boolean value and has a defined subtype kIOAudioToggleControlSubTypeMute for a mute control.  The
60 *  selector control has a list of allowed selections with a value and description for each allowed selection and
61 *  has the following sub types: kIOAudioSelectorControlSubTypeOutput for an output selector and
62 *  kIOAudioSelectorControlSubTypeInput for an input selector.  See the subclass documentation for a more
63 *  complete description of each
64 *
65 *  There are enums for default channel ID values and common channel names in IOAudioTypes.h.  The channel ID
66 *  values are prefixed with 'kIOAudioControlChannelID' and the common channel names are prefixed with
67 *  'kIOAudioControlChannelName'.  All of the attributes of the IOAudioControl are stored in the registry.
68 *  The key used for each attribute is defined in IOAudioTypes.h with the define matching the following
69 *  pattern: 'kIOAudioControl<attribute name>Key'.  For example: kIOAudioControlChannelIDKey.
70 *
71 *  In addition to the existing defined control types, drivers can define their own as well for other purposes.
72 *
73 *  Changes to the IOAudioControl's value made by the CoreAudio.framework are done through the IORegistry.
74 *  When the CoreAudio.framework initiates a value change, the control receives a setProperties() message.
75 *  The setProperties() implementation looks for the property 'IOAudioControlValue' and if present, calls
76 *  setValue() on the driver's IOWorkLoop with the new value.  The setValue() function first checks to see
77 *  if the new value is different.  If so, it calls performValueChange() to call through to the driver
78 *  to make the change in the hardware.  If that call succeeds the value is changed and the new value is set
79 *  in the registry.  Additionally notifications are sent to all clients that have registered for them.
80 */
81class IOAudioControl : public IOService
82{
83    friend class IOAudioPort;
84    friend class IOAudioDevice;
85    friend class IOAudioEngine;
86
87    OSDeclareDefaultStructors(IOAudioControl)
88
89public:
90
91    /*!
92     * @typedef IntValueChangeHandler
93     * @abstract Handler function used to make a notification when a value is to be changed.
94     * @param target Reference supplied when the handler was registered.
95     * @param audioControl The IOAudioControl that is changing.
96	 * @param oldValue The old value of the control.
97     * @param newValue The new value the control is being changed to.
98	 * @result Must return kIOReturnSuccess when the hardware is successfully updated.
99     */
100    typedef IOReturn (*IntValueChangeHandler)(OSObject *target, IOAudioControl *audioControl, SInt32 oldValue, SInt32 newValue ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
101    typedef IOReturn (*DataValueChangeHandler)(OSObject *target, IOAudioControl *audioControl, const void *oldData, UInt32 oldDataSize, const void *newData, UInt32 newDataSize ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
102    typedef IOReturn (*ObjectValueChangeHandler)(OSObject *target, IOAudioControl *audioControl, OSObject *oldValue, OSObject *newValue ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
103
104protected:
105    /*! @var workLoop
106        The IOWorkLoop for the audio driver - shared from the IOAudioDevice.
107    */
108    IOWorkLoop 		*workLoop;
109    /*! @var commandGate
110        The IOCommandGate for this control - attached to the driver's IOWorkLoop.
111    */
112    IOCommandGate	*commandGate;
113
114    /*! @var isStarted
115        Internal state keeping track of when the IOAudioControl has been started.
116    */
117    bool		isStarted;
118
119    /*! @var controlID
120        An optional identifier that can be used to identify the control.
121    */
122    UInt32 		controlID;
123    /*! @var channelID
124        The ID of the channel this control affects - may be kIOAudioControlChannelIDAll if it represents all channels.
125    */
126    UInt32		channelID;
127
128    UInt32		type;
129    UInt32		subType;
130    UInt32		usage;
131
132    OSObject	*value;
133
134    typedef enum {
135        kIntValueChangeHandler,
136        kDataValueChangeHandler,
137        kObjectValueChangeHandler
138    } ValueChangeHandlerType;
139
140    ValueChangeHandlerType valueChangeHandlerType;
141
142    union {
143        IntValueChangeHandler		intHandler;
144        DataValueChangeHandler		dataHandler;
145        ObjectValueChangeHandler	objectHandler;
146    } valueChangeHandler;
147
148    OSObject	*valueChangeTarget;
149
150    /*! @var clients
151        A list of user clients that have requested value change notifications.
152    */
153    OSSet		*userClients;
154
155protected:
156    struct ExpansionData {
157		IOAudioEngine *				providerEngine;
158		OSArray *					notificationQueue;
159		UInt32						commandGateStatus;			// <rdar://8518215>
160		SInt32						commandGateUsage;			// <rdar://8518215>
161	};
162
163    ExpansionData *reserved;
164
165public:
166	// OSMetaClassDeclareReservedUsed(IOAudioControl, 0);
167	virtual void sendChangeNotification(UInt32 notificationType ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
168
169	// OSMetaClassDeclareReservedUsed(IOAudioControl, 1);
170    /*!
171	 * @function setReadOnlyFlag
172     * @abstract Call this function to say that a control is read only.
173	 * This call cannot be undone, so if a control is only temporarily unsetable,
174	 * do not use this call but instead return an error from the control handler.
175     */
176	virtual void setReadOnlyFlag( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
177
178	// OSMetaClassDeclareReservedUsed(IOAudioControl, 2);
179	virtual void sendQueuedNotifications(void ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
180
181	// OSMetaClassDeclareReservedUsed(IOAudioControl, 3);
182    /*!
183     * @function createUserClient
184     * @abstract Creates a new IOAudioControlUserClient instance.
185     * @discussion This function is called by newUserClient() to create a new IOAudioControlUserClient instance.  This function may be overridden by subclasses that need to add functionality
186     *  to the IOAudioControlUserClient.  In that case, they must subclass IOAudioControlUserClient
187     *  and return a new, initialized instance of that subclass.
188	 *  A derived class that requires overriding of createUserClient should override the version with the properties
189	 *  parameter for Intel targets, and without the properties parameter for PPC targets.  The #if __i386__ directive
190	 *  can be used to select between the two behaviors.
191     * @param task The task requesting the new user client.
192     * @param securityID Optional security paramater passed in by the client - ignored.
193     * @param type Optional user client type passed in by the client.
194     * @param newUserClient The IOAudioControlUserClient * must be stored in this param on a successful
195     *  completion.
196     * @param properties A dictionary of additional properties for the connection.
197     * @result Returns kIOReturnSuccess on success.
198     */
199    virtual IOReturn createUserClient(task_t task, void *securityID, UInt32 taskType, IOAudioControlUserClient **newUserClient, OSDictionary *properties) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
200
201private:
202    OSMetaClassDeclareReservedUsed(IOAudioControl, 0);
203    OSMetaClassDeclareReservedUsed(IOAudioControl, 1);
204    OSMetaClassDeclareReservedUsed(IOAudioControl, 2);
205    OSMetaClassDeclareReservedUsed(IOAudioControl, 3);
206
207    OSMetaClassDeclareReservedUnused(IOAudioControl, 4);
208    OSMetaClassDeclareReservedUnused(IOAudioControl, 5);
209    OSMetaClassDeclareReservedUnused(IOAudioControl, 6);
210    OSMetaClassDeclareReservedUnused(IOAudioControl, 7);
211    OSMetaClassDeclareReservedUnused(IOAudioControl, 8);
212    OSMetaClassDeclareReservedUnused(IOAudioControl, 9);
213    OSMetaClassDeclareReservedUnused(IOAudioControl, 10);
214    OSMetaClassDeclareReservedUnused(IOAudioControl, 11);
215    OSMetaClassDeclareReservedUnused(IOAudioControl, 12);
216    OSMetaClassDeclareReservedUnused(IOAudioControl, 13);
217    OSMetaClassDeclareReservedUnused(IOAudioControl, 14);
218    OSMetaClassDeclareReservedUnused(IOAudioControl, 15);
219    OSMetaClassDeclareReservedUnused(IOAudioControl, 16);
220    OSMetaClassDeclareReservedUnused(IOAudioControl, 17);
221    OSMetaClassDeclareReservedUnused(IOAudioControl, 18);
222    OSMetaClassDeclareReservedUnused(IOAudioControl, 19);
223    OSMetaClassDeclareReservedUnused(IOAudioControl, 20);
224    OSMetaClassDeclareReservedUnused(IOAudioControl, 21);
225    OSMetaClassDeclareReservedUnused(IOAudioControl, 22);
226    OSMetaClassDeclareReservedUnused(IOAudioControl, 23);
227
228public:
229
230    /*!
231     * @function withAttributes
232     * @abstract Static function that allocates a new IOAudioControl with the given attributes.
233     * @param type The type of the control.  Common, known types are defined in IOAudioTypes.h.  They currently
234     *  consist of kIOAudioControlTypeLevel, kIOAudioControlTypeToggle, kIOAudioControlTypeSelector.
235     * @param channelID The ID of the channel(s) that the control acts on.  Common IDs are located in IOAudioTypes.h.
236     * @param channelName An optional name for the channel.  Common names are located in IOAudioDefines.h.  Any name not
237     *  defined in IOAudioDefines.h must be localized in order to be properly displayed in multiple languages.
238     * @param cntrlID An optional ID for the control that can be used to uniquely identify controls
239     * @param subType An optional subType specific to the given type
240     * @param usage An optional value specifying how the control will be used.  Currently defined usages are kIOAudioControlUsageInput,
241     *  kIOAudioControlUsageOutput and kIOAudioControlUsagePassThru.  This value is used when a control is set as a default control
242     *  on an IOAudioEngine.
243     * @result Returns a newly allocated and initialized IOAudioControl.
244     */
245    static IOAudioControl *withAttributes(UInt32 type,
246                                          OSObject *initialValue,
247                                          UInt32 channelID,
248                                          const char *channelName = 0,
249                                          UInt32 cntrlID = 0,
250                                          UInt32 subType = 0,
251                                          UInt32 usage = 0) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10 ;
252
253    /*!
254     * @function init
255     * @abstract Initializes a newly allocated IOAudioControl with the given attributes.
256     * @param type The type of the control.  Common, known types are defined in IOAudioTypes.h.  They currently
257     *  consist of kIOAudioControlTypeLevel, kIOAudioControlTypeToggle, kIOAudioControlTypeSelector.
258     * @param channelID The ID of the channel(s) that the control acts on.  Common IDs are located in IOAudioTypes.h.
259     * @param channelName An optional name for the channel.  Common names are located in IOAudioDefines.h.  Any name not
260     *  defined in IOAudioDefines.h must be localized in order to be properly displayed in multiple languages.
261     * @param cntrlID An optional ID for the control that can be used to uniquely identify controls
262     * @param subType An optional subType specific to the given type
263     * @param usage An optional value specifying how the control will be used.  Currently defined usages are kIOAudioControlUsageInput,
264     *  kIOAudioControlUsageOutput and kIOAudioControlUsagePassThru.  This value is used when a control is set as a default control
265     *  on an IOAudioEngine.
266     * @param properties Standard property list passed to the init() function of any new IOService.  This dictionary
267     *  gets stored in the registry entry for this instance.
268     * @result Returns true on success.
269     */
270    virtual bool init(UInt32 type,
271                      OSObject *initialValue,
272                      UInt32 channelID,
273                      const char *channelName = 0,
274                      UInt32 cntrlID = 0,
275                      UInt32 subType = 0,
276                      UInt32 usage = 0,
277                      OSDictionary *properties = 0) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10 ;
278
279    /*!
280     * @function free
281     * @abstract Frees all of the resources allocated by the IOAudioControl.
282     * @discussion Do not call this directly.  This is called automatically by the system when the instance's
283     *  refcount goes to 0.  To decrement the refcount, call release() on the object.
284     */
285    virtual void free( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
286
287    /*!
288     * @function start
289     * @abstract Starts a newly created IOAudioControl.
290     * @discussion This is called automatically by IOAudioPort when addAudioControl() is called or by IOAudioEngine
291     *  when addDefaultAudioControl() is called.  It will only be called by the first call to either addAudioControl() or
292     *  addDefaultAudioControl().
293     * @param provider The IOAudioPort or IOAudioEngine that owns this control.
294     * @result Returns true on success.
295     */
296    virtual bool start(IOService *provider) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
297
298	virtual bool attachAndStart(IOService *provider) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
299
300    /*!
301     * @function getIsStarted
302     * @abstract Returns true after start() has been called.
303     * @discussion Used by IOAudioPort and IOAudioEngine to decide if the control needs to be started.
304     */
305    virtual bool getIsStarted() AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
306
307    /*!
308     * @function stop
309     * @abstract Stops the control when the provider is going away.
310     * @param provider The IOAudioPort or IOAudioEngine that owns this control.
311     */
312    virtual void stop(IOService *provider) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
313
314    /*!
315     * @function getWorkLoop
316     * @abstract Returns the IOWorkLoop for the whole audio driver.
317     */
318    virtual IOWorkLoop *getWorkLoop() AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
319
320    /*!
321     * @function getCommandGate
322     * @abstract Returns the IOCommandGate for this IOAudioControl.
323     */
324    virtual IOCommandGate *getCommandGate() AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10 ;
325
326    /*!
327     * @function newUserClient
328     * @abstract Creates a new user client object for this IOAudioControl instance.
329     * @discussion This is called automatically by I/O Kit when a user process opens a connection to this
330     *  IOAudioControl.  This is typically done when the user process needs to register for value change
331     *  notifications.  This implementation allocates a new IOAudioControlUserClient object.  There is no
332     *  need to call this directly.
333	 *  A derived class that requires overriding of newUserClient should override the version with the properties
334	 *  parameter for Intel targets, and without the properties parameter for PPC targets.  The #if __i386__ directive
335	 *  can be used to select between the two behaviors.
336     * @param task The task requesting the new user client.
337     * @param securityID Optional security paramater passed in by the client - ignored.
338     * @param type Optional user client type passed in by the client - 0 for the default user client type.
339     * @param handler The new IOUserClient * must be stored in this param on a successful completion.
340     * @param properties A dictionary of additional properties for the connection.
341     * @result Returns kIOReturnSuccess on success.  May also result kIOReturnError or kIOReturnNoMemory.
342     */
343    virtual IOReturn newUserClient(task_t task, void *securityID, UInt32 type, IOUserClient **handler) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
344    virtual IOReturn newUserClient(task_t task, void *securityID, UInt32 type, OSDictionary *properties, IOUserClient **handler) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
345
346    /*!
347     * @function createUserClient
348     * @abstract Creates a new IOAudioControlUserClient instance.
349     * @discussion This function is called by newUserClient() to create a new IOAudioControlUserClient instance.  This function may be overridden by subclasses that need to add functionality
350     *  to the IOAudioControlUserClient.  In that case, they must subclass IOAudioControlUserClient
351     *  and return a new, initialized instance of that subclass.
352	 *  A derived class that requires overriding of createUserClient should override the version with the properties
353	 *  parameter for Intel targets, and without the properties parameter for PPC targets.  The #if __i386__ directive
354	 *  can be used to select between the two behaviors.
355     * @param task The task requesting the new user client.
356     * @param securityID Optional security paramater passed in by the client - ignored.
357     * @param type Optional user client type passed in by the client.
358     * @param newUserClient The IOAudioControlUserClient * must be stored in this param on a successful
359     *  completion.
360     * @result Returns kIOReturnSuccess on success.
361     */
362    virtual IOReturn createUserClient(task_t task, void *securityID, UInt32 type, IOAudioControlUserClient **newUserClient) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10 ;
363
364    /*!
365     * @function clientClosed
366     * @abstract Called automatically by the IOAudioControlUserClient when a user client closes its
367     *  connection to the control.
368     * @param client The user client object that has disconnected.
369     */
370    virtual void clientClosed(IOAudioControlUserClient *client) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
371
372    /*!
373     * @function setProperties
374     * @abstract Changes a property of this IOService.
375     * @discussion This is called when the user client changes a property of this
376     *  IOAudioControl.  In this case it is used to change the value.  This function
377     *  looks for that property and then calls setValue() through the IOCommandGate and
378     *  setValueAction().
379     * @param properties An OSDictionary containing the properties to change.
380     * @result Returns kIOReturnSuccess on success.
381     */
382    virtual IOReturn setProperties(OSObject *properties) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
383
384    virtual void setValueChangeHandler(IntValueChangeHandler intValueChangeHandler, OSObject *target) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
385    virtual void setValueChangeHandler(DataValueChangeHandler dataValueChangeHandler, OSObject *target) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
386    virtual void setValueChangeHandler(ObjectValueChangeHandler objectValueChangeHandler, OSObject *target) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
387
388    virtual void setValueChangeTarget(OSObject *target) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
389
390    /*!
391     * @function flushValue
392     * @abstract Forces the control to be flushed out to the hardware.
393     * @discussion This function calls performValueChange() directly with the current value of the IOAudioControl.
394     * @result Returns the result of performValueChange() - kIOReturnSuccess on success.
395     */
396    virtual IOReturn flushValue() AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
397
398    /*!
399     * @function setValueAction
400     * @abstract IOCommandGate Action which calls setValue() while holding the IOCommandGate.
401     * @discussion This is needed to allow setValue() to be called on the IOWorkLoop.
402     * @param owner The owner of the IOCommandGate (the IOAudioControl in this case).
403     * @param arg1 The new value for the IOAudioControl.
404     * @result Returns the result of setValue() - kIOReturnSuccess on success.
405     */
406    static IOReturn setValueAction(OSObject *owner, void *arg1, void *arg2, void *arg3, void *arg4) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
407
408	static IOReturn _setValueAction(OSObject *target, void *arg0, void *arg1, void *arg2, void *arg3) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;	// <rdar://7529580>
409
410    /*!
411     * @function setValue
412     * @abstract Sets the value for this control.
413     * @discussion When the control's value is changed, a call is made to performValueChange().  If that call
414     *  succeeds, the value is set and sendValueChangeNotification() is called to send a notification to the
415     *  user clients.  This function must be called on the IOWorkLoop.
416     * @param newValue The new value for this control.
417     * @result Returns kIOReturnSuccess if the value is successfully set.
418     */
419    virtual IOReturn setValue(OSObject *newValue ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
420
421    virtual IOReturn setValue(SInt32 intValue ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
422
423    /*!
424     * @function hardwareValueChanged
425     * @abstract Updates the value for this control and sends out the value changed notification.
426     * @discussion This is designed to be called by the driver when it detects that the hardware's value has
427     *  changed without driver intervention (e.g. when an external event causes the change).  The difference between
428     *  hardwareValueChanged() and setValue() is that hardwareValueChanged() doesn't call performValueChange() which
429     *  sends a message back to the driver to cause it to change the hardware with the new value.  This function must
430     *  be called on the IOWorkLoop.
431     * @param newValue The new value for this control.
432     * @result Returns kIOReturnSuccess if the value is successfully updated.
433     */
434    virtual IOReturn hardwareValueChanged(OSObject *newValue ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
435
436    /*!
437     * @function getValue
438     * @abstract Returns the current value of the control.
439     */
440    virtual OSObject *getValue( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
441    virtual SInt32 getIntValue( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
442    virtual const void *getDataBytes( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
443    virtual UInt32 getDataLength( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
444
445    /*!
446     * @function getControlID
447     * @abstract Returns the control ID for the control.
448     */
449    virtual UInt32 getControlID( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
450
451    /*!
452     * @function getChannelID
453     * @abstract Returns the channel ID for the control.
454     */
455    virtual UInt32 getChannelID( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
456
457    virtual UInt32 getType( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
458    virtual UInt32 getSubType( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
459    virtual UInt32 getUsage( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
460
461    virtual void setCoreAudioPropertyID(UInt32 propertyID ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
462
463	void setWorkLoop(IOWorkLoop *wl ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
464
465protected:
466    /*!
467     * @function sendValueChangeNotification
468     * @abstract Called when the value has changed for the control.
469     * @discussion This function sends out the value change notification to the user clients.
470     */
471    virtual void sendValueChangeNotification( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
472
473    /*!
474     * @function setChannelName
475     * @abstract Called at init time to set the channel name for this IOAudioControl.
476     */
477    virtual void setChannelName(const char *channelName ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
478
479    /*!
480     * @function setChannelID
481     * @abstract Called at init time to set the channel ID for this IOAudioControl.
482     */
483    virtual void setChannelID(UInt32 newChannelID ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
484    virtual void setChannelNumber(SInt32 channelNumber ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
485
486    /*!
487     * @function setSubType
488     * @abstract Called at init time to set the control subType.
489     */
490    virtual void setType(UInt32 type ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
491
492    /*!
493     * @function setType
494     * @abstract Called at init time to set the control type.
495     */
496    virtual void setSubType(UInt32 subType ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
497
498    /*!
499     * @function setUsage
500     * @abstract Called at init time to set the control usage.
501     */
502    virtual void setUsage(UInt32 usage ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
503
504    /*!
505     * @function setControlID
506     * @abstract Sets the controlID for this control.
507     * @discussion The control ID is an optional attribute that can be used to track IOAudioControls.  A typical
508     *  use is for the IOAudioDevice to assign a unique controlID to each control that it creates and then
509     *  do a switch statement on the id of the control when it gets an audioControlValueChanged() notification.
510     *  Typically the control ID is set when the object is created and doesn't need to be called again.
511     * @param cntrlID The control ID for the control.
512     */
513    virtual void setControlID(UInt32 cntrlID ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
514
515    /*!
516     * @function validateValue
517     * @abstract Called by setValue() to verify that the value is valid.
518     * @param newValue The new value to be verified.
519     * @result Returns kIOReturnSuccess if the value is valid.
520     */
521    virtual IOReturn validateValue(OSObject *newValue ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
522
523    /*!
524     * @function updateValue
525     * @abstract Called by setValue() in order to update the value and the registry.
526     * @discussion It also calls
527     *  sendValueChangedNotification() to send notifications to the user clients.
528     * @param newValue The new value to b updated.
529     * @result Returns kIOReturnSuccess if the value is successfully updated.
530     */
531    virtual IOReturn updateValue(OSObject *newValue ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
532
533    virtual IOReturn _setValue(OSObject *newValue ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
534
535    /*!
536     * @function performValueChange
537     * @abstract Called by setValue() to make the call to the valueChangeHandler
538     *  to update the hardware.
539     * @result Returns the result of the handler call (or kIOReturnError on an error).
540     */
541    virtual IOReturn performValueChange(OSObject *newValue ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
542
543    /*!
544     * @function addUserClientAction
545     * @abstract IOCommandGate Action which calls addUserClient() while holding the IOCommandGate.
546     * @discussion This is needed to allow addUserClient() to be called on the IOWorkLoop.
547     * @param owner The owner of the IOCommandGate (the IOAudioControl in this case).
548     * @param arg1 The IOAudioControlUserClient to be added.
549     * @result Returns the result of addUserClient() - kIOReturnSuccess on success.
550     */
551    static IOReturn addUserClientAction(OSObject *owner, void *arg1, void *arg2, void *arg3, void *arg4 ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
552
553	static IOReturn _addUserClientAction(OSObject *target, void *arg0, void *arg1, void *arg2, void *arg3 ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;	// <rdar://7529580>
554
555    /*!
556     * @function removeUserClientAction
557     * @abstract IOCommandGate Action which calls removeUserClient() while holding the IOCommandGate.
558     * @discussion This is needed to allow removeUserClient() to be called on the IOWorkLoop.
559     * @param owner The owner of the IOCommandGate (the IOAudioControl in this case).
560     * @param arg1 The IOAudioControlUserClient to be removed.
561     * @result Returns the result of removeUserClient() - kIOReturnSuccess on success.
562     */
563    static IOReturn removeUserClientAction(OSObject *owner, void *arg1, void *arg2, void *arg3, void *arg4 ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
564
565	static IOReturn _removeUserClientAction(OSObject *target, void *arg0, void *arg1, void *arg2, void *arg3 ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;	// <rdar://7529580>
566
567    /*!
568     * @function detachUserClientsAction
569     */
570     static IOReturn detachUserClientsAction(OSObject *owner, void *arg1, void *arg2, void *arg3, void *arg4 ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
571
572    /*!
573     * @function addUserClient
574     * @abstract Called on the IOWorkLoop to add a new IOAudioControlUserClient.
575     * @discussion There is no need to call this directly.  It is called on the workLoop
576     *  by newUserClient() through addUserClientAction().
577     * @param newUserClient The IOAudioControlUserClientto be added.
578     * @result Returns kIOReturnSuccess on success.
579     */
580    virtual IOReturn addUserClient(IOAudioControlUserClient *newUserClient ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
581
582    /*!
583     * @function removeUserClient
584     * @abstract Called on the IOWorkLoop to remove an IOAudioControlUserClient.
585     * @discussion This is called on the IOWorkLoop by clientClosed() through
586     *  removeUserClientAction() when the user client is going away.  It should
587     *  not be called directly.
588     * @param userClient The IOAudioControlUserClient to be removed.
589     * @result Returns kIOReturnSuccess on success.
590     */
591    virtual IOReturn removeUserClient(IOAudioControlUserClient *userClient ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
592
593    virtual IOReturn detachUserClients( ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;
594
595	static void setCommandGateUsage(IOAudioControl *control, bool increment ) AVAILABLE_MAC_OS_X_VERSION_10_4_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_10;		// <rdar://8518215>
596
597};
598
599#endif /* _IOKIT_IOAUDIOCONTROL_H */
600
601