Preciso passar vários argumentos para uma função que gostaria de chamar em um segmento separado. Eu li que a maneira típica de fazer isso é definir uma estrutura, passar um ponteiro para a função e desreferenciá-la para os argumentos. No entanto, não consigo fazer isso funcionar:
#include <stdio.h>
#include <pthread.h>
struct arg_struct {
int arg1;
int arg2;
};
void *print_the_arguments(void *arguments)
{
struct arg_struct *args = (struct arg_struct *)args;
printf("%d\n", args -> arg1);
printf("%d\n", args -> arg2);
pthread_exit(NULL);
return NULL;
}
int main()
{
pthread_t some_thread;
struct arg_struct args;
args.arg1 = 5;
args.arg2 = 7;
if (pthread_create(&some_thread, NULL, &print_the_arguments, (void *)&args) != 0) {
printf("Uh-oh!\n");
return -1;
}
return pthread_join(some_thread, NULL); /* Wait until thread is finished */
}
A saída para isso deve ser:
5
7
Mas quando eu o executo, eu realmente obtenho:
141921115
-1947974263
Alguém sabe o que estou fazendo de errado?
Respostas:
Porque voce diz
struct arg_struct *args = (struct arg_struct *)args;
ao invés de
struct arg_struct *args = arguments;
fonte
usar
no lugar de
fonte
main()
tem suas próprias variáveis de thread e pilha. aloque memória para 'args' no heap ou torne-o global:Então, é claro, altere as referências de
args->arg1
paraargs.arg1
etc.fonte
Usar:
E passe esses argumentos assim:
Não se esqueça de args grátis! ;)
fonte
Os argumentos de print_the_arguments são argumentos, então você deve usar:
fonte
-> esta atribuição está errada, quero dizer que o argumento variável deve ser usado neste contexto. Felicidades!!!
fonte
Na criação de thread desse código, o endereço de um ponteiro de função está sendo passado. O original
pthread_create(&some_thread, NULL, &print_the_arguments, (void *)&args) != 0
Deve ser lido como
pthread_create(&some_thread, NULL, print_the_arguments, (void *) &args)
Uma boa maneira de lembrar é que todos os argumentos dessa função devem ser endereços.
some_thread
é declarado estaticamente, então o endereço é enviado corretamente usando&
.Eu criaria uma
pthread_attr_t
variável, usariapthread_attr_init()
nela e passaria o endereço dessa variável. Mas, passar umNULL
ponteiro também é válido.O
&
na frente do rótulo da função é o que está causando o problema aqui. O rótulo usado já é umvoid*
para uma função, portanto, apenas o rótulo é necessário.Dizer
!= 0
com o argumento final pareceria causar um comportamento indeterminado. Adicionar isso significa que um booleano está sendo passado em vez de uma referência.A resposta de Akash Agrawal também é parte da solução para o problema desse código.
fonte
Tenho a mesma pergunta do autor do pôster original, Michael.
No entanto, tentei aplicar as respostas enviadas para o código original sem sucesso
Depois de algumas tentativas e erros, aqui está minha versão do código que funciona (ou pelo menos funciona para mim!). E se você olhar com atenção, notará que é diferente das soluções postadas anteriormente.
fonte