Chinaunix首页 | 论坛 | 博客
  • 博客访问: 1738997
  • 博文数量: 438
  • 博客积分: 9799
  • 博客等级: 中将
  • 技术积分: 6092
  • 用 户 组: 普通用户
  • 注册时间: 2012-03-25 17:25
文章分类

全部博文(438)

文章存档

2019年(1)

2013年(8)

2012年(429)

分类: 系统运维

2012-03-31 23:16:47

没有包含在pthread_attr_t结构体里的两个线程属性是取消状态和取消类型。这些属性影响了一个线程响应pthread_cancel(11.5节)调用的行为。


响应状态属性可以是PTHREAD_CANCEL_ENABLE或PTHREAD_CANCEL_DISABLE。一个线程可以改变它的取消状态,通过调用pthread_setcancelsatate。



  1. #include <pthread.h>

  2. int pthread_setcancelstate(int state, int *oldstate);

  3. 成功返回0,失败返回错误号。


在一个原子操作里,pthread_setcancelstate设置当前的取消状态为state,并存储之前的取消状态到oldstate所指的内存位置。


回 想11.5节,一个pthread_cancel的调用不等待一个线程的终止。在默认情况下,线程将在取消请求发出后继续执行,直到这个线程到达取消点。 一个取消点是线程检查它是否被取消并执行这个请求的位置。POSIX.1保证取消点将发生在当一个线程调用下表列出的任何函数时。


POSIX.1定义的取消点
acceptmq_timedsendputpmsgsigsuspend
aio_suspendmsgrcvpwritesigtimedwait
clock_nanosleepmsgsndreadsigwait
closemsyncreadvsigwaitinfo
connectnanosleeprecvsleep
creatopenrecvfromsystem
fcnt12pauserecvmsgtcdrain
fsyncpollselectusleep
getmsgpreadsem_timedwaitwait
getpmsgpthread_cond_timedwaitsem_waitwaitid
lockfpthread_cond_waitsendwaitpid
mq_receivepthread_joinsendmsgwrite
mq_sendpthread_testcancelsendtowritev
mq_timedreceiveputmsgsigpause

一 个线程以默认的的PTHREAD_CANCEL_ENABLE取消状态启动。当状态被设为PTHREAD_CANCEL_DISABLE时,一个 pthread_cancel将不会杀死这个线程。相反,取消请求为这个线程保持待定。当状态再次启用时,线程将在下个取消点响应任何待定的取消请求。

除了上表列出的函数,POSIX.1还列出下表中的函数作为可选取消点。


POSIX.1定义的可选取消点
catcloseftellgetwcprintf
catgetsftellogetwcharputc
catopenftwgetwdputc_unlocked
closedirfwprintfglobputchar
closelogfwriteiconv_closeputchar_unlocked
ctermidfwscanficonv_openputs
dbm_closegetcioctlpututxline
dbm_deletegetc_unlockedlseekputwc
dbm_fetchgetcharmkstempputwchar
dbm_nextkeygetchar_unlockednftwreaddir
dbm_opengetcwdopendirreaddir_r
dbm_storegetdateopenlogremove
dlclosegetgrentpcloserename
dlopengetgrgidperrorrewind
endgrentgetgrgid_rpopenrewinddir
endhostentgetgrnamposix_fadvisescanf
endnetentgetgrnam_rposix_fallocateseekdir
endprotoentgethostbyaddrposix_madvisesemop
endpwentgethostbynameposix_spawnsetgrent
endserventgethostentposix_spawnpsethostent
endutxentgethostnameposix_trace_clearsetnetent
fclosegetloginposix_trace_closesetprotoent
fcntlgetlogin_rposix_trace_createsetpwent
fflushgetnetbyaddrposix_trace_create_withlogsetservent
fgetcgetnetbynameposix_trace_eventtypelist_getnext_idsetutxent
fgetposgetnetentposix_trace_eventtypelist_rewindstrerror
fgetsgetprotobynameposix_trace_flushsyslog
fgetwcgetprotobynumberposix_trace_get_attrtmpfile
fgetwsgetprotoentposix_trace_get_filtertmpnam
fopengetpwentposix_trace_get_statusttyname
fprintfgetpwnamposix_trace_getnext_eventttyname_r
fputcgetpwnam_rposix_trace_openungetc
fputsgetpwuidposix_trace_rewindungetwc
fputwcgetpwuid_rposix_trace_set_filterunlink
fputwsgetsposix_trace_shutdownvfprintf
freadgetservbynameposix_trace_timedgetnext_eventvfwprintf
freopengetservbyportposix_typed_mem_openvprintf
fscanfgetserventpthread_rwlock_rdlockvwprintf
fseekgetutxentpthread_rwlock_timedrdlockwprintf
fseekogetutxidpthread_rwlock_timedwrlockwscanf
fsetposgetutxlinepthread_rwlock_wrlock

注意上表列出的函数中有几个在本文不会再讨论。许多在SUS里是可选的。

如果你的应用在很长时间内没有调用上面两个表中的某个函数(比如受计算机限制),那么你可以调用pthread_testcancel来在你的程序里加入你自己的取消点。



  1. #include <pthread.h>

  2. void pthread_testcancel(void);


当你调用pthread_testcancel时,如果一个取消请求已经待定,且取消没有被禁止,那么线程将被取消。当取消被禁止时,调用pthread_testcancel没有效果。


我们已经描述过的默认取消类型被称为延迟取消。在pthread_cancel调用后,真实的取消不会发生,直到线程碰到一个取消点。我们可以调用pthread_setcanceltype来改变取消类型。



  1. #include <pthread.h>

  2. int pthread_setcanceltype(int type, int *oldtype);

  3. 成功返回0,失败返回错误号。


type参数可以是PTHREAD_CANCEL_DEFERRED或PTHREAD_CANCEL_ASYNCHRONOUS。pthread_setcanceltype函数设置取消类型为type并返回之前的类型到oldtype所指的整型。


异步取消和延迟取消区别在于线程可以随时被取消。线程不必击中一个取消点来被取消。
阅读(2271) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~