Global Sources
EE Times-India
Stay in touch with EE Times India
 
EE Times-India > Embedded
 
 
Embedded  

Using Pthreads in embedded Linux designs (Part 1)

Posted: 11 Jul 2014     Print Version  Bookmark and Share

Keywords:Linux  POSIX  Pthreads  API  multi-tasking 

A thread may terminate by calling pthread_exit(). The argument to pthread_exit() is the start routine's return value.

In much the same way that a parent process can wait for a child to complete by calling waitpid(), a thread can wait for another thread to complete by calling pthread_join(). The arguments to pthread_join() are the ID of the thread to wait on and a place to store the thread's return value. The calling thread is blocked until the target thread terminates.

A thread can determine its own ID by calling pthread_self(). Finally, a thread can voluntarily yield the processor by calling sched_yield().

Figure 3: Sample Thread Program.

Note that most of the functions above return an int value. This reflects the threads approach to error handling. Rather than reporting errors in the global variable errno, threads functions report errors through their return value. This is because errno is global and visible to all threads. This makes it susceptible to the same kind of preemption problem we saw earlier in discussing interrupts.

Figure 3 is a simple example of creating a thread. To make it simpler, error return status has been ignored. This is a thread version of the traditional Hello World program.

All thread programs must include the header file pthread.h. This program reates a thread, passing as the argument the first element of argv passed to main. After telling us it created a thread, the main function waits for the thread to terminate and then outputs the returned value.

The thread simply prints its argument as a string and returns the argument as its value. Note that a thread may terminate by simply returning rather than calling pthread_exit().

Figure 4 illustrates the life cycle of a thread as represented by a state machine. A thread is "born" by the pthread_create() function, which places it in the ready state. A thread runs when it is scheduled. The running thread may be blocked because it must wait for some resource, or it may be preempted either because a higher priority thread is ready to run or its timeslice has expired.

Figure 4: Thread State Machine.

When the resource becomes available a blocked thread transitions to the Ready state and will eventually be scheduled to run again. Finally, a thread is terminated when it is done or another thread requests its cancellation.

Thread Termination. A thread may be terminated either voluntarily or involuntarily. A thread terminates itself either by simply returning or by calling pthread_exit(). In the latter case, all cleanup handlers that the thread registered by calls to pthread_cleanup_push() are called prior to termination.

A thread may be involuntarily terminated if another thread cancels it. The cleanup handlers are also called in this case. We'll return to the notion of cleanup handlers and thread cancellation later.

Threads have an attribute called detach state. The detach state determines whether or not a thread can be joined when it terminates. The default detach state is PTHREAD_CREATE_JOINABLE, meaning that the thread can be joined on termination. The alternative is PTHREAD_CREATE_DETACHED, which means the thread can't be joined.

Joining is useful for two reasons: either you need the thread's return value, or you need to be sure the thread has terminated before proceeding. Otherwise it's better to create the thread detached. The resources of a joinable thread can't be recovered until another thread joins it whereas a detached thread's resources can be recovered as soon as it terminates. Most multi-tasking kernels have no concept of a joinable task. All tasks are detached.

Attribute Objects. POSIX provides an open-ended mechanism for extending the API through the use of attribute objects. For each pthread object there is a corresponding attribute object. This attribute object is effectively an extended argument list to the related object create function. A pointer to an attribute object is always the second argument to a create function. If this argument is NULL the create function uses appropriate default values.

An important philosophical point is that all pthread objects are considered to be "opaque". This means that you never directly access members of the object itself. All access is through API functions that get and set the member fields of the object.

 First Page Previous Page 1 • 2 • 3 • 4 Next Page Last Page



Comment on "Using Pthreads in embedded Linux des..."
Comments:  
*  You can enter [0] more charecters.
*Verify code:
 
 
Webinars

Seminars

Visit Asia Webinars to learn about the latest in technology and get practical design tips.

 

Go to top             Connect on Facebook      Follow us on Twitter      Follow us on Orkut

 
Back to Top