Commit 3f0ea566 authored by sletz's avatar sletz
Browse files

Avoid using Terminate when quitting in RT thread. Cleanup JackEngineInterface.

git-svn-id: http://subversion.jackaudio.org/jack/jack2/trunk/jackmp@2391 0c269be4-1314-0410-8aa9-9f06e86f4224
parent c93b4ebe
......@@ -20,10 +20,14 @@ Fernando Lopez-Lezcano
Jackdmp changes log
---------------------------
2008-05-30 Stephane Letz <letz@grame.fr>
* Avoid using Terminate when "quitting" in RT thread. Cleanup JackEngineInterface.
2008-05-29 Stephane Letz <letz@grame.fr>
* Tim Blechmann patch for JackPosixSemaphore (still to test...).
* Correct JackWinThread::Terminate.
* Correct JackWinThread::Terminate.
2008-05-28 Stephane Letz <letz@grame.fr>
......
......@@ -347,7 +347,7 @@ bool JackClient::Execute()
if (WaitFirstSync())
ExecuteThread();
}
return false; // Never reached
return false;
}
inline bool JackClient::WaitFirstSync()
......@@ -366,15 +366,12 @@ inline bool JackClient::WaitFirstSync()
}
SignalSync();
}
return false; // Never reached
return false;
}
inline void JackClient::ExecuteThread()
{
while (true) {
if (Wait(CallProcessCallback()) != GetEngineControl()->fBufferSize)
return;
}
while (Wait(CallProcessCallback()) == GetEngineControl()->fBufferSize);
}
jack_nframes_t JackClient::Wait(int status)
......@@ -447,8 +444,7 @@ inline int JackClient::End()
fThread->DropRealTime();
GetClientControl()->fActive = false;
fChannel->ClientDeactivate(GetClientControl()->fRefNum, &result);
fThread->Terminate();
return 0; // Never reached
return 0;
}
inline int JackClient::Error()
......@@ -460,8 +456,7 @@ inline int JackClient::Error()
GetClientControl()->fActive = false;
fChannel->ClientDeactivate(GetClientControl()->fRefNum, &result);
ShutDown();
fThread->Terminate();
return 0; // Never reached
return 0;
}
//-----------------
......
......@@ -85,10 +85,8 @@ class JackEngineInterface
virtual void NotifyGraphReorder() = 0;
virtual void NotifyBufferSize(jack_nframes_t nframes) = 0;
virtual void NotifyFreewheel(bool onoff) = 0;
virtual void NotifyPortRegistation(jack_port_id_t port_index, bool onoff) = 0;
virtual void NotifyPortConnect(jack_port_id_t src, jack_port_id_t dst, bool onoff) = 0;
virtual void NotifyActivate(int refnum) = 0;
};
};
/*!
\brief Engine description.
......@@ -123,6 +121,9 @@ class JackEngine
void NotifyClient(int refnum, int event, int sync, int value1, int value2);
void NotifyClients(int event, int sync, int value1, int value2);
void NotifyPortRegistation(jack_port_id_t port_index, bool onoff);
void NotifyPortConnect(jack_port_id_t src, jack_port_id_t dst, bool onoff);
void NotifyActivate(int refnum);
public:
......@@ -169,9 +170,6 @@ class JackEngine
void NotifyGraphReorder();
void NotifyBufferSize(jack_nframes_t nframes);
void NotifyFreewheel(bool onoff);
void NotifyPortRegistation(jack_port_id_t port_index, bool onoff);
void NotifyPortConnect(jack_port_id_t src, jack_port_id_t dst, bool onoff);
void NotifyActivate(int refnum);
};
......
......@@ -179,22 +179,7 @@ class JackLockedEngine : public JackEngineInterface, public JackLockAble
JackLock lock(this);
fEngine.NotifyFreewheel(onoff);
}
void NotifyPortRegistation(jack_port_id_t port_index, bool onoff)
{
JackLock lock(this);
fEngine.NotifyPortRegistation(port_index, onoff);
}
void NotifyPortConnect(jack_port_id_t src, jack_port_id_t dst, bool onoff)
{
JackLock lock(this);
fEngine.NotifyPortConnect(src, dst, onoff);
}
void NotifyActivate(int refnum)
{
JackLock lock(this);
fEngine.NotifyActivate(refnum);
}
int GetClientPID(const char* name)
{
JackLock lock(this);
......
......@@ -158,7 +158,7 @@ int JackServer::InternalClientLoad(const char* client_name, const char* so_name,
*status = 0;
JackLoadableInternalClient* client = new JackLoadableInternalClient(fInstance, GetSynchroTable(), so_name, objet_data);
assert(client);
int res = client->Open("unused", client_name, (jack_options_t)options, (jack_status_t*)status);
int res = client->Open(JACK_DEFAULT_SERVER_NAME, client_name, (jack_options_t)options, (jack_status_t*)status);
if (res < 0) {
delete client;
*int_ref = 0;
......
......@@ -69,12 +69,21 @@ static void* jack_thread(void *arg)
jack_client_t* client = (jack_client_t*) arg;
while (1) {
jack_nframes_t frames = jack_cycle_wait (client);
int status = _process(frames);
jack_cycle_signal (client, status);
// possibly do something else after signaling next clients in the graph
/*
Possibly do something else after signaling next clients in the graph
*/
/* End condition */
if (status != 0)
return 0;
}
/* not reached*/
return 0;
}
......
......@@ -808,7 +808,7 @@
isa = PBXContainerItemProxy;
containerPortal = 08FB7793FE84155DC02AAC07 /* Project object */;
proxyType = 1;
remoteGlobalIDString = 4BFA5E8B0DEC4D9C00FA4CDB /* testMutex Universal */;
remoteGlobalIDString = 4BFA5E8B0DEC4D9C00FA4CDB;
remoteInfo = "testMutex Universal";
};
4B699DB3097D421700A18468 /* PBXContainerItemProxy */ = {
......@@ -2029,8 +2029,8 @@
4BA550FB05E2420000569492 /* Engine */ = {
isa = PBXGroup;
children = (
4B5F253D0DEE9B8F0041E486 /* JackLockedEngine.h */,
4B168CA3076A5319005B2802 /* MIG_RPC */,
4B5F253D0DEE9B8F0041E486 /* JackLockedEngine.h */,
4BF8D2130834F02800C94B91 /* JackEngine.h */,
4BF8D2140834F02800C94B91 /* JackEngine.cpp */,
4BF8FB0E08AC88EF00D1A344 /* JackFrameTimer.h */,
......
......@@ -29,67 +29,192 @@
#include "JackPosixThread.h"
#include "JackMutex.h"
#include <jack/thread.h>
using namespace Jack;
static void CleanupHandler(void * arg)
{
JackLockAble* locked = (JackLockAble*)arg;
printf("CleanupHandler locked %x \n", locked);
locked->Unlock();
}
struct LockedObject : public JackLockAble {
JackThread* fThread;
int fCount;
LockedObject():fCount(0)
{}
virtual ~LockedObject()
{
fThread->Kill();
delete fThread;
}
{}
/*
void LockedMethod1()
{
JackLock lock(this);
fCount++;
printf("LockedMethod1 self %x fCount %d\n", pthread_self(), fCount);
}
if (fCount >= 1000) {
printf("Terminate self %x\n", pthread_self());
pthread_exit(NULL);
}
}
void LockedMethod2()
{
JackLock lock(this);
fCount--;
fCount++;
printf("LockedMethod2 self %x fCount %d\n", pthread_self(), fCount);
if (fCount >= 1500) {
printf("Terminate self %x\n", pthread_self());
pthread_exit(NULL);
}
}
void LockedMethod3()
{
JackLock lock(this);
fCount--;
fCount++;
printf("LockedMethod3 self %x fCount %d\n", pthread_self(), fCount);
if (fCount >= 3000) {
printf("Terminate self %x\n", pthread_self());
pthread_exit(NULL);
}
}
*/
void LockedMethod1()
{
pthread_cleanup_push(CleanupHandler, this);
Lock();
fCount++;
//printf("LockedMethod1 self %x fCount %d\n", pthread_self(), fCount);
if (fCount >= 1000) {
printf("Terminate self = %x count = %d\n", pthread_self(), fCount);
pthread_exit(NULL);
}
Unlock();
pthread_cleanup_pop(0);
}
void LockedMethod2()
{
pthread_cleanup_push(CleanupHandler, this);
Lock();
fCount++;
//printf("LockedMethod2 self %x fCount %d\n", pthread_self(), fCount);
if (fCount >= 1500) {
printf("Terminate self = %x count = %d\n", pthread_self(), fCount);
pthread_exit(NULL);
}
Unlock();
pthread_cleanup_pop(0);
}
void LockedMethod3()
{
pthread_cleanup_push(CleanupHandler, this);
Lock();
fCount++;
//printf("LockedMethod3 self %x fCount %d\n", pthread_self(), fCount);
if (fCount >= 3000) {
printf("Terminate self = %x count = %d\n", pthread_self(), fCount);
pthread_exit(NULL);
}
Unlock();
pthread_cleanup_pop(0);
}
};
struct TestThread : public JackRunnableInterface {
JackThread* fThread;
JackMachThread* fThread;
LockedObject* fObject;
int fNum;
TestThread(LockedObject* obj, int num)
{
printf("TestThread\n");
fThread = new JackMachThread(this);
fObject = obj;
fNum = num;
fThread->StartSync();
}
}
virtual ~TestThread()
{
printf("DELETE %x\n", fThread);
fThread->Kill();
delete fThread;
}
bool Execute()
{
//printf("TestThread Execute\n");
switch (fNum) {
case 1:
fObject->LockedMethod1();
/*
if (fObject->fCount >= 500) {
printf("Terminate self %x\n", pthread_self());
fThread->Terminate();
}
*/
break;
case 2:
fObject->LockedMethod2();
/*
if (fObject->fCount >= 1500) {
printf("Terminate self %x\n", pthread_self());
fThread->Terminate();
}
*/
break;
case 3:
fObject->LockedMethod3();
/*
if (fObject->fCount >= 2000) {
printf("Terminate self %x\n", pthread_self());
fThread->Terminate();
}
*/
break;
};
//usleep(fNum * 1000);
return true;
}
};
static void* TestThread1_Execute(void* arg);
struct TestThread1 : public JackRunnableInterface {
pthread_t fThread;
LockedObject* fObject;
int fNum;
TestThread1(LockedObject* obj, int num)
{
if (jack_client_create_thread(NULL, &fThread, 0, 0, TestThread1_Execute, this))
jack_error( "Can't create the network manager control thread." );
fObject = obj;
fNum = num;
}
virtual ~TestThread1()
{}
bool Execute()
{
printf("TestThread Execute\n");
......@@ -108,21 +233,76 @@ struct TestThread : public JackRunnableInterface {
break;
};
usleep(fNum * 1000);
//usleep(fNum * 1000);
return true;
}
};
static void* TestThread1_Execute(void* arg)
{
TestThread1* obj = (TestThread1*)arg;
while (true) {
//printf("TestThread Execute\n");
switch (obj->fNum) {
case 1:
obj->fObject->LockedMethod1();
break;
case 2:
obj->fObject->LockedMethod2();
break;
case 3:
obj->fObject->LockedMethod3();
break;
};
//usleep(obj->fNum * 1000);
}
return 0;
}
int main (int argc, char * const argv[])
{
char c;
LockedObject obj;
TestThread th1(&obj, 1);
TestThread th2(&obj, 2);
TestThread th3(&obj, 3);
/*
LockedObject obj;
TestThread1 th1(&obj, 1);
TestThread th2(&obj, 2);
TestThread th3(&obj, 3);
*/
while ((c = getchar()) != 'q') {}
/*
while ((c = getchar()) != 'q') {
}
*/
while (true) {
usleep(1000);
th1.fThread->Kill();
}
/*
th1.fThread->Kill();
th2.fThread->Kill();
th3.fThread->Kill();
while (true) {
//usleep(100000);
th1.fThread->Kill();
}
*/
}
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment