包含如下API:
1. pthread_equal
2. pthread_self
3. pthread_create
4. pthread_exit
5. pthread_join
6. pthread_cancel
7. pthread_cleanup_push
8. pthread_cleanup_pop
9. pthread_detach
10. pthread_mutex_init
11. pthread_mutex_destroy
1-pthread_equal
pthread_equal - compare thread IDs
#include <pthread.h>
int pthread_equal(pthread_t t1, pthread_t t2);
//Returns: nonzero if equal, 0 otherwise
2-pthread_self
pthread_self - obtain ID of the calling thread
#include <pthread.h>
pthread_t pthread_self(void);
//Returns: the thread ID of calling thread
3-pthread_create
pthread_create - create a new thread
#include <pthread.h>
int pthread_create(pthread_t *thread, const pthread_attr_t *attr,
void *(*start_routine) (void *), void *arg);
//Return: 0 if OK, error number on failure
参数
attr
用于定制线程属性(customize various attribute),为NULL时表示默认属性
start_routine
,在创建线程后,新线程运行在start_routine的地址
arg
用于传递参数,如果想传递一个以上参数,需要将他们保存在structure
中,然后传递进去
线程的注意点
- 可以使用process的地址空间,并且继承调用者的
float-point enviornment
和signal mask
- 但是: the set of pending signals都被清除
- 若要在新建thread中得到thread ID,不要将create的参数
thread
的值传递给新线程,因为可能在pthread_create返回前,新线程就开始执行了,那么thread是垃圾值。 - Linux有过用clone实现thread的可能
example
#include <stdio.h>
#include <pthread.h>
pthread_t ntid;
void printids(const char *s)
{
pid_t pid;
pthread_t tid;
pid = getpid();
tid = pthread_self();
printf("%s pid %lu tid %lu (0x%lx)\n", s, (unsigned long)pid,
(unsigned long)tid, (unsigned long)tid);
}
void * thr_fn(void *arg)
{
printids("new thread: ");
return((void *)0);
}
int main(void)
{
int err;
err = pthread_create(&ntid, NULL, thr_fn, NULL);
if (err != 0)
{
fprintf(stderr, "pthread_create error!\n");
}
printids("main thread:");
sleep(1);
exit(0);
}
4-pthread_exit
pthread_exit - terminate calling thread
#include <pthread.h>
void pthread_exit(void *retval);//retval会被pthread_join捕获
5-pthread_join
pthread_join - join with a terminated thread
#include <pthread.h>
int pthread_join(pthread_t thread, void **retval);
//Return: 0 if OK, error number on failure
注意点
- 如果相关线程被取消,
retval
被设置为PTHREAD_CANCELED
- 通过调用
pthread_join
,我们自动将pthread
设置为detached state
,这样的他的资源可以被恢复。 - 如果调用
pthread_join
的线程已经处于detached state
,出错并且返回EINVAL
线程中return和pthread_exit区别
return仅能返回整数
pthread_exit能返回更多得信息,比如返回结构体,如果该结构体是局部变量分配的,那么可能会被改变内容。可以使用全局变量或者malloc
6-pthread_cancel
send a cancellation request to a thread
#include <pthread.h>
int pthread_cancel(pthread_t thread);
//Return: 0 if OK, error number on failure
不等待thread terminate, 仅仅是发送请求
7-thread cleanup handlers
类似于atexit
这些handlers保存在stack中,意味着它们以注册的反序执行
pthread_cleanup_push, pthread_cleanup_pop - push and pop thread cancellation clean-up handlers
#include <pthread.h>
void pthread_cleanup_push(void (*routine)(void *),
void *arg);
void pthread_cleanup_pop(int execute);
如果execute
设置为0,cleanup function不会被调用。否则会将最近register的handler移除。
8- pthread_detach
pthread_detach - detach a thread
#include <pthread.h>
int pthread_detach(pthread_t thread);
//Returns:0 if OK, error number on failure
9- pthread_mutex_init/destroy
pthread_mutex_destroy, pthread_mutex_init - destroy and initialize a mutex
#include <pthread.h>
int pthread_mutex_destroy(pthread_mutex_t *mutex);
int pthread_mutex_init(pthread_mutex_t *restrict mutex,
const pthread_mutexattr_t *restrict attr);
//Returns: 0 if OK, error number on failure
10- pthread_mutex_lock/trylock/unlock
pthread_mutex_lock, pthread_mutex_trylock, pthread_mutex_unlock - lock and unlock a mutex
#include <pthread.h>
int pthread_mutex_lock(pthread_mutex_t *mutex);
int pthread_mutex_trylock(pthread_mutex_t *mutex);
int pthread_mutex_unlock(pthread_mutex_t *mutex);
//Returns: 0 if OK, error number on failure
11-pthread_rwlock_destroy, pthread_rwlock_init
destroy and initialize a read-write lock object
#include <pthread.h>
int pthread_rwlock_destroy(pthread_rwlock_t *rwlock);
int pthread_rwlock_init(pthread_rwlock_t *restrict rwlock, const pthread_rwlockattr_t *restrict attr);
//Return: 0 if OK, error number on failure
注意点
- 动态分配的rwlock需要在释放前调用 destroy,不然该lock所占有的资源会丢失
12- pthread_rwlock_rdlock/wrlock/unlock
#include <pthread.h>
int pthread_rwlock_rdlock(pthread_rwlock_t *rwlock);
int pthread_rwlock_wrlock(pthread_rwlock_t *rwlock);
int pthread_rwlock_unlock(pthread_rwlock_t *rwlock);
//Return: 0 if OK, error number on failure
注意点
- 实现在shared mode(read-locked)下有数量限制,因此我们需要检查rdlock的返回值
- rwlock、unlock仅在使用未初始化的锁 或者 试图获得本身已经拥有的锁 这两种情况下返回错误值,一般我们不需要检查返回值。
13-pthread_rwlock_tryrdlock/trywrlock
#include <pthread.h>
int pthread_rwlock_tryrdlock(pthread_rwlock_t *rwlock);
int pthread_rwlock_trywrlock(pthread_rwlock_t *rwlock);
//Return: 0 if OK, error number on failure
类似mutex的trylock,适合用于lock hierarchy不足以避免死锁的情况
14-pthread_condi_init/destroy
pthread_cond_destroy, pthread_cond_init - destroy and initialize condition variables
#include <pthread.h>
int pthread_cond_destroy(pthread_cond_t *cond);
int pthread_cond_init(pthread_cond_t *restrict cond, const pthread_condattr_t *restrict attr);
//returns:0 if OK, error number on failure
pthread_cond_t cond = PTHREAD_COND_INITIALIZER;
当attr = NULL时,使用默认属性。
15-pthread_cond_wait/timedwait
pthread_cond_timedwait, pthread_cond_wait - wait on a condition
#include <pthread.h>
int pthread_cond_timedwait(pthread_cond_t *restrict cond,
pthread_mutex_t *restrict mutex,
const struct timespec *restrict abstime);
int pthread_cond_wait(pthread_cond_t *restrict cond,
pthread_mutex_t *restrict mutex);
//return: 0 if OK, error number on failure
- wait是等待condition(条件)为真,wait return时,mutex自动上锁
- timespec 结构体的使用方法
struct timespec{
time_t tv_sec; /*seconds*/
long tv_nsec; /*nanoseconds*/
};
将现在的时间+3分钟,来表示等待3分钟
16- pthread_con_signal/broadcast
pthread_cond_broadcast, pthread_cond_signal - broadcast or signal a condition
#include <pthread.h>
int pthread_cond_broadcast(pthread_cond_t *cond);
int pthread_cond_signal(pthread_cond_t *cond);
//returns: 0 if OK, error number on failure