Index: /jack2/trunk/jackmp/common/JackLockedEngine.h =================================================================== --- /jack2/trunk/jackmp/common/JackLockedEngine.h (revision 3853) +++ /jack2/trunk/jackmp/common/JackLockedEngine.h (revision 3901) @@ -38,5 +38,4 @@ // Assuming thread cancellation, must rethrow throw; - } */ @@ -63,9 +62,10 @@ } \ + /*! \brief Locked Engine, access to methods is serialized using a mutex. */ -class SERVER_EXPORT JackLockedEngine : public JackLockAble +class SERVER_EXPORT JackLockedEngine { private: @@ -100,5 +100,5 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); return fEngine.ClientCheck(name, name_res, protocol, options, status); CATCH_EXCEPTION_RETURN @@ -107,5 +107,5 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); return fEngine.ClientExternalOpen(name, pid, ref, shared_engine, shared_client, shared_graph_manager); CATCH_EXCEPTION_RETURN @@ -114,5 +114,5 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); return fEngine.ClientInternalOpen(name, ref, shared_engine, shared_manager, client, wait); CATCH_EXCEPTION_RETURN @@ -122,6 +122,6 @@ { TRY_CALL - JackLock lock(this); - return fEngine.ClientExternalClose(refnum); + JackLock lock(&fEngine); + return (fEngine.CheckClient(refnum)) ? fEngine.ClientExternalClose(refnum) : - 1; CATCH_EXCEPTION_RETURN } @@ -129,6 +129,6 @@ { TRY_CALL - JackLock lock(this); - return fEngine.ClientInternalClose(refnum, wait); + JackLock lock(&fEngine); + return (fEngine.CheckClient(refnum)) ? fEngine.ClientInternalClose(refnum, wait) : -1; CATCH_EXCEPTION_RETURN } @@ -137,6 +137,6 @@ { TRY_CALL - JackLock lock(this); - return fEngine.ClientActivate(refnum, is_real_time); + JackLock lock(&fEngine); + return (fEngine.CheckClient(refnum)) ? fEngine.ClientActivate(refnum, is_real_time) : -1; CATCH_EXCEPTION_RETURN } @@ -144,6 +144,6 @@ { TRY_CALL - JackLock lock(this); - return fEngine.ClientDeactivate(refnum); + JackLock lock(&fEngine); + return (fEngine.CheckClient(refnum)) ? fEngine.ClientDeactivate(refnum) : -1; CATCH_EXCEPTION_RETURN } @@ -153,5 +153,5 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); return fEngine.GetInternalClientName(int_ref, name_res); CATCH_EXCEPTION_RETURN @@ -160,5 +160,5 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); return fEngine.InternalClientHandle(client_name, status, int_ref); CATCH_EXCEPTION_RETURN @@ -167,5 +167,6 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); + // Client is tested in fEngine.InternalClientUnload return fEngine.InternalClientUnload(refnum, status); CATCH_EXCEPTION_RETURN @@ -176,6 +177,6 @@ { TRY_CALL - JackLock lock(this); - return fEngine.PortRegister(refnum, name, type, flags, buffer_size, port); + JackLock lock(&fEngine); + return (fEngine.CheckClient(refnum)) ? fEngine.PortRegister(refnum, name, type, flags, buffer_size, port) : -1; CATCH_EXCEPTION_RETURN } @@ -183,6 +184,6 @@ { TRY_CALL - JackLock lock(this); - return fEngine.PortUnRegister(refnum, port); + JackLock lock(&fEngine); + return (fEngine.CheckClient(refnum)) ? fEngine.PortUnRegister(refnum, port) : -1; CATCH_EXCEPTION_RETURN } @@ -191,6 +192,6 @@ { TRY_CALL - JackLock lock(this); - return fEngine.PortConnect(refnum, src, dst); + JackLock lock(&fEngine); + return (fEngine.CheckClient(refnum)) ? fEngine.PortConnect(refnum, src, dst) : -1; CATCH_EXCEPTION_RETURN } @@ -198,6 +199,6 @@ { TRY_CALL - JackLock lock(this); - return fEngine.PortDisconnect(refnum, src, dst); + JackLock lock(&fEngine); + return (fEngine.CheckClient(refnum)) ? fEngine.PortDisconnect(refnum, src, dst) : -1; CATCH_EXCEPTION_RETURN } @@ -206,6 +207,6 @@ { TRY_CALL - JackLock lock(this); - return fEngine.PortConnect(refnum, src, dst); + JackLock lock(&fEngine); + return (fEngine.CheckClient(refnum)) ? fEngine.PortConnect(refnum, src, dst) : -1; CATCH_EXCEPTION_RETURN } @@ -213,6 +214,6 @@ { TRY_CALL - JackLock lock(this); - return fEngine.PortDisconnect(refnum, src, dst); + JackLock lock(&fEngine); + return (fEngine.CheckClient(refnum)) ? fEngine.PortDisconnect(refnum, src, dst) : -1; CATCH_EXCEPTION_RETURN } @@ -221,6 +222,6 @@ { TRY_CALL - JackLock lock(this); - return fEngine.PortRename(refnum, port, name); + JackLock lock(&fEngine); + return (fEngine.CheckClient(refnum)) ? fEngine.PortRename(refnum, port, name) : -1; CATCH_EXCEPTION_RETURN } @@ -242,13 +243,12 @@ void NotifyXRun(int refnum) { - TRY_CALL - JackLock lock(this); + // RT : no lock fEngine.NotifyXRun(refnum); - CATCH_EXCEPTION - } + } + void NotifyGraphReorder() { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); fEngine.NotifyGraphReorder(); CATCH_EXCEPTION @@ -257,5 +257,5 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); fEngine.NotifyBufferSize(buffer_size); CATCH_EXCEPTION @@ -264,5 +264,5 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); fEngine.NotifySampleRate(sample_rate); CATCH_EXCEPTION @@ -271,5 +271,5 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); fEngine.NotifyFreewheel(onoff); CATCH_EXCEPTION @@ -279,5 +279,5 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); fEngine.NotifyFailure(code, reason); CATCH_EXCEPTION @@ -287,5 +287,5 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); return fEngine.GetClientPID(name); CATCH_EXCEPTION_RETURN @@ -295,5 +295,5 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); return fEngine.GetClientRefNum(name); CATCH_EXCEPTION_RETURN @@ -303,5 +303,5 @@ { TRY_CALL - JackLock lock(this); + JackLock lock(&fEngine); return fEngine.NotifyQuit(); CATCH_EXCEPTION Index: /jack2/trunk/jackmp/common/JackEngineControl.h =================================================================== --- /jack2/trunk/jackmp/common/JackEngineControl.h (revision 3782) +++ /jack2/trunk/jackmp/common/JackEngineControl.h (revision 3901) @@ -163,5 +163,5 @@ // XRun - void NotifyXRun(float delayed_usecs); + void NotifyXRun(jack_time_t callback_usecs, float delayed_usecs); void ResetXRun() { Index: /jack2/trunk/jackmp/common/JackEngine.cpp =================================================================== --- /jack2/trunk/jackmp/common/JackEngine.cpp (revision 3853) +++ /jack2/trunk/jackmp/common/JackEngine.cpp (revision 3901) @@ -35,6 +35,4 @@ namespace Jack { - -#define AssertRefnum(ref) assert(ref >= 0 && ref < CLIENT_NUM); JackEngine::JackEngine(JackGraphManager* manager, @@ -214,26 +212,26 @@ // The client may be notified by the RT thread while closing - if (!client) { - jack_log("JackEngine::NotifyClient: client not available anymore"); - } else if (client->GetClientControl()->fCallback[event]) { - if (client->ClientNotify(refnum, client->GetClientControl()->fName, event, sync, message, value1, value2) < 0) - jack_error("NotifyClient fails name = %s event = %ld val1 = %ld val2 = %ld", client->GetClientControl()->fName, event, value1, value2); - } else { - jack_log("JackEngine::NotifyClient: no callback for event = %ld", event); - } -} - -void JackEngine::NotifyClients(int event, int sync, const char* message, int value1, int value2) + if (client) { + + if (client && client->GetClientControl()->fCallback[event]) { + /* + Important for internal clients : unlock before calling the notification callbacks. + */ + bool res = fMutex.Unlock(); + if (client->ClientNotify(refnum, client->GetClientControl()->fName, event, sync, message, value1, value2) < 0) + jack_error("NotifyClient fails name = %s event = %ld val1 = %ld val2 = %ld", client->GetClientControl()->fName, event, value1, value2); + if (res) + fMutex.Lock(); + + } else { + jack_log("JackEngine::NotifyClient: no callback for event = %ld", event); + } + } +} + +void JackEngine::NotifyClients(int event, int sync, const char* message, int value1, int value2) { for (int i = 0; i < CLIENT_NUM; i++) { - JackClientInterface* client = fClientTable[i]; - if (client) { - if (client->GetClientControl()->fCallback[event]) { - if (client->ClientNotify(i, client->GetClientControl()->fName, event, sync, message, value1, value2) < 0) - jack_error("NotifyClient fails name = %s event = %ld val1 = %ld val2 = %ld", client->GetClientControl()->fName, event, value1, value2); - } else { - jack_log("JackEngine::NotifyClients: no callback for event = %ld", event); - } - } + NotifyClient(i, event, sync, message, value1, value2); } } @@ -275,6 +273,5 @@ { // Use the audio thread => request thread communication channel - fEngineControl->ResetFrameTime(callback_usecs); - fEngineControl->NotifyXRun(delayed_usecs); + fEngineControl->NotifyXRun(callback_usecs, delayed_usecs); fChannel.Notify(ALL_CLIENTS, kXRunCallback, 0); } @@ -349,12 +346,7 @@ int JackEngine::GetInternalClientName(int refnum, char* name_res) { - AssertRefnum(refnum); JackClientInterface* client = fClientTable[refnum]; - if (client) { - strncpy(name_res, client->GetClientControl()->fName, JACK_CLIENT_NAME_SIZE); - return 0; - } else { - return -1; - } + strncpy(name_res, client->GetClientControl()->fName, JACK_CLIENT_NAME_SIZE); + return 0; } @@ -379,5 +371,4 @@ int JackEngine::InternalClientUnload(int refnum, int* status) { - AssertRefnum(refnum); JackClientInterface* client = fClientTable[refnum]; if (client) { @@ -593,16 +584,10 @@ int JackEngine::ClientExternalClose(int refnum) { - AssertRefnum(refnum); JackClientInterface* client = fClientTable[refnum]; - - if (client) { - fEngineControl->fTransport.ResetTimebase(refnum); - int res = ClientCloseAux(refnum, client, true); - client->Close(); - delete client; - return res; - } else { - return -1; - } + fEngineControl->fTransport.ResetTimebase(refnum); + int res = ClientCloseAux(refnum, client, true); + client->Close(); + delete client; + return res; } @@ -610,7 +595,6 @@ int JackEngine::ClientInternalClose(int refnum, bool wait) { - AssertRefnum(refnum); JackClientInterface* client = fClientTable[refnum]; - return (client) ? ClientCloseAux(refnum, client, wait) : -1; + return ClientCloseAux(refnum, client, wait); } @@ -657,9 +641,7 @@ int JackEngine::ClientActivate(int refnum, bool is_real_time) { - AssertRefnum(refnum); JackClientInterface* client = fClientTable[refnum]; - assert(fClientTable[refnum]); - jack_log("JackEngine::ClientActivate ref = %ld name = %s", refnum, client->GetClientControl()->fName); + if (is_real_time) fGraphManager->Activate(refnum); @@ -678,9 +660,5 @@ int JackEngine::ClientDeactivate(int refnum) { - AssertRefnum(refnum); JackClientInterface* client = fClientTable[refnum]; - if (client == NULL) - return -1; - jack_log("JackEngine::ClientDeactivate ref = %ld name = %s", refnum, client->GetClientControl()->fName); @@ -718,7 +696,5 @@ { jack_log("JackEngine::PortRegister ref = %ld name = %s type = %s flags = %d buffer_size = %d", refnum, name, type, flags, buffer_size); - AssertRefnum(refnum); - assert(fClientTable[refnum]); - + // Check if port name already exists if (fGraphManager->GetPort(name) != NO_PORT) { @@ -739,7 +715,5 @@ { jack_log("JackEngine::PortUnRegister ref = %ld port_index = %ld", refnum, port_index); - AssertRefnum(refnum); - assert(fClientTable[refnum]); - + // Disconnect port ==> notification is sent PortDisconnect(refnum, port_index, ALL_PORTS); @@ -756,5 +730,4 @@ { jack_log("JackEngine::PortConnect src = %s dst = %s", src, dst); - AssertRefnum(refnum); jack_port_id_t port_src, port_dst; @@ -767,5 +740,4 @@ { jack_log("JackEngine::PortConnect src = %d dst = %d", src, dst); - AssertRefnum(refnum); JackClientInterface* client; int ref; @@ -803,5 +775,4 @@ { jack_log("JackEngine::PortDisconnect src = %s dst = %s", src, dst); - AssertRefnum(refnum); jack_port_id_t port_src, port_dst; @@ -814,6 +785,5 @@ { jack_log("JackEngine::PortDisconnect src = %d dst = %d", src, dst); - AssertRefnum(refnum); - + if (dst == ALL_PORTS) { @@ -851,5 +821,4 @@ int JackEngine::PortRename(int refnum, jack_port_id_t port, const char* name) { - AssertRefnum(refnum); char old_name[JACK_CLIENT_NAME_SIZE + JACK_PORT_NAME_SIZE]; strcpy(old_name, fGraphManager->GetPort(port)->GetName()); Index: /jack2/trunk/jackmp/common/JackEngineControl.cpp =================================================================== --- /jack2/trunk/jackmp/common/JackEngineControl.cpp (revision 3526) +++ /jack2/trunk/jackmp/common/JackEngineControl.cpp (revision 3901) @@ -82,6 +82,7 @@ } -void JackEngineControl::NotifyXRun(float delayed_usecs) +void JackEngineControl::NotifyXRun(jack_time_t callback_usecs, float delayed_usecs) { + ResetFrameTime(callback_usecs); fXrunDelayedUsecs = delayed_usecs; if (delayed_usecs > fMaxDelayedUsecs) Index: /jack2/trunk/jackmp/common/JackEngine.h =================================================================== --- /jack2/trunk/jackmp/common/JackEngine.h (revision 3853) +++ /jack2/trunk/jackmp/common/JackEngine.h (revision 3901) @@ -24,4 +24,5 @@ #include "JackGraphManager.h" #include "JackSynchro.h" +#include "JackMutex.h" #include "JackTransportEngine.h" #include "JackPlatformPlug.h" @@ -38,6 +39,8 @@ */ -class SERVER_EXPORT JackEngine +class SERVER_EXPORT JackEngine : public JackLockAble { + friend class JackLockedEngine; + private: @@ -72,4 +75,9 @@ void NotifyPortRename(jack_port_id_t src, const char* old_name); void NotifyActivate(int refnum); + + bool CheckClient(int refnum) + { + return (refnum >= 0 && refnum < CLIENT_NUM && fClientTable[refnum] != NULL); + } public: Index: /jack2/trunk/jackmp/common/JackMutex.h =================================================================== --- /jack2/trunk/jackmp/common/JackMutex.h (revision 2907) +++ /jack2/trunk/jackmp/common/JackMutex.h (revision 3901) @@ -37,9 +37,7 @@ { - private: - + protected: + JackMutex fMutex; - - protected: JackLockAble() Index: /jack2/trunk/jackmp/posix/JackPosixMutex.h =================================================================== --- /jack2/trunk/jackmp/posix/JackPosixMutex.h (revision 3665) +++ /jack2/trunk/jackmp/posix/JackPosixMutex.h (revision 3901) @@ -104,9 +104,10 @@ } - void Lock() + bool Lock() { int res = pthread_mutex_lock(&fMutex); if (res != 0) jack_error("JackPosixMutex::Lock res = %d", res); + return (res == 0); } @@ -116,9 +117,10 @@ } - void Unlock() + bool Unlock() { int res = pthread_mutex_unlock(&fMutex); if (res != 0) jack_error("JackPosixMutex::Unlock res = %d", res); + return (res == 0); }