Re: Using POSIX threads with Cocoa?
Re: Using POSIX threads with Cocoa?
- Subject: Re: Using POSIX threads with Cocoa?
- From: Michael Rothwell <email@hidden>
- Date: Tue, 20 Apr 2004 22:23:23 -0400
It looks like their "setup" code merely creates two threads to call
doTimer() and doInput(), and then waits for both to exit (i.e.,
pthread_join() ).
You could do something similar using NSThread rather than using
pthreads directly. If you need to be notified when one of these worker
threads exits, put a performSelectorOnMainThread at the bottom of each
thread function. For example:
static TeleoInterface* teleoInterface;
static pthread_mutex_t teleoThreadMutex;
-(int) doInput:(id)owner
{
uint8 c;
// see what characters there are ready to look at
while ( 1 )
{
if ( TI_get( teleoInterface, &c, 1 ) == TELEO_OK )
{
//printf( "%d ", c );
TeleoEasy_Lock();
TC_input( teleoChannel, c );
TeleoEasy_Unlock();
}
}
// notify thread is ending -- not that it ever will, thanks to the
while(1) above (is that right?)
[self performSelectorOnMainThread:@selector(doInputExited:)
withObject:nil
waitUntilDone:NO ];
return 0;
}
-(void)TeleoEasy_Start
{
pthread_mutex_init( &teleoThreadMutex, NULL );
[NSThread detachNewThreadSelector:@selector(doInput:)
toTarget:self
withObject:self];
};
TeleoEasy_Lock() and TeleoEasy_Unlock() depend on your initialization
of static pthread_mutex_t teleoThreadMutex -- I would assume other
parts of their library also use that mutex, so you probably can't
substitute an NSLock, and I would definitely initialize it.
TeleoEasy_Continue() would, indeed, prevent NSApplicationMain from
running. Don't call it. Or at the least, gut it.
How are these worker threads supposed to interact with your
application's main thread?
Hope that helps.
Michael Rothwell
email@hidden
On Apr 17, 2004, at 1:38 PM, Vince Ackerman wrote:
I'm new to Obj C and I don't know much about using threads as I've been
away from Mac and C programing for a long time. Hope you guys can help.
I've been trying to learn Obj C by writing an app in Cocoa that uses a
third parties library to control some USB devices and have run into
several problems (previously was the C style callback topic). I've
asked the authors of the library/devices I'm using for help but they're
not Cocoa programmers and can't really figure out why it's not woking
(though they're in the process of learning Cocoa.... I hope).
It looks like they're running several threads in their sample code,
one's a timer function and another an input thread.
Here are two functions that they want me to call after I do some
initialization stuff (these are built into their library):
static TeleoInterface* teleoInterface;
static pthread_t teleoInputThread;
static pthread_t teleoTimerThread;
static pthread_mutex_t teleoThreadMutex;
void TeleoEasy_Start()
{
// Create the mutex
pthread_mutex_init( &teleoThreadMutex, NULL );
// Fire up the input thread
pthread_create( &teleoInputThread, NULL, doInput, NULL );
// Fire up the timer thread
pthread_create( &teleoTimerThread, NULL, doTimer, NULL );
}
void TeleoEasy_Continue() // Waits for the library to exit
{
pthread_join( teleoInputThread, NULL );
pthread_join( teleoTimerThread, NULL );
pthread_mutex_destroy( &teleoThreadMutex );
}
void* doTimer( void *data )
{
uint8 c;
while( true )
{
TeleoEasy_Lock();
TC_timerEvent( teleoChannel, EVENT_TIME );
TMM_timerModuleEvent( teleoModuleManager, EVENT_TIME );
TeleoEasy_Unlock();
usleep( EVENT_TIME * 1000 );
}
}
void* doInput( void* data )
{
uint8 c;
// see what characters there are ready to look at
while ( 1 )
{
if ( TI_get( teleoInterface, &c, 1 ) == TELEO_OK )
{
//printf( "%d ", c );
TeleoEasy_Lock();
TC_input( teleoChannel, c );
TeleoEasy_Unlock();
}
}
return NULL;
}
The TeleoEasy_Continue() call appears to be a run loop (they call it in
main() ) which interferes with NSApplicationMain(argc, argv). If I
comment it out, NSApplicationMain works, and the callbacks I've set up
work fine, but the getvalue() setvalue() stuff I need to call doesn't
seem to go any where. At launch time I've detached a dummy NSThread
since the Apple Cocoa docs say you have to force Multithreading:
- (void) dummyThread: (id) dummyObject
{
int x,y;
for(x = 0,y = 0; x<10; x++) // Not sure what I need to accomplish in
the dummy thread?
{
y = x;
}
}
- (BOOL) startMultithread
{
[NSThread detachNewThreadSelector:@selector(dummyThread:)
toTarget:self withObject: NULL ];
return [NSThread isMultiThreaded];
}
// ------------------------------------------------------
The USB device docs also tell me that if I don't use the
TeleoEasy_Continue() call then I must use their lock/unlock calls
before using any of the setter/getter functions:
void TeleoEasy_Lock()
{
pthread_mutex_lock( &teleoThreadMutex );
}
void TeleoEasy_Unlock()
{
pthread_mutex_unlock( &teleoThreadMutex );
}
I have tried various combinations using the lock/unlock calls or the
TeleoEasy_Continue() but it doesn't seem to matter. I'm not
communicating with the devices for some reason. Not really knowing
much about threads this maybe a stupid question, but should I be using
NSLock instead? Don't know where to start looking for this answer.
Apples docs don't say much except this:
//--------------------------------//
Using POSIX Threads
NSThreads are built upon POSIX threads (pthreads). You can create your
own pthreads, but you must be cautious about using Cocoa from them.
When you detach an NSThread, Cocoa enters a multithreaded mode, which
activates greater thread safety measures. When you create your own
pthreads, Cocoa does not know to change modes. To force Cocoa into its
multithreaded mode, you must detach an NSThread, which could
immediately exit. To identify whether Cocoa is already in multithreaded
mode, use the NSThread class method isMultiThreaded.
If you need access to the pthread within an NSThread, call the
pthread_self function from within that thread.
//-------------------------------//
Thanks in advance. This list and all it's members is an invaluable
resource!
Vince
_______________________________________________
cocoa-dev mailing list | email@hidden
Help/Unsubscribe/Archives:
http://www.lists.apple.com/mailman/listinfo/cocoa-dev
Do not post admin requests to the list. They will be ignored.
_______________________________________________
cocoa-dev mailing list | email@hidden
Help/Unsubscribe/Archives:
http://www.lists.apple.com/mailman/listinfo/cocoa-dev
Do not post admin requests to the list. They will be ignored.