Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/276.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C 使用pthreads时出现SegFault_C_Pthreads - Fatal编程技术网

C 使用pthreads时出现SegFault

C 使用pthreads时出现SegFault,c,pthreads,C,Pthreads,我正在尝试为我的OS类开发一个项目,在使用pthreads时,我遇到了一个SegFault,但我不确定是什么导致了这个问题 关于该计划,我正在努力完成以下计划: 在南非克鲁格国家公园的某处有一个很深的峡谷,有一根绳子横跨峡谷。 狒狒可以在绳索上摆动手,穿过峡谷,但是如果两个狒狒在相反的方向相遇,它们会战斗并掉落到它们的死亡中。此外,绳子的强度只能容纳三只狒狒。如果绳子上同时有更多的狒狒,绳子就会断。假设我们可以教狒狒使用信号量,我们想设计一个具有以下属性的同步方案 一旦狒狒开始穿越,就可以保证它

我正在尝试为我的OS类开发一个项目,在使用pthreads时,我遇到了一个SegFault,但我不确定是什么导致了这个问题

关于该计划,我正在努力完成以下计划:

在南非克鲁格国家公园的某处有一个很深的峡谷,有一根绳子横跨峡谷。 狒狒可以在绳索上摆动手,穿过峡谷,但是如果两个狒狒在相反的方向相遇,它们会战斗并掉落到它们的死亡中。此外,绳子的强度只能容纳三只狒狒。如果绳子上同时有更多的狒狒,绳子就会断。假设我们可以教狒狒使用信号量,我们想设计一个具有以下属性的同步方案

  • 一旦狒狒开始穿越,就可以保证它不会撞到另一边的狒狒
  • 绳子上的狒狒永远不会超过三只。狒狒穿过绳索的顺序应保持不变;i、 e.进入绳索的顺序应为退出绳索的顺序
  • 持续不断的狒狒从一个方向穿过不应该阻止狒狒无限期地往另一个方向走(没有饥饿)。解决此要求,以保持FIFO顺序。也就是说,一只狒狒试图向左/向右交叉,而它到达的时间比另一只狒狒试图向相反方向交叉的时间要早,它首先会爬上绳子
  • 基本上,我是在读一个文本文件,然后模拟一个先进先出系统,在这个系统中,一些猴子正试图通过一个绳桥。 奇怪的是,我能够让程序运行几次,但它经常会导致一个错误

    pthread_create(&eastern[i],NULL,(void *) &east_side,(void *)&id[i]);
    pthread_create(&western[i],NULL,(void *) &west_side,(void *)&id[i]);
    
    东侧和西侧在下面

    void* east_side(void*arg)            
    {
        int baboon = *(int*)arg;
        int on_rope;
        sem_wait(&deadlock_protection);
        sem_wait(&east_mutex);
        east++;
        if (east == 1)
        {
            sem_wait(&rope);
            printf("Baboon %d: waiting\n", baboon);
        }
        sem_post(&east_mutex);
        sem_post(&deadlock_protection);
        sem_wait(&counter);
        sem_getvalue(&counter, &on_rope);
        printf("Baboon %d: Cross rope request granted (Current crossing: left to right, Number of baboons on rope: %d)\n", baboon,3-on_rope);
        sleep(travel_time);
        sem_getvalue(&counter, &on_rope);
        printf("Baboon %d: Exit rope (Current crossing: left to right, Number of baboons on rope: %d)\n", baboon, 2-on_rope);
        sem_post(&counter);
        sem_wait(&east_mutex);
        east--;
        if (east == 0)
            sem_post(&rope);
        sem_post(&east_mutex);
    }
    
    //thread handling west to east travel
    void* west_side(void*arg)    
    {
        int baboon = *(int*)arg;
        int on_rope;
        sem_wait(&deadlock_protection);
        sem_wait(&west_mutex);
        west++;
        if (west == 1)
        {
            sem_wait(&rope);
            printf("Baboon %d: waiting\n", baboon);
        }
        sem_post(&west_mutex);
        sem_post(&deadlock_protection);
        sem_wait(&counter);
        sem_getvalue(&counter, &on_rope);
        printf("Baboon %d: Cross rope request granted (Current crossing: right to left, Number of baboons on rope: %d)\n", baboon, 3-on_rope);
        sleep(travel_time);
        sem_getvalue(&counter, &on_rope);
        printf("Baboon %d: Exit rope (Current crossing: right to left, Number of baboons on rope: %d)\n", baboon, 2-on_rope);
        sem_post(&counter);
        sem_wait(&west_mutex);
        west--;
        if (west == 0)
            sem_post(&rope);
        sem_post(&west_mutex);
    
    }
    
    我在一个纯文本文件中使用一个示例输入

    L,R,R,R,R,R,L,L,R
    
    这将创建输出:

    sh-4.3$main input.txt 5
    输入是
    L R L R
    狒狒1:请求跨越绳索(从左到右)
    狒狒1:等待
    狒狒1:允许交叉绳索请求(当前交叉:从左到右,绳索上的狒狒数量:1)
    狒狒2:请求跨越绳索(从右到左)
    狒狒3:请求跨越绳索(从右到左)
    狒狒4:请求跨越绳索(从右到左)
    狒狒5:请求跨越绳索(从右到左)
    狒狒1:出口绳索(电流交叉:从左到右,绳索上的狒狒数量:0)
    狒狒2:等待
    狒狒2:允许交叉绳索请求(当前交叉:从右到左,绳索上的狒狒数量:1)
    狒狒3:允许交叉绳索请求(当前交叉:从右到左,绳索上的狒狒数量:2)
    狒狒4:允许交叉绳索请求(当前交叉:从右到左,绳索上的狒狒数量:3)
    狒狒6:请求跨越绳索(从右到左)
    狒狒7:请求跨越绳索(从左到右)
    狒狒8:请求跨越绳索(从左到右)
    狒狒9:请求跨越绳索(从右到左)
    分段故障(堆芯转储)

    我已经包括了整个文件,以防问题实际上不是我认为的问题所在

    /*include header files*/
    
    #include <pthread.h>
    #include <stdio.h>
    #include <stdlib.h>
    #include <unistd.h>
    #include <sys/types.h>
    #include <sys/ipc.h>
    #include <sys/shm.h>
    #include <sys/wait.h>
    #include <fcntl.h>
    #include <semaphore.h>
    //#include <stdbool.h>
    
    
    //compile with command 
    //gcc -o main *.c -lpthread -lrt
    
    /*semaphores*/
    sem_t rope;
    sem_t east_mutex;
    sem_t west_mutex;
    sem_t deadlock_protection;
    sem_t counter;
    
    /*global variables*/
    int east = 0;
    int west = 0;
    int travel_time;    
    
    /*function prototypes*/
    void crossing(int x);
    void* east_side(void*);
    void* west_side(void*);
    
    /*main function*/
    int main(int argc, char *argv[])
    { 
    
        char c;
        int baboonCnt=0;
        char temp[100];
    
        sem_init(&rope,0,1);                        //ensure mutual exclusion on rope ownership
        sem_init(&east_mutex,0,1);                  //east side on travel
        sem_init(&west_mutex,0,1);                  //west side on travel
        sem_init(&deadlock_protection,0,1);         //used to prevent deadlocks while using semaphores
        sem_init(&counter,0,3);                     //ensure only 3 baboons are allowed on the rope
    
        //ensure all input arguements are entered
        if ( argc == 3 )                    
        {
            travel_time = atoi(argv[2]);
            FILE *file;
            int baboonCnt=0;
            if (file = fopen(argv[1], "r") )
            {
                while((c=getc(file))!=EOF)
                {
                    if(c == 'L'|| c == 'R')
                    {
                        temp[baboonCnt] = c;
                        baboonCnt++;
                    }
                }
            }
            else   
            {
                printf("Unable to read data from the input file.");
                return 0;
            }
            printf("The input is\n");
            int j=0;
            for(j;j<baboonCnt;++j)
            {
                printf("%c ",temp[j]);
            }
            printf("\n");
            int id[baboonCnt];
            pthread_t eastern[baboonCnt],western[baboonCnt];
            int i=0;
            for(i;i<baboonCnt;++i)
            {
                sleep(1);
                if(temp[i]=='L')
                {
                    id[i] = i+1;
                    printf("Baboon %d: Request to cross rope (left to right)\n", i+1);
                    pthread_create(&eastern[i],NULL,(void *) &east_side,(void *)&id[i]);
                }
                else if(temp[i]=='R')
                {
                    id[i] = i+1;
                    printf("Baboon %d: Request to cross rope (right to left)\n", i+1);
                    pthread_create(&western[i],NULL,(void *) &west_side,(void *)&id[i]);
                }
            }
            int k=0;
            printf("before k loop");
            for(k;k<baboonCnt;++k)
            {
    
                pthread_join(eastern[k],NULL);
                printf("eastern",k);
                pthread_join(western[k],NULL); 
                printf("western %d",k);         
            }
    
            //destroy all semaphores
            sem_destroy (&rope); 
            sem_destroy (&east_mutex);
            sem_destroy (&west_mutex);
            sem_destroy (&deadlock_protection);
            sem_destroy (&counter);
            return 0;
        }
        else
        {
            printf("Proper command line usage is: \n<name> <filename> <cross time>\n");
        }
    }
    //thread handling the east to west to travel
    void* east_side(void*arg)            
    {
        int baboon = *(int*)arg;
        int on_rope;
        sem_wait(&deadlock_protection);
        sem_wait(&east_mutex);
        east++;
        if (east == 1)
        {
            sem_wait(&rope);
            printf("Baboon %d: waiting\n", baboon);
        }
        sem_post(&east_mutex);
        sem_post(&deadlock_protection);
        sem_wait(&counter);
        sem_getvalue(&counter, &on_rope);
        printf("Baboon %d: Cross rope request granted (Current crossing: left to right, Number of baboons on rope: %d)\n", baboon,3-on_rope);
        sleep(travel_time);
        sem_getvalue(&counter, &on_rope);
        printf("Baboon %d: Exit rope (Current crossing: left to right, Number of baboons on rope: %d)\n", baboon, 2-on_rope);
        sem_post(&counter);
        sem_wait(&east_mutex);
        east--;
        if (east == 0)
            sem_post(&rope);
        sem_post(&east_mutex);
    }
    
    //thread handling west to east travel
    void* west_side(void*arg)    
    {
        int baboon = *(int*)arg;
        int on_rope;
        sem_wait(&deadlock_protection);
        sem_wait(&west_mutex);
        west++;
        if (west == 1)
        {
            sem_wait(&rope);
            printf("Baboon %d: waiting\n", baboon);
        }
        sem_post(&west_mutex);
        sem_post(&deadlock_protection);
        sem_wait(&counter);
        sem_getvalue(&counter, &on_rope);
        printf("Baboon %d: Cross rope request granted (Current crossing: right to left, Number of baboons on rope: %d)\n", baboon, 3-on_rope);
        sleep(travel_time);
        sem_getvalue(&counter, &on_rope);
        printf("Baboon %d: Exit rope (Current crossing: right to left, Number of baboons on rope: %d)\n", baboon, 2-on_rope);
        sem_post(&counter);
        sem_wait(&west_mutex);
        west--;
        if (west == 0)
            sem_post(&rope);
        sem_post(&west_mutex);
    }
    
    /*包括头文件*/
    #包括
    #包括
    #包括
    #包括
    #包括
    #包括
    #包括
    #包括
    #包括
    #包括
    //#包括
    //用命令编译
    //gcc-o main*.c-lpthread-lrt
    /*信号量*/
    钢丝绳;
    sem_t east_mutex;
    sem_t west_mutex;
    sem_t死锁保护;
    扫描电镜计数器;
    /*全局变量*/
    int东=0;
    int-west=0;
    国际旅行时间;
    /*功能原型*/
    空隙交叉(int x);
    空*东侧(空*);
    void*西侧(void*);
    /*主要功能*/
    int main(int argc,char*argv[])
    { 
    字符c;
    int狒狒cnt=0;
    炭温度[100];
    sem_init(&rope,0,1);//确保rope所有权的互斥性
    sem_init(&east_mutex,0,1);//东边旅行
    sem_init(&west_mutex,0,1);//西边旅行
    sem_init(&deadlock_protection,0,1);//用于在使用信号量时防止死锁
    sem_init(&counter,0,3);//确保绳子上只允许有3只狒狒
    //确保输入了所有输入参数
    如果(argc==3)
    {
    行程时间=atoi(argv[2]);
    文件*文件;
    int狒狒cnt=0;
    if(file=fopen(argv[1],“r”))
    {
    而((c=getc(文件))!=EOF)
    {
    如果(c='L'| | c=='R')
    {
    温度[狒狒]=摄氏度;
    狒狒cnt++;
    }
    }
    }
    其他的
    {
    printf(“无法从输入文件读取数据”);
    返回0;
    }
    printf(“输入为\n”);
    int j=0;
    
    对于(j;j而言,运行valgrind几乎可以立即检测到您的错误:

    ==10217== Use of uninitialised value of size 8
    ==10217==    at 0x4E39241: pthread_join (in /usr/lib64/libpthread-2.18.so)
    ==10217==    by 0x400E64: main (example.c:103)
    
    第103行是
    pthread_join(eastern[k],NULL);
    ;valgrind强调读取eastern数组而不进行设置

    数组未完成,您访问了未设置的元素。 您可能可以通过以下方式修改联接循环:

    for(k;k<baboonCnt;++k)
    {
        if(temp[k]=='L') {
                pthread_join(eastern[k],NULL);
                printf("eastern %d\n",k);
        }
        else if(temp[k]=='R') {
                pthread_join(western[k],NULL);
                printf("western %d\n",k);
        }
    }
    

    for(k;k正如本线程中的其他人所提到的,我在尝试访问未正确初始化的数组元素时遇到了代码错误。我在这里总结了我的更改。非常感谢@kaylum帮助我得出这一结论

    这些阵列访问发生在此处:

    for(k;k<baboonCnt;++k)
        {
    
            pthread_join(eastern[k],NULL);
            printf("eastern",k);
            pthread_join(western[k],NULL); 
            printf("western %d",k);         
        }
    

    for(k;kWhen调试segfaults、gdb(或类似调试器)绝对是无价之宝,也不是那么难学——还有很多教程可供选择:另外——你可能会通过发布一个最小的、完整的、可验证的示例得到更好的答案——更多信息请点击这里:+1获取关于使用调试器的建议——如果你自己动手而不是求助于他人,你将从长远来看学到更多用于基本调试。如果您已经用尽了调试方法,则作为迷你
    
    for(i;i<baboonCnt;++i)
        {
            sleep(1);
            if(temp[i]=='L')
            {
                id[i] = i+1;
                printf("Baboon %d: Request to cross rope (left to right)\n", i+1);
                pthread_create(&eastern[i],NULL,(void *) &east_side,(void *)&id[i]);
            }
            else if(temp[i]=='R')
            {
                id[i] = i+1;
                printf("Baboon %d: Request to cross rope (right to left)\n", i+1);
                pthread_create(&western[i],NULL,(void *) &west_side,(void *)&id[i]);
            }
        }
    
    int eastcnt=0, westcnt=0, eastid[eastBab], westid[westBab], i=0;
        for(i;i<baboonCnt;++i)
          {
            sleep(1);
            if(temp[i]=='L')
              {
            eastid[eastcnt]=i;
            printf("Baboon %d wants to cross left to right\n",i);
            pthread_create(&eastern[eastcnt],NULL, (void *) &east_side,(void *) &eastid[eastcnt] );
            ++eastcnt;
              }
            else if(temp[i]=='R')
              {
            westid[westcnt]=i;
            printf("Baboon %d wants to cross right to left\n",i);
            pthread_create(&western[westcnt],NULL, (void *) &west_side,(void *) &westid[westcnt] );
            ++westcnt;
              }
          }
    
    int k =0;
        for(k;k<westBab;++k)
        {
            pthread_join(western[k],NULL); 
        }
        k=0;
        for(k;k<eastBab;++k)
        {
            pthread_join(eastern[k],NULL); 
        }