调用pthread_join函数后main不会继续

时间:2017-06-21 04:08:58

标签: c multithreading pthreads

我是pthread和多线程的新手,我编写了类似的代码。

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


void *nfc_read(void *arg)
{
    int fd = -1;   
    int ret;
    uint8_t read_data[24];

    while(1){
        ret = read_block(fd, 8, read_data);
        if(!ret){
            return (void)read_data;
        }
    }
}

int main(int argc, char *argv[])
{
    pthread_t my_thread;
    void  *returnValue;

    pthread_create(&my_thread, NULL, nfc_read, NULL);
    pthread_join(my_thread, &returnValue);

    printf("NFC card value is : %s \n", (char)returnValue);

    printf("other process");

  return 0;
}

直到 nfc_read 函数的返回值,因为我将需要运行其他代码,我不想在main中阻塞。我怎么能这样做?

1 个答案:

答案 0 :(得分:0)

这是一个示例,其中读取线程同时运行到正在执行其他工作的“主”线程(在这种情况下,打印点和休眠)。

为了简单起见,从输入设备模拟读取,逐个字符地复制常量字符串。我想,这是合理的,因为线程的同步是集中的。

对于线程同步,我使用了atomic_bool atomic_store()atomic_load() test-concurrent-read.c提供的Atomic Library(自C11起)。

我的示例应用#include <stdio.h> #include <stdlib.h> #include <pthread.h> #include <stdatomic.h> #include <unistd.h> /* sampe input */ const char sampleInput[] = "This is sample input which is consumed as if it was read from" " a (very slow) external device."; atomic_bool readDone = ATOMIC_VAR_INIT(0); void* threadRead(void *pArg) { char **pPBuffer = (char**)pArg; size_t len = 0, size = 0; int c; const char *pRead; for (pRead = sampleInput; (c = *pRead++) > 0; sleep(1)) { if (len + 1 >= size) { if (!(*pPBuffer = realloc(*pPBuffer, (size + 64) * sizeof(char)))) { fprintf(stderr, "ERROR! Allocation failed!\n"); break; } size += 64; } (*pPBuffer)[len++] = c; (*pPBuffer)[len] = '\0'; } atomic_store(&readDone, 1); return NULL; } int main() { /* start thread to read concurrently */ printf("Starting thread...\n"); pthread_t idThreadRead; /* thread ID for read thread */ char *pBuffer = NULL; /* pointer to return buffer from thread */ if (pthread_create(&idThreadRead, NULL, &threadRead, &pBuffer)) { fprintf(stderr, "ERROR: Failed to start read thread!\n"); return -1; } /* start main loop */ printf("Starting main loop...\n"); do { putchar('.'); fflush(stdout); sleep(1); } while (!atomic_load(&readDone)); putchar('\n'); void *ret; pthread_join(idThreadRead, &ret); /* after sync */ printf("\nReceived: '%s'\n", pBuffer ? pBuffer : "<NULL>"); free(pBuffer); /* done */ return 0; }

$ gcc -std=c11 -pthread -o test-concurrent-read test-concurrent-read.c

$ ./test-concurrent-read
Starting thread...
Starting main loop...
.............................................................................................

Received: 'This is sample input which is consumed as if it was read from a (very slow) external device.'

$ 

在Windows 10(64位)上用cygwin中的gcc进行编译和测试:

pBuffer

我想,值得一提的是为什么main()以及threadRead()中使用的pBuffer没有互斥锁保护。

  1. main()在调用 pthread_create()之前在thread_read() 中初始化。

  2. pBuffer正在运行时,pPBuffer仅由main()通过其pthread_join()中的传递地址使用。

  3. 可以在threadRead()中再次访问,不在 {{1}}之前授予{{1}}已结束。

  4. 我试图通过谷歌找到一个参考来确认这个程序是明确的和合理的。我能找到的最好的是SO: pthread_create(3) and memory synchronization guarantee in SMP architectures引用The Open Group Base Specifications Issue 7 - 4.12 Memory Synchronization