免费注册 查看新帖 |

Chinaunix

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

创建线程时的几个陷阱 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2010-01-12 10:04 |只看该作者 |倒序浏览

题记:弄清楚线程何时启动,怎么结束!
转载时请注明出处和作者联系方式
文章出处:
http://www.limodev.cn/blog
作者联系方式:李先静
前几天帮同事查一个多线程的BUG,不到十秒钟我就找到了问题的根源。N年前我曾犯过类似的错误,呵,今天仍然有人在重复。这些问题都比较典型,把它们写出来,供新手参考吧。
o 用临时变量作为线程参数的问题。
#include
#include
#include
void* start_routine(void* param)
{
    char* str = (char*)param;
    printf("%s:%s\n", __func__, str);
    return NULL;
}
pthread_t create_test_thread()
{
    pthread_t id = 0;
    char str[] = "it is ok!";
    pthread_create(&id, NULL, start_routine, str);
    return id;
}
int main(int argc, char* argv[])
{
    void* ret = NULL;
    pthread_t id = create_test_thread();
    pthread_join(id, &ret);
    return 0;
}
分析:由于新线程和当前线程是并发的,谁先谁后是无法预测的。可 能create_test_thread 已经执行完成,str已经被释放了,新线程才拿到这参数,此时它的内容已经无法确定了,自然打印出的字符串是随机的。
o 线程参数共享的问题。
#include
#include
#include  
void* start_routine(void* param)
{
    int index = *(int*)param;
    printf("%s:%d\n", __func__, index);
    return NULL;
}
#define THREADS_NR 10
void create_test_threads()
{
    int i = 0;
    void* ret = NULL;
    pthread_t ids[THREADS_NR] = {0};
    for(i = 0; i
分析:由于新线程和当前线程是并发的,谁先谁后是无法预测的。i在不断变化,所以新线程拿到的参数值是无法预知的,自然打印出的字符串也是随机的。
o 虚假并发。
#include
#include
#include
void* start_routine(void* param)
{
    int index = *(int*)param;
    printf("%s:%d\n", __func__, index);
    return NULL;
}
#define THREADS_NR 10
void create_test_threads()
{
    int i = 0;
    void* ret = NULL;
    pthread_t ids[THREADS_NR] = {0};
    for(i = 0; i
分析:因为pthread_join会阻塞直到线程退出,所以这些线程实际上是串行执行的,一个退出了,才创建下一个。当年一个同事写了一个多线程的测试程序,就是这样写的,结果没有测试出一个潜伏的问题,直到产品运行时,这个问题才暴露出来
在某个机器的运行结果:
ʹÓÃÄÚ½¨ specs¡£
Ä¿±ê£ºi386-redhat-linux
ÅäÖÃΪ£º../configure --prefix=/usr --mandir=/usr/share/man --infodir=/usr/share/info --enable-shared --enable-threads=posix --enable-checking=release --with-system-zlib --enable-__cxa_atexit --disable-libunwind-exceptions --enable-libgcj-multifile --enable-languages=c,c++,objc,obj-c++,java,fortran,ada --enable-java-awt=gtk --disable-dssi --with-java-home=/usr/lib/jvm/java-1.4.2-gcj-1.4.2.0/jre --with-cpu=generic --host=i386-redhat-linux
Ïß³ÌÄ£ÐÍ£ºposix
gcc °æ±¾ 4.1.0 20060304 (Red Hat 4.1.0-3)
[root@dep4 test]#
(3)
[root@dep4 test]# ./tes
start_routine:0
start_routine:1
start_routine:2
start_routine:3
start_routine:4
start_routine:5
start_routine:6
start_routine:7
start_routine:8
start_routine:9
[root@dep4 test]#
(2)
[root@dep4 test]# ./pthreadtes
start_routine:0
start_routine:1
start_routine:2
start_routine:3
start_routine:4
start_routine:5
start_routine:6
start_routine:7
start_routine:8
start_routine:9
[root@dep4 test]# ./pthreadtes
start_routine:8
start_routine:8
start_routine:8
start_routine:8
start_routine:4
start_routine:5
start_routine:6
start_routine:7
start_routine:8
start_routine:9
[root@dep4 test]# ./pthreadtes
(1)
start_routine:
[root@dep4 test]# ./lpthreadtes
start_routine:
[root@dep4 test]# ./lpthreadtes
start_routine:
[root@dep4 test]# ./lpthreadtes
start_routine:
[root@dep4 test]# ./lpthreadtes
start_routine:
[root@dep4 test]# ./lpthreadtes
start_routine:
[root@dep4 test]#
               
               
               

本文来自ChinaUnix博客,如果查看原文请点:http://blog.chinaunix.net/u2/64117/showart_2146391.html
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

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

清除 Cookies - ChinaUnix - Archiver - WAP - TOP