int main(int argc, char *argv[]) { curl_global_init(CURL_GLOBAL_ALL); curlm = curl_multi_init(); multi_setopt(curlm, CURLMOPT_TIMERFUNCTION, timer_func); memset(slices, 0, sizeof(slices)); show_progress = isatty(fileno(stdout)); parse_args(argc, argv); init_slices(0, 0); perform(); if (load_percent && file_size) { init_slices(bytes_written, file_size); perform(); } if (file) fclose(file); print_progress(); if (show_progress) putchar('\n'); curl_multi_cleanup(curlm); curl_global_cleanup(); return 0; }
int test(char *URL) { int res = 0; CURLM *m = NULL; CURLMsg *msg; /* for picking up messages with the transfer status */ int msgs_left; /* how many messages are left */ int running; int handlenum = 0; struct timeval last_handle_add; if(parse_url_file("log/urls.txt") <= 0) goto test_cleanup; start_test_timing(); curl_global_init(CURL_GLOBAL_ALL); multi_init(m); create_handles(); multi_setopt(m, CURLMOPT_PIPELINING, 1L); multi_setopt(m, CURLMOPT_MAX_HOST_CONNECTIONS, 2L); multi_setopt(m, CURLMOPT_MAX_PIPELINE_LENGTH, 3L); multi_setopt(m, CURLMOPT_CONTENT_LENGTH_PENALTY_SIZE, 15000L); multi_setopt(m, CURLMOPT_CHUNK_LENGTH_PENALTY_SIZE, 10000L); multi_setopt(m, CURLMOPT_PIPELINING_SITE_BL, site_blacklist); multi_setopt(m, CURLMOPT_PIPELINING_SERVER_BL, server_blacklist); last_handle_add = tutil_tvnow(); for(;;) { struct timeval interval; struct timeval now; long int msnow, mslast; fd_set rd, wr, exc; int maxfd = -99; long timeout; interval.tv_sec = 1; interval.tv_usec = 0; if(handlenum < num_handles) { now = tutil_tvnow(); msnow = now.tv_sec * 1000 + now.tv_usec / 1000; mslast = last_handle_add.tv_sec * 1000 + last_handle_add.tv_usec / 1000; if(msnow - mslast >= urltime[handlenum] && handlenum < num_handles) { fprintf(stdout, "Adding handle %d\n", handlenum); setup_handle(URL, m, handlenum); last_handle_add = now; handlenum++; } } curl_multi_perform(m, &running); abort_on_test_timeout(); /* See how the transfers went */ while ((msg = curl_multi_info_read(m, &msgs_left))) { if (msg->msg == CURLMSG_DONE) { int i, found = 0; /* Find out which handle this message is about */ for (i = 0; i < num_handles; i++) { found = (msg->easy_handle == handles[i]); if(found) break; } printf("Handle %d Completed with status %d\n", i, msg->data.result); curl_multi_remove_handle(m, handles[i]); } } if(handlenum == num_handles && !running) { break; /* done */ } FD_ZERO(&rd); FD_ZERO(&wr); FD_ZERO(&exc); curl_multi_fdset(m, &rd, &wr, &exc, &maxfd); /* At this point, maxfd is guaranteed to be greater or equal than -1. */ curl_multi_timeout(m, &timeout); if(timeout < 0) timeout = 1; interval.tv_sec = timeout / 1000; interval.tv_usec = (timeout % 1000) * 1000; interval.tv_sec = 0; interval.tv_usec = 1000; select_test(maxfd+1, &rd, &wr, &exc, &interval); abort_on_test_timeout(); } test_cleanup: remove_handles(); /* undocumented cleanup sequence - type UB */ curl_multi_cleanup(m); curl_global_cleanup(); free_urls(); return res; }
int test(char *url) { CURLM *multi = NULL; int running; int i, j; int num_handles = 0; enum HandleState state = ReadyForNewHandle; size_t urllen = strlen(url) + 4 + 1; char* full_url = malloc(urllen); start_test_timing(); if(!full_url) { fprintf(stderr, "Not enough memory for full url\n"); return TEST_ERR_MAJOR_BAD; } for(i = 0; i < MAX_EASY_HANDLES; ++i) { easy[i] = NULL; sockets[i] = CURL_SOCKET_BAD; } res_global_init(CURL_GLOBAL_ALL); if(res) { free(full_url); return res; } multi_init(multi); #ifdef USE_PIPELINING multi_setopt(multi, CURLMOPT_PIPELINING, 1L); multi_setopt(multi, CURLMOPT_MAX_HOST_CONNECTIONS, 5L); multi_setopt(multi, CURLMOPT_MAX_TOTAL_CONNECTIONS, 10L); #endif for(;;) { struct timeval interval; fd_set fdread; fd_set fdwrite; fd_set fdexcep; long timeout = -99; int maxfd = -99; bool found_new_socket = FALSE; /* Start a new handle if we aren't at the max */ if(state == ReadyForNewHandle) { easy_init(easy[num_handles]); if(num_handles % 3 == 2) { snprintf(full_url, urllen, "%s0200", url); easy_setopt(easy[num_handles], CURLOPT_HTTPAUTH, CURLAUTH_NTLM); } else { snprintf(full_url, urllen, "%s0100", url); easy_setopt(easy[num_handles], CURLOPT_HTTPAUTH, CURLAUTH_BASIC); } easy_setopt(easy[num_handles], CURLOPT_FRESH_CONNECT, 1L); easy_setopt(easy[num_handles], CURLOPT_URL, full_url); easy_setopt(easy[num_handles], CURLOPT_VERBOSE, 1L); easy_setopt(easy[num_handles], CURLOPT_HTTPGET, 1L); easy_setopt(easy[num_handles], CURLOPT_USERPWD, "testuser:testpass"); easy_setopt(easy[num_handles], CURLOPT_WRITEFUNCTION, callback); easy_setopt(easy[num_handles], CURLOPT_WRITEDATA, easy + num_handles); easy_setopt(easy[num_handles], CURLOPT_HEADER, 1L); multi_add_handle(multi, easy[num_handles]); num_handles += 1; state = NeedSocketForNewHandle; } multi_perform(multi, &running); abort_on_test_timeout(); if(!running && state == NoMoreHandles) break; /* done */ FD_ZERO(&fdread); FD_ZERO(&fdwrite); FD_ZERO(&fdexcep); multi_fdset(multi, &fdread, &fdwrite, &fdexcep, &maxfd); /* At this point, maxfd is guaranteed to be greater or equal than -1. */ /* Any socket which is new in fdread is associated with the new handle */ for(i = 0; i <= maxfd; ++i) { bool socket_exists = FALSE; curl_socket_t curfd = (curl_socket_t)i; if(!FD_ISSET(curfd, &fdread)) { continue; } /* Check if this socket was already detected for an earlier handle (or for this handle, num_handles-1, in the callback */ for(j = 0; j < num_handles; ++j) { if(sockets[j] == curfd) { socket_exists = TRUE; break; } } if(socket_exists) { continue; } if(found_new_socket || state != NeedSocketForNewHandle) { fprintf(stderr, "Unexpected new socket\n"); res = TEST_ERR_MAJOR_BAD; goto test_cleanup; } /* Now we know the socket is for the most recent handle, num_handles-1 */ if(sockets[num_handles-1] != CURL_SOCKET_BAD) { /* A socket for this handle was already detected in the callback; if it matched socket_exists should be true and we would never get here */ assert(curfd != sockets[num_handles-1]); fprintf(stderr, "Handle %d wrote to socket %d then detected on %d\n", num_handles-1, (int)sockets[num_handles-1], (int)curfd); res = TEST_ERR_MAJOR_BAD; goto test_cleanup; } else { sockets[num_handles-1] = curfd; found_new_socket = TRUE; /* continue to make sure there's only one new handle */ } } if(state == NeedSocketForNewHandle) { if(maxfd != -1 && !found_new_socket) { fprintf(stderr, "Warning: socket did not open immediately for new " "handle (trying again)\n"); continue; } state = num_handles < MAX_EASY_HANDLES ? ReadyForNewHandle : NoMoreHandles; } multi_timeout(multi, &timeout); /* At this point, timeout is guaranteed to be greater or equal than -1. */ fprintf(stderr, "%s:%d num_handles %d timeout %ld\n", __FILE__, __LINE__, num_handles, timeout); if(timeout != -1L) { int itimeout = (timeout > (long)INT_MAX) ? INT_MAX : (int)timeout; interval.tv_sec = itimeout/1000; interval.tv_usec = (itimeout%1000)*1000; } else { interval.tv_sec = TEST_HANG_TIMEOUT/1000+1; interval.tv_usec = 0; /* if there's no timeout and we get here on the last handle, we may already have read the last part of the stream so waiting makes no sense */ if(!running && num_handles == MAX_EASY_HANDLES) { break; } } select_test(maxfd+1, &fdread, &fdwrite, &fdexcep, &interval); abort_on_test_timeout(); } test_cleanup: /* proper cleanup sequence - type PB */ for(i = 0; i < MAX_EASY_HANDLES; i++) { curl_multi_remove_handle(multi, easy[i]); curl_easy_cleanup(easy[i]); } curl_multi_cleanup(multi); curl_global_cleanup(); free(full_url); return res; }
int test(char *URL) { int res = 0; CURL *curl = NULL; FILE *hd_src = NULL; int hd ; int error; struct_stat file_info; CURLM *m = NULL; struct ReadWriteSockets sockets = {{NULL, 0, 0}, {NULL, 0, 0}}; struct timeval timeout = {-1, 0}; int success = 0; start_test_timing(); if (!libtest_arg3) { fprintf(stderr, "Usage: lib582 [url] [filename] [username]\n"); return TEST_ERR_USAGE; } hd_src = fopen(libtest_arg2, "rb"); if(NULL == hd_src) { error = ERRNO; fprintf(stderr, "fopen() failed with error: %d (%s)\n", error, strerror(error)); fprintf(stderr, "Error opening file: (%s)\n", libtest_arg2); return TEST_ERR_FOPEN; } /* get the file size of the local file */ hd = fstat(fileno(hd_src), &file_info); if(hd == -1) { /* can't open file, bail out */ error = ERRNO; fprintf(stderr, "fstat() failed with error: %d (%s)\n", error, strerror(error)); fprintf(stderr, "ERROR: cannot open file (%s)\n", libtest_arg2); fclose(hd_src); return TEST_ERR_FSTAT; } fprintf(stderr, "Set to upload %d bytes\n", (int)file_info.st_size); res_global_init(CURL_GLOBAL_ALL); if(res) { fclose(hd_src); return res; } easy_init(curl); /* enable uploading */ easy_setopt(curl, CURLOPT_UPLOAD, 1L); /* specify target */ easy_setopt(curl,CURLOPT_URL, URL); /* go verbose */ easy_setopt(curl, CURLOPT_VERBOSE, 1L); /* now specify which file to upload */ easy_setopt(curl, CURLOPT_READDATA, hd_src); easy_setopt(curl, CURLOPT_USERPWD, libtest_arg3); easy_setopt(curl, CURLOPT_SSH_PUBLIC_KEYFILE, "curl_client_key.pub"); easy_setopt(curl, CURLOPT_SSH_PRIVATE_KEYFILE, "curl_client_key"); easy_setopt(curl, CURLOPT_INFILESIZE_LARGE, (curl_off_t)file_info.st_size); multi_init(m); multi_setopt(m, CURLMOPT_SOCKETFUNCTION, curlSocketCallback); multi_setopt(m, CURLMOPT_SOCKETDATA, &sockets); multi_setopt(m, CURLMOPT_TIMERFUNCTION, curlTimerCallback); multi_setopt(m, CURLMOPT_TIMERDATA, &timeout); multi_add_handle(m, curl); while (!checkForCompletion(m, &success)) { fd_set readSet, writeSet; curl_socket_t maxFd = 0; struct timeval tv = {10, 0}; FD_ZERO(&readSet); FD_ZERO(&writeSet); updateFdSet(&sockets.read, &readSet, &maxFd); updateFdSet(&sockets.write, &writeSet, &maxFd); if (timeout.tv_sec != -1) { int usTimeout = getMicroSecondTimeout(&timeout); tv.tv_sec = usTimeout / 1000000; tv.tv_usec = usTimeout % 1000000; } else if (maxFd <= 0) { tv.tv_sec = 0; tv.tv_usec = 100000; } select_test(maxFd, &readSet, &writeSet, NULL, &tv); /* Check the sockets for reading / writing */ checkFdSet(m, &sockets.read, &readSet, CURL_CSELECT_IN, "read"); checkFdSet(m, &sockets.write, &writeSet, CURL_CSELECT_OUT, "write"); if (timeout.tv_sec != -1 && getMicroSecondTimeout(&timeout) == 0) { /* Curl's timer has elapsed. */ notifyCurl(m, CURL_SOCKET_TIMEOUT, 0, "timeout"); } abort_on_test_timeout(); } if (!success) { fprintf(stderr, "Error uploading file.\n"); res = TEST_ERR_MAJOR_BAD; } test_cleanup: /* proper cleanup sequence - type PB */ curl_multi_remove_handle(m, curl); curl_easy_cleanup(curl); curl_multi_cleanup(m); curl_global_cleanup(); /* close the local file */ fclose(hd_src); /* free local memory */ free(sockets.read.sockets); free(sockets.write.sockets); return res; }
int test(char *URL) { int res = 0; CURL *curl[NUM_HANDLES]; int running; CURLM *m = NULL; int i; char target_url[256]; char dnsentry[256]; struct curl_slist *slist = NULL; char *port = libtest_arg3; char *address = libtest_arg2; (void)URL; /* Create fake DNS entries for serverX.example.com for all handles */ for(i=0; i < NUM_HANDLES; i++) { sprintf(dnsentry, "server%d.example.com:%s:%s", i + 1, port, address); printf("%s\n", dnsentry); slist = curl_slist_append(slist, dnsentry); } for(i=0; i < NUM_HANDLES; i++) curl[i] = NULL; start_test_timing(); global_init(CURL_GLOBAL_ALL); multi_init(m); multi_setopt(m, CURLMOPT_MAXCONNECTS, 3); /* get NUM_HANDLES easy handles */ for(i=0; i < NUM_HANDLES; i++) { /* get an easy handle */ easy_init(curl[i]); /* specify target */ sprintf(target_url, "http://server%d.example.com:%s/path/1506%04i", i + 1, port, i + 1); target_url[sizeof(target_url) - 1] = '\0'; easy_setopt(curl[i], CURLOPT_URL, target_url); /* go verbose */ easy_setopt(curl[i], CURLOPT_VERBOSE, 1L); /* include headers */ easy_setopt(curl[i], CURLOPT_HEADER, 1L); easy_setopt(curl[i], CURLOPT_RESOLVE, slist); } fprintf(stderr, "Start at URL 0\n"); for(i=0; i < NUM_HANDLES; i++) { /* add handle to multi */ multi_add_handle(m, curl[i]); for(;;) { struct timeval interval; fd_set rd, wr, exc; int maxfd = -99; interval.tv_sec = 1; interval.tv_usec = 0; multi_perform(m, &running); abort_on_test_timeout(); if(!running) break; /* done */ FD_ZERO(&rd); FD_ZERO(&wr); FD_ZERO(&exc); multi_fdset(m, &rd, &wr, &exc, &maxfd); /* At this point, maxfd is guaranteed to be greater or equal than -1. */ select_test(maxfd+1, &rd, &wr, &exc, &interval); abort_on_test_timeout(); } } test_cleanup: /* proper cleanup sequence - type PB */ for(i=0; i < NUM_HANDLES; i++) { curl_multi_remove_handle(m, curl[i]); curl_easy_cleanup(curl[i]); } curl_slist_free_all(slist); curl_multi_cleanup(m); curl_global_cleanup(); return res; }