免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
12下一页
最近访问板块 发新帖
查看: 4730 | 回复: 14
打印 上一主题 下一主题

帮我看哈这个在linux下多线程编程-条件变量编程,哪儿出错了!! [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2011-11-13 11:03 |只看该作者 |倒序浏览
/* condmutex.c
*
*/  
#include <stdlib.h>   
#include <stdio.h>   
#include <pthread.h>   
#include <errno.h>     

int gnum = 0;                // globle variable
pthread_mutex_t mutex;        
pthread_cond_t  cond;         


void pthread_func_1 (void);     
void pthread_func_2 (void);     
int main (void)     
{     
    pthread_t tid1 = 0;     
    pthread_t tid2 = 0;     
    int ret = 0;     
      
    pthread_mutex_init (&mutex, NULL);   
    pthread_cond_init(&cond,NULL);  
    ret = pthread_create (&tid1, NULL, (void *)pthread_func_1, NULL);  
    if (ret != 0) {     
        perror ("pthread_1_create";     
    }     
      
    ret = pthread_create (&tid2, NULL, (void *)pthread_func_2, NULL);
    if (ret != 0) {     
        perror ("pthread_2_create";     
    }
    sleep(1);     
    pthread_join (tid1, NULL);     
    pthread_join (tid2, NULL);     
      
    printf ("main programme exit!/n";   
    return 0;     
}   

void pthread_func_1 (void)     
{     
    int i = 0;     
      
    for (i; i<10; i++)     
    {     
        printf ("This is pthread1!/n";      
        pthread_mutex_lock(&mutex);             // acquire mutex lock
     
        while (gnum <= 3) {  
            pthread_cond_wait(&cond, &mutex);  
        }

        gnum = 0;   // gnum++;  // critical resource.  
        printf ("Thread1 add one to num:%d/n", gnum);  
        pthread_mutex_unlock(&mutex);     // release mutex lock
        sleep (1);  
    }     
    pthread_exit(0);
}     
void pthread_func_2 (void)     
{     
    int i = 0;     
      
    for (i; i<15; i++)     
    {     
        printf ("This is pthread2!/n";   
        pthread_mutex_lock(&mutex);         // acquire nutex lock.
        gnum++;  
        printf ("Thread2 add one to num:%d/n", gnum);  
  
        if(gnum == 4) {   
            pthread_cond_signal(&cond);  
        }
        pthread_mutex_unlock(&mutex);   
        sleep(1);
    }     

    pthread_exit (0);     
}   

程序运行起来就没得结果的!也不知道多线程的该怎么调试....谢谢解答

论坛徽章:
0
2 [报告]
发表于 2011-11-13 16:00 |只看该作者
线程1获得互斥量后等待线程2触发条件量,线程2等待线程1释放互斥量,这样会死锁的,楼主还是好好看看互斥量和条件量的使用吧

论坛徽章:
0
3 [报告]
发表于 2011-11-15 16:18 |只看该作者
楼主这程序有什么问题吗?
程序工作得很好,没问题.
唯一的问题就是,没有打印出结果来,可这也是由于楼主将 "\n"  写成了 "/n"导致的,改过来就好了.

论坛徽章:
0
4 [报告]
发表于 2011-11-15 16:31 |只看该作者
本帖最后由 crazyhadoop 于 2011-11-17 13:14 编辑

对于多线程的调试,其实也很简单的:
用GDB进行多线程调试

a.新线程创建、退出以及线程切换信息提示:这些信息的具体显示依赖于具体的操作系统,但所表达的含义是相同,在SUSE Linux上其信息如同下面所示:

(1) 新线程创建:[New Thread -1209853024 (LWP 32705)]

(2) 线程退出:[Thread -1209853024 (LWP 32705) exited]

(3) 发生运行线程切换:[Switching to Thread -1209853024 (LWP 32705)]


b.线程信息的查看:i/info threads

gdb会显示当前调试程序中所有线程信息并标识出当前线程,每个线程信息的格式如下:


•<线程号> <线程信息>
<位置信息>


(1)

•: *用于标识gdb当前的线程上下文,其是唯一的

(2) <线程号>: 由gdb分配的线程唯一标识,而非操作系统线程标识,用于gdb相关命令中标识线程

(3) <线程信息>: 依赖于具体的操作系统,在SUSE Linux下,信息如同:“Thread -1209853024 (LWP 32705)”

(4) <位置信息>: 对于包含调试信息的代码,其包含了当前所在源文件、代码行和函数信息;而对于没有调试信息的代码,其包含了指令地址、可执行文件等信息

c.当前线程的切换

在调试多线程程序时,我们经常需要来回查看多个线程的堆栈信息,这时可用命令:"thread <线程号>"将指定的线程设定为当前线程。<线程号>是gdb所分配线程标识,

可用“info threads”查看


d.设置某个线程的断点

在前面所讲到关于“断点设置”的命令都是针对系统中所有的线程,gdb允许只对指定的线程设置断点,命令格式如下:

break <location> thread <线程号> [if ...]


该命令实际上是在普通断点设置之后,追加对于线程的限制。如果包含了断点条件设置,则条件设置应放在线程限制信息之后


e.线程调度锁

在调试多线程程序时,有时不希望gdb因为其它线程遇到某个断点或接受到某个信号,而打断了当前线程的调试;或根本就不期望其它线程运行。

这时可打开线程调度锁,从而禁止线程切换的发生。缺省情况下,gdb调试程序时是关闭线程调度锁的。

(1) set scheduler-locking on/off: 打开/关闭线程调度锁

(2) show scheduler-locking: 查看当前线程调度锁的设置状态

论坛徽章:
0
5 [报告]
发表于 2011-11-17 20:52 |只看该作者
pthread_t tid1 = 0;     
pthread_t tid2 = 0;
这俩句可能在不同的系统下会出错,应为线程号不像进程号那样只是非负整数,在可移植性操作系统中他们不能当整数处理,这样才有了pthread_equal存在的必要。

有产生死锁的可能,加入线程1先执行,条件量不成立,阻塞;线程2接着执行,对同一把锁进行枷锁,就会产生死锁

论坛徽章:
0
6 [报告]
发表于 2011-11-18 17:22 |只看该作者
这个,你确定会产生死锁吗?
这里是条件变量呢,线程1阻塞在条件变量上,自动解锁,线程2就可执行了,哪来的死锁?

论坛徽章:
1
拜羊年徽章
日期:2015-03-03 16:15:43
7 [报告]
发表于 2011-11-19 22:15 |只看该作者
本帖最后由 linuxfellow 于 2011-11-19 22:37 编辑
对于多线程的调试,其实也很简单的:
用GDB进行多线程调试

a.新线程创建、退出以及线程切换信息提示:这些 ...
qqrilxk 发表于 2011-11-15 16:31



    我最近正为交互式GDB调试头痛,请大家帮我看看。
就以一楼的程序为例,在GDB下, 设置两个断点:
(GDB) b main
(GDB) b pthread_create
(GDB) run
程序停在main
(GDB) continue
程序停在pthread_create
(GDB) s
(GDB) next
(GDB) finish
这些命令有时行, 有时不行;运气好时,我能跳到pthread_create的下一行,查看产生的线程,并转到线程
很多时候, s/next/finish后GDB就挂在那里了
不知有什么办法让我能可靠地next到下一句语句? 多谢!

论坛徽章:
1
拜羊年徽章
日期:2015-03-03 16:15:43
8 [报告]
发表于 2011-11-19 22:29 |只看该作者
对于多线程的调试,其实也很简单的:
用GDB进行多线程调试

a.新线程创建、退出以及线程切换信息提示:这些 ...
qqrilxk 发表于 2011-11-15 16:31


我也在做交互式多线程的GDB调试,我碰到下面的问题:
以一楼的程序为例:
在pthread_create设置断点,程序会停在那里:
(GDB)b pthread_create
但下一步无论是单步step还是跳过去都不行。不稳定,时可时不可。很多时候GDB挂到那里。 如果跳过去了,GDB就可以转到线程
可能是产生的线程影响了GDBSERVER.我一下子新建6个线程。有时么办法能让GDB可靠地跳过pthread_create? 多谢!

论坛徽章:
1
拜羊年徽章
日期:2015-03-03 16:15:43
9 [报告]
发表于 2011-11-19 22:35 |只看该作者
不好意思,发了两次:第一次送帖后server告诉我:你的回复来路不明,不能上贴。server刷新也慢,没看到我的帖子。只好很郁闷地又敲了一次。

论坛徽章:
0
10 [报告]
发表于 2011-11-21 10:05 |只看该作者
你把代码和调试时的现象,问题具体一点贴出来吧,没太明白你的问题.你具体想干什么呢,想单步进入线程中或跳过线程体的调试?
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP