<p>I have used fork() in C to start another process. How do I start a new thread?</p>

[{'answer_id': 56818, 'author': 'epatel', 'author_id': 842, 'author_profile': 'https://Stackoverflow.com/users/842', 'pm_score': 3, 'selected': False, 'text': '<p>pthreads is a good start, look <a href="https://computing.llnl.gov/tutorials/pthreads/" rel="noreferrer">here</a></p>\n'}, {'answer_id': 56822, 'author': 'Jay Conrod', 'author_id': 1891, 'author_profile': 'https://Stackoverflow.com/users/1891', 'pm_score': 2, 'selected': False, 'text': '<p>Check out the <a href="https://computing.llnl.gov/tutorials/pthreads/" rel="nofollow noreferrer">pthread</a> (POSIX thread) library.</p>\n'}, {'answer_id': 56825, 'author': 'Commodore Jaeger', 'author_id': 4659, 'author_profile': 'https://Stackoverflow.com/users/4659', 'pm_score': 7, 'selected': True, 'text': '<p>Since you mentioned fork() I assume you\'re on a Unix-like system, in which case <a href="http://en.wikipedia.org/wiki/POSIX_Threads" rel="noreferrer">POSIX threads</a> (usually referred to as pthreads) are what you want to use.</p>\n\n<p>Specifically, pthread_create() is the function you need to create a new thread. Its arguments are:</p>\n\n<pre><code>int  pthread_create(pthread_t  *  thread, pthread_attr_t * attr, void *\n   (*start_routine)(void *), void * arg);\n</code></pre>\n\n<p>The first argument is the returned pointer to the thread id. The second argument is the thread arguments, which can be NULL unless you want to start the thread with a specific priority. The third argument is the function executed by the thread. The fourth argument is the single argument passed to the thread function when it is executed.</p>\n'}, {'answer_id': 56829, 'author': 'Brannon', 'author_id': 5745, 'author_profile': 'https://Stackoverflow.com/users/5745', 'pm_score': 4, 'selected': False, 'text': "<p>AFAIK, ANSI C doesn't define threading, but there are various libraries available.</p>\n\n<p>If you are running on Windows, link to msvcrt and use _beginthread or _beginthreadex.</p>\n\n<p>If you are running on other platforms, check out the pthreads library (I'm sure there are others as well).</p>\n"}, {'answer_id': 56986, 'author': 'botismarius', 'author_id': 4528, 'author_profile': 'https://Stackoverflow.com/users/4528', 'pm_score': 3, 'selected': False, 'text': '<p>Threads are not part of the C standard, so the only way to use threads is to use some library (eg: POSIX threads in Unix/Linux, _beginthread/_beginthreadex if you want to use the C-runtime from that thread or just CreateThread Win32 API)</p>\n'}, {'answer_id': 52453291, 'author': 'Ciro Santilli OurBigBook.com', 'author_id': 895245, 'author_profile': 'https://Stackoverflow.com/users/895245', 'pm_score': 4, 'selected': False, 'text': '<p><strong>C11 threads + C11 <code>atomic_int</code></strong></p>\n\n<p>Added to glibc 2.28. Tested in Ubuntu 18.10 amd64 (comes with glic 2.28) and Ubuntu 18.04 (comes with glibc 2.27) by compiling glibc 2.28 from source: <a href="https://stackoverflow.com/questions/847179/multiple-glibc-libraries-on-a-single-host/52454603#52454603">Multiple glibc libraries on a single host</a></p>\n\n<p>Example adapted from: <a href="https://en.cppreference.com/w/c/language/atomic" rel="noreferrer">https://en.cppreference.com/w/c/language/atomic</a></p>\n\n<p>main.c</p>\n\n<pre><code>#include &lt;stdio.h&gt;\n#include &lt;threads.h&gt;\n#include &lt;stdatomic.h&gt;\n\natomic_int atomic_counter;\nint non_atomic_counter;\n\nint mythread(void* thr_data) {\n    (void)thr_data;\n    for(int n = 0; n &lt; 1000; ++n) {\n        ++non_atomic_counter;\n        ++atomic_counter;\n        // for this example, relaxed memory order is sufficient, e.g.\n        // atomic_fetch_add_explicit(&amp;atomic_counter, 1, memory_order_relaxed);\n    }\n    return 0;\n}\n\nint main(void) {\n    thrd_t thr[10];\n    for(int n = 0; n &lt; 10; ++n)\n        thrd_create(&amp;thr[n], mythread, NULL);\n    for(int n = 0; n &lt; 10; ++n)\n        thrd_join(thr[n], NULL);\n    printf("atomic     %d\\n", atomic_counter);\n    printf("non-atomic %d\\n", non_atomic_counter);\n}\n</code></pre>\n\n<p><a href="https://github.com/cirosantilli/linux-kernel-module-cheat/blob/e0fb39c92ae071a444cb92fbb2d0c1977fa7af51/userland/c/atomic.c" rel="noreferrer">GitHub upstream</a>.</p>\n\n<p>Compile and run:</p>\n\n<pre><code>gcc -ggdb3 -std=c11 -Wall -Wextra -pedantic -o main.out main.c -pthread\n./main.out\n</code></pre>\n\n<p>Possible output:</p>\n\n<pre><code>atomic     10000\nnon-atomic 4341\n</code></pre>\n\n<p>The non-atomic counter is very likely to be smaller than the atomic one due to racy access across threads to the non-atomic variable.</p>\n\n<p>See also: <a href="https://stackoverflow.com/questions/2353371/how-to-do-an-atomic-increment-and-fetch-in-c/30878480#30878480">How to do an atomic increment and fetch in C?</a></p>\n\n<p><strong>Disassembly analysis</strong></p>\n\n<p>Disassemble with:</p>\n\n<pre><code>gdb -batch -ex "disassemble/rs mythread" main.out\n</code></pre>\n\n<p>contains:</p>\n\n<pre><code>17              ++non_atomic_counter;\n   0x00000000004007e8 &lt;+8&gt;:     83 05 65 08 20 00 01    addl   $0x1,0x200865(%rip)        # 0x601054 &lt;non_atomic_counter&gt;\n\n18              __atomic_fetch_add(&amp;atomic_counter, 1, __ATOMIC_SEQ_CST);\n   0x00000000004007ef &lt;+15&gt;:    f0 83 05 61 08 20 00 01 lock addl $0x1,0x200861(%rip)        # 0x601058 &lt;atomic_counter&gt;\n</code></pre>\n\n<p>so we see that the atomic increment is done at the instruction level with the <a href="https://stackoverflow.com/questions/8891067/what-does-the-lock-instruction-mean-in-x86-assembly"><code>f0</code> lock prefix</a>.</p>\n\n<p>With <code>aarch64-linux-gnu-gcc</code> 8.2.0, we get instead:</p>\n\n<pre><code>11              ++non_atomic_counter;\n   0x0000000000000a28 &lt;+24&gt;:    60 00 40 b9     ldr     w0, [x3]\n   0x0000000000000a2c &lt;+28&gt;:    00 04 00 11     add     w0, w0, #0x1\n   0x0000000000000a30 &lt;+32&gt;:    60 00 00 b9     str     w0, [x3]\n\n12              ++atomic_counter;\n   0x0000000000000a34 &lt;+36&gt;:    40 fc 5f 88     ldaxr   w0, [x2]\n   0x0000000000000a38 &lt;+40&gt;:    00 04 00 11     add     w0, w0, #0x1\n   0x0000000000000a3c &lt;+44&gt;:    40 fc 04 88     stlxr   w4, w0, [x2]\n   0x0000000000000a40 &lt;+48&gt;:    a4 ff ff 35     cbnz    w4, 0xa34 &lt;mythread+36&gt;\n</code></pre>\n\n<p>so the atomic version actually has a <code>cbnz</code> loop that runs until the <code>stlxr</code> store succeed. Note that ARMv8.1 can do all of that with a single LDADD instruction.</p>\n\n<p>This is analogous to what we get with C++ <code>std::atomic</code>: <a href="https://stackoverflow.com/questions/31978324/what-exactly-is-stdatomic/58904448#58904448">What exactly is std::atomic?</a></p>\n\n<p><strong>Benchmark</strong></p>\n\n<p>TODO. Crate a benchmark to show that atomic is slower.</p>\n\n<p><strong>POSIX threads</strong></p>\n\n<p>main.c</p>\n\n<pre><code>#define _XOPEN_SOURCE 700\n#include &lt;assert.h&gt;\n#include &lt;stdlib.h&gt;\n#include &lt;pthread.h&gt;\n\nenum CONSTANTS {\n    NUM_THREADS = 1000,\n    NUM_ITERS = 1000\n};\n\nint global = 0;\nint fail = 0;\npthread_mutex_t main_thread_mutex = PTHREAD_MUTEX_INITIALIZER;\n\nvoid* main_thread(void *arg) {\n    int i;\n    for (i = 0; i &lt; NUM_ITERS; ++i) {\n        if (!fail)\n            pthread_mutex_lock(&amp;main_thread_mutex);\n        global++;\n        if (!fail)\n            pthread_mutex_unlock(&amp;main_thread_mutex);\n    }\n    return NULL;\n}\n\nint main(int argc, char **argv) {\n    pthread_t threads[NUM_THREADS];\n    int i;\n    fail = argc &gt; 1;\n    for (i = 0; i &lt; NUM_THREADS; ++i)\n        pthread_create(&amp;threads[i], NULL, main_thread, NULL);\n    for (i = 0; i &lt; NUM_THREADS; ++i)\n        pthread_join(threads[i], NULL);\n    assert(global == NUM_THREADS * NUM_ITERS);\n    return EXIT_SUCCESS;\n}\n</code></pre>\n\n<p>Compile and run:</p>\n\n<pre><code>gcc -std=c99 -Wall -Wextra -pedantic -o main.out main.c -pthread\n./main.out\n./main.out 1\n</code></pre>\n\n<p>The first run works fine, the second fails due to missing synchronization.</p>\n\n<p>There don\'t seem to be POSIX standardized atomic operations: <a href="https://stackoverflow.com/questions/1130018/unix-portable-atomic-operations">UNIX Portable Atomic Operations</a> </p>\n\n<p>Tested on Ubuntu 18.04. <a href="https://github.com/cirosantilli/cpp-cheat/blob/1778918f77bc913915386e602ad29f8505e73073/posix/pthread_mutex.c" rel="noreferrer">GitHub upstream</a>.</p>\n\n<p><strong>GCC <code>__atomic_*</code> built-ins</strong></p>\n\n<p>For those that don\'t have C11, you can achieve atomic increments with the <code>__atomic_*</code> GCC extensions.</p>\n\n<p>main.c </p>\n\n<pre><code>#define _XOPEN_SOURCE 700\n#include &lt;pthread.h&gt;\n#include &lt;stdatomic.h&gt;\n#include &lt;stdio.h&gt;\n#include &lt;stdlib.h&gt;\n\nenum Constants {\n    NUM_THREADS = 1000,\n};\n\nint atomic_counter;\nint non_atomic_counter;\n\nvoid* mythread(void *arg) {\n    (void)arg;\n    for (int n = 0; n &lt; 1000; ++n) {\n        ++non_atomic_counter;\n        __atomic_fetch_add(&amp;atomic_counter, 1, __ATOMIC_SEQ_CST);\n    }\n    return NULL;\n}\n\nint main(void) {\n    int i;\n    pthread_t threads[NUM_THREADS];\n    for (i = 0; i &lt; NUM_THREADS; ++i)\n        pthread_create(&amp;threads[i], NULL, mythread, NULL);\n    for (i = 0; i &lt; NUM_THREADS; ++i)\n        pthread_join(threads[i], NULL);\n    printf("atomic     %d\\n", atomic_counter);\n    printf("non-atomic %d\\n", non_atomic_counter);\n}\n</code></pre>\n\n<p>Compile and run:</p>\n\n<pre><code>gcc -ggdb3 -O3 -std=c99 -Wall -Wextra -pedantic -o main.out main.c -pthread\n./main.out\n</code></pre>\n\n<p>Output and generated assembly: the same as the "C11 threads" example.</p>\n\n<p>Tested in Ubuntu 16.04 amd64, GCC 6.4.0.</p>\n'}]
['https://Stackoverflow.com/questions/56810', 'https://Stackoverflow.com', 'https://Stackoverflow.com/users/2077/']