Re: CoreAudio Plug-In
Re: CoreAudio Plug-In
- Subject: Re: CoreAudio Plug-In
- From: Laurent Cerveau <email@hidden>
- Date: Tue, 20 Nov 2001 11:35:09 +0100
On Monday, November 19, 2001, at 06:24 PM, Sean Morrell wrote:
The plug-in was suggested as a method of communicating between a system
preference pane and our audio driver. Besides plug-ins, what other form
of IPC is recommended? I was thinking about Distributed Notifications.
Can this and other Core Foundation services can be used in the kernel?
You can not use CoreFoundation in the kernel. Note that here we are
really in a user/kernel communication path.
Basically the plugin is a plugin to the HAL. The story goes like
this : When you pass a property change to the hardware, it is passed as
a selector which is an OS type with an associated value.
There are however only a few standards properties defined. These are for
volume, mute, gain , input selector, output selector and playthrough
(if there is hardware playthrough). What we thought is that these
selectors represents the common denominator between all audio hardware.
Each time one of these change the HAL is looking for a IOAudioControl
with the same selector, in the IORegistry and modify the value through
the use of the rehgistry. If you look in the IOAudioControl.h header
file you will see :
* Changes to the IOAudioControl's value made by the
CoreAudio.framework are done through the IORegistry.
* When the CoreAudio.framework initiates a value change, the control
receives a setProperties() message.
* The setProperties() implementation looks for the property
'IOAudioControlValue' and if present, calls
* setValue() on the driver's IOWorkLoop with the new value. The
setValue() function first checks to see
* if the new value is different. If so, it calls performValueChange()
to call through to the driver
* to make the change in the hardware. If that call succeeds the value
is changed and the new value is set
* in the registry. Additionally notifications are sent to all clients
that have registered for them.
The problem is now the following one. What happens if your hardware can
do more, and I want to pass other pair selector/values : then you need
to declare a plugin. When the HAL is passed a selector that is not one
of the "common denominator" one, then it looks to see if there are
plugin around and if yes, pass it to the plugin. On the Kernel side you
would have created appropriate IOAudio controls and in the plugin you
would do exactly like the HAL does : parse the registry for these and do
the changes.
What I do not remember 100% (it happens :-)), is that I think there is
the possibility to declare a control with a custom OS type, and the HAL
will look for it and pass the value as "raw data". Jeff would know
better. If this is the case, the choice between implementing a plugin or
simply add a control could be done following the complexity of the
structure : for example if you want to control a hardware EQ you may
want to pass a property/value like:
(selector 'eqqu', EQstruct value) with
EQstruct {
float frequency;
float gain;
float Q;
}
But practically, the hardware understand only low-level coefficient like
a good DSP citizen, that is coefficients ao, a1, a2, b0, b1, b2 and
gain G
(practically one of them is always 1 , I know I know...). So you would
prefere to implement a HAL plugin; in the implementation of
AudioDriverPlugInStreamSetProperty you could do the transformation:
(f, g, Q) --> (a0, a1, a2, b0, b1, b2, G)
During the driver setup you could have created one IOAudioLevelControl
for each coefficient, with type and subtype. The routine would them look
for them in the registry and modify their value. Note that there are
other possibility in the way you create controls : you may have
preferred to have a custom control that accepts all (a0...b2)
coefficients and one for the Gain.
This has the following pro and con.
- PRO : the command from a user land perspective is simplier (only f, Q,
g)
- PRO : you can do some checkin on the values and control the fact that
the parameters passed to your hardware will always describe a stable
filter , and never destry your hardware.
- CON : you loose some hardware capabilities due to the fact that the
implementation of the filter (and the translation high level, low level
coefficients) is part of the plugin. So your hardware is already
abstracted, and some flexibility is lost.
If you had one control that would accept raw OSData (and with a custom
OStype that the HAl would recognize for you) , from a user land you
would be obliged to pass a big block of data with (Ga0a1a2bb0b1b2) all
compacted. Remember also that float operation in the kernel are not
welcomed , so doing a transform like (f, g, Q) --> (a0, a1, a2, b0, b1,
b2, G) should happen in user land.
Laurent
Laurent Cerveau
Applications Division
Apple Computer Inc.
email@hidden