2011-11-05 4 views
5

Je suis coréen et je ne suis pas bon en anglais mais si vous me donnez un commentaire là-bas
Je serai très heureux et je vais essayer de le comprendre.pthread (erreur de segmentation)

J'ai créé, par exemple, 10 threads et j'ai essayé de les joindre après la création et de renvoyer la valeur.
Mais quand je rejoins le dernier thread, j'obtiens un défaut de segmentation.

Le résultat est comme ça ..

Before Thread 1 create 
After Thread 1 create 
Before Thread 0 create 
After Thread 0 create 
Before Thread 1 join 
After Thread 1 join 
Before Thread 0 join 
Segmentation Fault(core dumped) 

lorsque je crée 4 fils, il est comme

Before Thread 3 create 
After Thread 3 create 
Before Thread 2 create 
After Thread 2 create 
Before Thread 1 create 
After Thread 1 create 
Before Thread 0 create 
After Thread 0 create 
Before Thread 3 join 
After Thread 3 join 
Before Thread 2 join 
After Thread 2 join 
Before Thread 1 join 
After Thread 1 join 
Before Thread 0 join 
Segmentation Fault(core dumped) 

Je ne peux pas sembler trouver pourquoi.

#include <stdio.h> 
#include <stdlib.h> 
#include <pthread.h> 
#include <unistd.h> 

pthread_mutex_t mutex_lock; 

struct arg_struct { 
     int a; 
     int b; 
}; 

void *t_function(void *data) { 
     pthread_mutex_lock(&mutex_lock); 

     struct arg_struct *arg = (struct arg_struct *)data; 
     long int s; 

     s = arg->a; 

     pthread_mutex_unlock(&mutex_lock); 

     return (void **)s; 
} 

int main() 
{ 
     int i; 

     pthread_t p_thread[2]; 
     int thr_id; 
     int status; 

     struct arg_struct arg[2]; 

     for(i = 1; i >= 0; i--) { 
       arg[i].a = i; 
       arg[i].b = i; 
     } 

     pthread_mutex_init(&mutex_lock, NULL); 

     for(i = 1; i >= 0; i--) { 
       printf("Before Thread %d create\n", i); 
       thr_id = pthread_create(&p_thread[i],NULL, t_function, (void *)&arg[i]); 
       printf("After Thread %d create\n", i); 
       usleep(1000); 
     } 

     int temp[2]; 

     for(i = 1; i >= 0; i--) { 
       printf("Before Thread %d join\n", i); 
       pthread_join(p_thread[i], (void**)&status); 
       printf("After Thread %d join\n", i); 
       temp[i] = status; 
     }i 

     printf("%d%d", temp[1], temp[0]); 

     pthread_mutex_destroy(&mutex_lock); 

     return 0; 
} 
+0

Je ne peux pas reproduire cela, j'ai essayé 2 et 4 discussions. Cela fonctionne parfaitement, même à l'intérieur de Valgrind. Pouvez-vous nous dire autre chose sur le problème? – VolatileDream

+1

Avez-vous essayé un débogueur? gdb est ton ami. – vanza

+1

Bienvenue sur SO. :-) –

Répondre

9
pthread_t p_thread[2]; 
    struct arg_struct arg[2]; 
    int temp[2]; 

Vous seul espace alloué deux éléments ici, donc si vous lancez plus de 2 fils vous précipitez la fin du tableau et peut-être un accident ou corrompre la pile.

De plus:

  pthread_join(p_thread[i], (void**)&status); 

status est un int, pas un void *; tenter cela va essayer de stocker un void * dans un int. Sur de nombreuses plates-formes 64 bits, cela débordera également (puisque void * sera 8 octets alors que int est 4). Faites status un void *, et arrêtez d'essayer de rejeter les erreurs du compilateur comme ceci. Ce sont des erreurs pour une raison.

+0

quand je lance plus de 2 threads j'ai changé ces nombres. – IKS

+0

Bon point, mais nous ne pouvons toujours pas expliquer la segfault sur 2 threads bien. – VolatileDream

+0

@IKS, vous devrez montrer le code où vous avez changé ces chiffres, il est parfaitement possible que vous ayez oublié d'en changer un. Mieux encore, commencez à utiliser '# define's ou une variable pour définir le nombre de threads à lancer, et utilisez à la fois les boucles et les allocations de matrice pour utiliser cette variable/macro, afin d'éviter les incohérences. – bdonlan