pthread_jion() , pthread_create() 导致的segmentation fault

本文档分析了一个因使用pthread_create和pthread_join不当导致的segmentation fault问题。在main函数中,pthread_create的返回值被错误地赋给了sock_listen_tid,导致在调用pthread_join时出现问题。当移除pthread_join后,程序运行正常。解决办法是正确处理pthread_create的返回值,并在pthread_join中传入正确的线程ID。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

下午调试程序的“segmentation fault”,先上代码:

 

 

左看右看找不到错在那,尝试去掉pthread_join, 竟然正常了。

 

注意这句:

sock_listen_tid = pthread_create(&sock_listen_tid,NULL,listen_thread,NULL);

 

pthread_create的返回值赋给了sock_listen_tid,这行代码看起来的确的确的确有些怪~

 

看函数说明 man 3 pthread_create

 

函数返回值描述如下:

 

RETURN VALUE

       If successful, the pthread_create() function shall return  zero;  otherwise,

       an error number shall be returned to indicate the error.


ERRORS

       The pthread_create() function shall fail if:


       EAGAIN The  system  lacked the necessary resources to create another thread,

              or the system-imposed limit on the  total  number  of  threads  in  a

              process {PTHREAD_THREADS_MAX} would be exceeded.


       EINVAL The value specified by attr is invalid.


       EPERM  The  caller  does not have appropriate permission to set the required

              scheduling parameters or scheduling policy.


       The pthread_create() function shall not return an error code of [EINTR].


       The following sections are informative.

 

 

如果创建成功, pthread_create将返回0. 赋值给sock_listen_tid等于0。然后执行pthread_join(0, NULL),相当于等待线程号为0的线程,当然segmentation fault

 

 

``` typedef struct { pthread_mutex_t hLock; volatile int iIsRun; void* (* volatile pfnTask)(void*); //函数指针 void *arg; //任务参数 }Task; typedef struct { pthread_mutex_t StackLock; int iIDStack[MAX_TASK_NUM]; int iTopPointer; }Stack; static Stack g_IDTaskStack; static Task stTaskQueueAry[MAX_TASK_NUM]; //static int iTaskCount = 0; //static pthread_mutex_t stMutexQueue; //static pthread_cond_t stCondQueue; static pthread_t stThreadAry[cmnDfn_WORKING_PTHREAD_NUMBER]; void* PthreadPoolWorker(void* arg) { int iRet = -1; int iTskID = (int)(long)arg; Task *pstTsk = &stTaskQueueAry[iTskID]; while(g_iExit == 0) { LOCK(pstTsk->hLock) { if (pstTsk->iIsRun == 0) { sleep(1); continue; } } iRet = (int)(long)pstTsk->pfnTask(pstTsk->arg); if (iRet == 0) { continue; } LOCK(pstTsk->hLock) { pstTsk->pfnTask = NULL; pstTsk->iIsRun = 0; } LOCK(g_IDTaskStack.StackLock) { g_IDTaskStack.iIDStack[++g_IDTaskStack.iTopPointer] = iTskID; } if(iRet < 0) { break; } } iRet = 0; return (void *)(long)iRet; } int ThreadPoolSubmit(void* (*task)(void*),void* arg,int *piTskID) { //int iLoopNum; int iTskID = 0; /*for(iLoopNum = 0; iLoopNum < MAX_TASK_NUM;iLoopNum++) { if (stTaskQueueAry[iLoopNum].pfnTask == NULL) { break; } } if(iLoopNum >= MAX_TASK_NUM) { return -1; }*/ if(g_IDTaskStack.iTopPointer < 0) { return -1; } LOCK(g_IDTaskStack.StackLock) { iTskID = g_IDTaskStack.iIDStack[g_IDTaskStack.iTopPointer--]; assert(iTskID >= 0 && iTskID < MAX_TASK_NUM); } LOCK(stTaskQueueAry[iTskID].hLock) { stTaskQueueAry[iTskID].pfnTask = task; stTaskQueueAry[iTskID].arg = arg; stTaskQueueAry[iTskID].iIsRun = 1; *piTskID = iTskID; } return 0; } int ThreadPoolInit(void) { int iLoopNum; int iRet = -1; int iTskID = 0; g_IDTaskStack.iTopPointer = -1; if(pthread_mutex_init(&g_IDTaskStack.StackLock,NULL) < 0) { cmn_PrtError("Error in initializing stack mutex"); } for(iLoopNum = 0; iLoopNum < cmnDfn_WORKING_PTHREAD_NUMBER; iLoopNum++) { g_IDTaskStack.iIDStack[++g_IDTaskStack.iTopPointer] = iLoopNum; } for(iLoopNum = 0; iLoopNum < cmnDfn_WORKING_PTHREAD_NUMBER; iLoopNum++) { if(pthread_mutex_init(&stTaskQueueAry[iLoopNum].hLock,NULL) < 0) { cmn_PrtError("Error in initializing mutex"); } if(pthread_create(&stThreadAry[iLoopNum],NULL,PthreadPoolWorker,(void *)(long)iTskID) != 0) { cmn_PrtError("Error in creating thread"); } stTaskQueueAry[iLoopNum].pfnTask = NULL; stTaskQueueAry[iLoopNum].iIsRun = 0; iTskID++; } iRet = 0; _Exit: return iRet; } int ThreadPoolDestroy(void) { int iLoopNum; int iRet = -1; g_iExit = 1; for(iLoopNum = 0; iLoopNum < cmnDfn_WORKING_PTHREAD_NUMBER; iLoopNum++) { pthread_join(stThreadAry[iLoopNum], NULL); } for(iLoopNum = 0; iLoopNum < cmnDfn_WORKING_PTHREAD_NUMBER; iLoopNum++) { pthread_mutex_destroy(&stTaskQueueAry[iLoopNum].hLock); } iRet = 0; return iRet; }```段错误 (核心已转储)
03-19
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值