Re: User-land CoreAudio driver and Leopard
Re: User-land CoreAudio driver and Leopard
- Subject: Re: User-land CoreAudio driver and Leopard
- From: Jeff Moore <email@hidden>
- Date: Mon, 26 Nov 2007 11:32:15 -0800
Sorry this took so long. We had the week off last week for the holiday
here in the US.
On Nov 19, 2007, at 4:59 AM, Stéphane Letz wrote:
Actually after trying all sort of implementation variants, my plugin
still does not working properly: it works with some applications
(Live, Reason, Garageband..) and fails with many others (iTunes: for
example switching from JackRouter to Built-in output and vice-versa
repeatidly fails, same issue with QuickTimePlayer, DVD player
refuses to see it...)
The *simplest* implementation does basically the following:
void JackRouterDevice::StartHardware()
{
// JACK
[START JACK IO]
// set the device state to know the engine is running
IOEngineStarted();
// notify clients that the engine is running
CAPropertyAddress
theIsRunningAddress(kAudioDevicePropertyDeviceIsRunning);
PropertiesChanged(1, &theIsRunningAddress);
}
The timing of sending the IsRunning notification is important since it
means to the application that timing services are running and IOProcs
are firing. You have to be darn sure that your state is ready for the
app to do it's thing when you send that notification. You'll note that
HP_IOThread accomplishes this by sending the notification from the IO
thread in it's WorkLoop method.
void JackRouterDevice::StopHardware()
{
// set the device state to know the engine has stopped
IOEngineStopped();
// Notify clients that the IO callback is stopping
CAPropertyAddress
theIsRunningAddress(kAudioDevicePropertyDeviceIsRunning);
PropertiesChanged(1, &theIsRunningAddress);
// JACK
[STOP JACK IO]
}
Same here. In fact, this looks like a race to me between your IO
thread and sending the IsRunning notification if you aren't careful
since you appear to be actually stopping IO after sending the
notification.
I'm using a CAGuard to protect access to the IOProc list thus:
bool JackRouterDevice::IsSafeToExecuteCommand()
{
bool theAnswer = true;
// Checking if call is done in Jack IO thread
if (mClient) {
theAnswer = jack_client_thread_id(mClient) != pthread_self();
}
JARLog("JackRouterDevice::IsSafeToExecuteCommand theAnswer = %ld
\n", theAnswer);
return theAnswer;
}
bool JackRouterDevice::StartCommandExecution(void**
outSavedCommandState)
{
*outSavedCommandState = mIOGuard.Lock() ? (void*)1 : (void*)0;
return true;
}
void JackRouterDevice::FinishCommandExecution(void*
inSavedCommandState)
{
if (inSavedCommandState != 0) {
mIOGuard.Unlock();
}
}
And Jack IO callback does:
int JackRouterDevice::Process(jack_nframes_t nframes, void* arg)
{
bool wasLocked;
JackRouterDevice* client = (JackRouterDevice*)arg;
// Lock is on, so drop this cycle.
if (!client->mIOGuard.Try(wasLocked)) {
return 0;
}
// JACK processing
[JACK IO] (use the IOProc list...)
client->mIOGuard.Unlock();
// execute any deferred commands
client->ExecuteAllCommands();
return 0;
}
This seems fine, although you'll note that HP_IOThread continues to
hold mIOGuard when calling HP_Device::ExecuteAllCommands().
As said before this version does not work well, second try was to
follow more what SHP_PlugIn example does : that is using the 4 state
system kNotRunningPhase, kInitializingPhase, kRunningPhase,
kTeardownPhase, having the JackRouterDevice::StartHardware() start
JACK and wait for the Jack IO callback to actually run... and so on.
But same kind of problems
Can I expect to have the simpler first version working? what
important thing is still lacking?
It's hard to say. On first blush, it seems that your handling of the
IsRunning notification is a little looser than what HP_IOThread
implements. I know QuickTime is sensitive to the problems with the
IsRunning notification.
At any rate, can you describe the failure cases in more detail? I
don't have a clear picture of what the symptoms are when things go bad
on you.
--
Jeff Moore
Core Audio
Apple
_______________________________________________
Do not post admin requests to the list. They will be ignored.
Coreaudio-api mailing list (email@hidden)
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden