Wird eine URL angefordert wird ein Worker-Thread mit curl-multi gestartet. Ist curl fertig wird der Thread wieder beendet.
Eigentlich total sinnlos, aber das habe ich erst bemerkt als es fast fertig war.
Daher noch eine Warnung:
Die Benutzung fuehrt zu unendlichem SNAFU
1 #include <stdio.h> 2 #include <pthread.h> 3 #include <unistd.h> 4 #include <curl/curl.h> 5 6 static pthread_t __worker = 0; 7 static CURL *__curl_hnd; 8 static pthread_mutex_t __worker_mutex; // lock this when exiting while(handl 9 es) 10 11 12 static __attribute__ ((constructor)) void __cos_mutex() 13 { 14 pthread_mutex_init(&__worker_mutex, NULL); 15 printf ("Created mutex\n"); 16 } 17 18 static __attribute__ ((destructor)) void __dcos_mutex() 19 { 20 pthread_mutex_destroy(&__worker_mutex); 21 printf ("Destroyed mutex\n"); 22 } 23 24 static void *__fetcher_worker(void *p) 25 { 26 int msgs_in_queue, handles = 1; 27 char *curlinfo_private; 28 void (*feed_function)(void*, void*); 29 CURLMsg *cmsg; 30 31 printf("Started worker thread\n"); 32 33 34 while (1) 35 { 36 while ((cmsg = curl_multi_info_read(__curl_hnd, &msgs_in_queue)) != 37 NULL) 38 if (cmsg->msg == CURLMSG_DONE) 39 { 40 curl_easy_getinfo(cmsg->easy_handle, CURLINFO_PRIVATE, 41 &curlinfo_private); 42 feed_function = (void*)curlinfo_private; 43 feed_function(NULL, NULL); 44 curl_easy_cleanup(cmsg->easy_handle); 45 } 46 47 pthread_mutex_lock(&__worker_mutex); 48 if (handles == 0) 49 { 50 curl_multi_cleanup(__curl_hnd); 51 __worker = 0; 52 __curl_hnd = NULL; 53 pthread_mutex_unlock(&__worker_mutex); 54 break; 55 } 56 pthread_mutex_unlock(&__worker_mutex); 57 58 curl_multi_perform(__curl_hnd, &handles); 59 } 60 61 printf("Stopped worker thread\n"); 62 63 return NULL; 64 } 65 66 static void __fetcher_worker_start() 67 { 68 __worker = 1; 69 70 __curl_hnd = curl_multi_init(); 71 72 pthread_create(&__worker, NULL, __fetcher_worker, NULL); 73 74 //pthread_join(__worker, NULL); 75 pthread_detach(__worker); 76 } 77 78 void fetcher_add_url(char *url, void *function, void *userdata) 79 { 80 CURL *hnd; 81 82 hnd = curl_easy_init(); 83 84 curl_easy_setopt(hnd, CURLOPT_INFILESIZE_LARGE, (curl_off_t)-1); 85 curl_easy_setopt(hnd, CURLOPT_URL, url); 86 curl_easy_setopt(hnd, CURLOPT_NOPROGRESS, 1); 87 curl_easy_setopt(hnd, CURLOPT_FAILONERROR, 0); 88 curl_easy_setopt(hnd, CURLOPT_USERAGENT, ""); 89 curl_easy_setopt(hnd, CURLOPT_RESUME_FROM_LARGE, (curl_off_t)0); 90 curl_easy_setopt(hnd, CURLOPT_MAXREDIRS, 50); 91 curl_easy_setopt(hnd, CURLOPT_SSLVERSION, 0); 92 curl_easy_setopt(hnd, CURLOPT_TIMECONDITION, 0); 93 curl_easy_setopt(hnd, CURLOPT_TIMEVALUE, 0); 94 curl_easy_setopt(hnd, CURLOPT_CUSTOMREQUEST, NULL); 95 curl_easy_setopt(hnd, CURLOPT_CONNECTTIMEOUT, 0); 96 curl_easy_setopt(hnd, CURLOPT_HTTPAUTH, 1); 97 curl_easy_setopt(hnd, CURLOPT_ENCODING, NULL); 98 curl_easy_setopt(hnd, CURLOPT_IPRESOLVE, 0); 99 curl_easy_setopt(hnd, CURLOPT_IGNORE_CONTENT_LENGTH, 0); 100 curl_easy_setopt(hnd, CURLOPT_POSTREDIR, 0); 101 curl_easy_setopt(hnd, CURLOPT_WRITEFUNCTION, function); 102 curl_easy_setopt(hnd, CURLOPT_PRIVATE, function); 103 curl_easy_setopt(hnd, CURLOPT_WRITEDATA, userdata); 104 105 pthread_mutex_lock(&__worker_mutex); 106 if (__curl_hnd == NULL) 107 __fetcher_worker_start(); 108 curl_multi_add_handle(__curl_hnd, hnd); 109 pthread_mutex_unlock(&__worker_mutex); 110 111 } 112 113 size_t show(char *txt, size_t size, size_t nmemb, char *userdata) 114 { 115 int i; 116 117 if (txt != NULL) 118 { 119 printf("\n--------------> userdata: %s\n", userdata); 120 for (i = 0; i < nmemb*size; i++) 121 printf("%c", txt[i]); 122 } 123 else 124 printf("\n--------------------------------------------------------\n"); 125 126 fflush(stdout); 127 128 return nmemb*size; 129 130 } 131 132 int main() 133 { 134 fetcher_add_url("http://www.google.de", show, "google"); 135 fetcher_add_url("http://www.heise.de", show, "heise"); 136 sleep(3); 137 fetcher_add_url("http://www.google.de/news", show, "google-news"); 138 139 sleep(7); 140 return 0; 141 }

