View Bug Activity | Format For Printing
I found a bug about the return value of pthread_create. The posix expects EAGAIN for lack of memory, but in fact, it returns ENOMEM. This problem can be reproduced by the following code: -------------------------------------------------------------------- #include <stdio.h> #include <sys/mman.h> #include <errno.h> #include <stdlib.h> #include <unistd.h> #include <pthread.h> #include <string.h> void use_up_memory(void) { char *c; int PAGESIZE = getpagesize(); while (1) { c = mmap(NULL, PAGESIZE, PROT_NONE, MAP_ANON | MAP_PRIVATE, -1, 0); if (c == MAP_FAILED) break; } printf("errno %d: %s\n", errno, strerror(errno)); } void child() { sleep(1); } int main(int argc, char *argv[]) { int err; pthread_t tid; use_up_memory(); err = pthread_create(&tid, NULL, (void *)child, NULL); if (err) { printf("pthread_cretate returns %d: %s\n", err, strerror(err)); return 1; } err = pthread_join(tid, NULL); if (err){ printf("pthread_join returns %d\n", err); return 1; } return 0; } -------------------------------------------------------------------- The result is as follows: ---------------------------------------------------------- $ ./test_pthread_create errno 12: Cannot allocate memory pthread_cretate returns 12: Cannot allocate memory ----------------------------------------------------------
Created an attachment (id=2073) patch to fix the bug
This is tested with glibc version 2.7. And the attached patch fixes the bug. After applying the patch, the test result is: ----------------------------------------------------------- $ ./test_pthread_create errno 12: Cannot allocate memory pthread_cretate returns 11: Resource temporarily unavailable -----------------------------------------------------------
Fixed in cvs trunk but noth with the patch you provided.
pthread_create() calls the static function creat_thread(), and this funciton at last calls __clone(), __clone() may set errno to ENOMEM. So why not check the ENOMEM in pthread_create(), it won't miss any ENOMEM case.
(In reply to comment #4) > So why not check > the ENOMEM in pthread_create(), it won't miss any ENOMEM case. Because unlike crappy proprietary software we don't settle for garbage.