• 设为首页
  • 收藏本站
  • 手机版
  • 微博
  • 微信
    微信公众号 添加方式:
    1:搜索微信号(888888
    2:扫描左侧二维码
  • 快捷导航
    论坛调试中-请所有人不要下载资料,下载失败,浪费积分后果自负。
    查看: 1655|回复: 0

    Linux下多线程编程的互斥与同步-嵌入式

    [复制链接]

    1万

    主题

    1291

    回帖

    2万

    积分

    管理员

    积分
    29575

    社区居民最爱沙发原创达人社区明星终身成就奖优秀斑竹奖宣传大使奖特殊贡献奖

    QQ
    发表于 2013-7-30 19:13:50 | 显示全部楼层 |阅读模式
    本文将说明如何使用信号量实现线程之间的互斥与同步。互斥锁只有0,1两中状态,适合于线程对共享资源的独占访问,很多时候每个资源可以同时被有限的线程访问,此时互斥锁将无法满足;条件变量同步也同样存在这种问题。信号量实际是一种非负整型计数器,可以很好的控制线程之间资源访问,互斥锁能实现的功能,信号量同样可以。信号量控制资源共享主要是PV原语操作, PV原语是对整数计数器信号量sem的操作。一次 P操作使 sem减一,而一次 V操作使sem 加一。进程(或线程)根据信号量的值来判断是否对公共资源具有访问权限。当信号量sem 的值大于等于零时,该进程(或线程)具有公共资源的访问权限;相反,当信号量 sem的值小于零时,该进程(或线程)就将阻塞直到信号量 sem的值大于等于 0 为止。Linux 实现了POSIX 的无名信号量,主要用于线程间的互斥同步。这里主要介绍几个常见函数。· sem_init用于创建一个信号量,并能初始化它的值。· sem_wait和sem_trywait相当于P操作,它们都能将信号量的值减一,两者的区别在 于若信号量小于零时,sem_wait将会阻塞进程,而 sem_trywait则会立即返回。· sem_post相当于V操作,它将信号量的值加一同时发出信号唤醒等待的进程。· sem_getvalue用于得到信号量的值。· sem_destroy用于删除信号量。所需头文件 #i nclude函数原型 int sem_init(sem_t *sem,int pshared,unsigned int value)sem:信号量pshared:决定信号量能否在几个进程间共享。由于目前Linux还没有实现进程间共享信号量,所以这个值只能够取0value:信号量初始化值函数返回值 成功:0 ,出错:-1所需头文件 #i nclude函数原型int sem_wait(sem_t *sem)int sem_trywait(sem_t *sem)int sem_post(sem_t *sem)int sem_getvalue(sem_t *sem)int sem_destroy(sem_t *sem)函数传入值 sem:信号量函数返回值 成功:0 ,出错:-1从上面函数来看,实现线程之间同步信号量比互斥锁使用起来相对容易一些,操作简单,容易理解,适用范围广。下面上一篇的问题用信号量来实现,线程使用部分没变,主要改变了对资源的控制方式:(代码本人亲自编译通过)view plaincopy to clipboardprint?01.#i nclude02.#i nclude03.#i nclude04.#i nclude05.#i nclude06.#i nclude07.08.int g_Flag = 0;09.sem_t sem_mutex; // 用于互斥10.sem_t sem_syn; // 用于同步11.12.void *thread1( void *arg );13.void *thread2( void *arg );14.int main()15.{16. pthread_t tid1, tid2;17. int rc1, rc2;18.19. sem_init( &sem_mutex, 0, 1 );20. sem_init( &sem_syn, 0, 0 );21. printf( " Inter main !n" );22.23. rc2 = pthread_create( &tid2, NULL, thread2, NULL );24. if( rc2 != 0 )25. printf( " %s, %d n", __func__, strerror( rc2 ) );26.27. rc1 = pthread_create( &tid1, NULL, thread1, &tid2 );28. if( rc1 != 0 )29. printf( " %s, %d n", __func__, strerror(rc1) );30. printf( " Leave main!nn" );31.32. sem_wait( &sem_syn ); // 同步等待,阻塞33. exit( 0 );34.}35.36.void *thread1( void *arg )37.{38. pthread_t *ptid = NULL;39. printf( " Enter thread1n" );40. printf( " thread1 id: %u, g_Flag: %d n", ( unsigned int )pthread_self(), g_Flag );41.42. if( sem_wait( &sem_mutex ) != 0)43. {44. perror(" pthread1 sem_mutexn");45. }46.47. if( g_Flag == 2 )48. sem_post( &sem_syn );49. g_Flag = 1;50.51. if( sem_post( &sem_mutex ) != 0)52. {53. perror( "pthread1 sem_postn" );54. }55. printf( " thread1 id: %u, g_Flag: %d n",( unsigned int )pthread_self(), g_Flag );56. printf( "Leave thread1 nn" );57.58. ptid = ( pthread_t *)arg;59. printf( " ptid = %u n", *ptid );60. pthread_join( *ptid, NULL );61. pthread_exit(0 );62.}63.64.void *thread2( void *arg )65.{66. printf( " Enter thread2 !n" );67. printf( " thread2 id: %u , g_Flag: %d n", ( unsigned int)pthread_self(), g_Flag );68.69. if( sem_wait( &sem_mutex ) != 0 )70. {71. perror( "thread2 sem_wait n" );72. }73.74. if( g_Flag == 1 )75. sem_post( &sem_syn );76.77. g_Flag = 2;78.79. if( sem_post( &sem_mutex ) != 0)80. {81. perror( " thread2 sem_postn" );82. }83. printf( " thread2 id: %u , g_Flag: %d n", ( unsigned int )pthread_self(), g_Flag );84. printf( "Leave thread2 nn" );85.86. pthread_exit(0);87.}
    回复

    使用道具 举报

    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则

    公告:服务器刚移机,
    大家请不要下载东西。
    会下载失败


    QQ 手机版 小黑屋 监管台 遇到问题请联系QQ1308068381 逆天PCB论坛

    Powered by Discuz! X3.5 © 2001-2023

    快速回复 返回顶部 返回列表