void CurlStreamFile::fillCache(std::streampos size){ #if 1 assert(size >= 0); if(! _running || _cached >=size){ return ; } fd_set readfd, writefd, exceptfd; int maxfd; CURLMcode mcode; timeval tv; //hard-coded slect timeout //this number is kept low to give more thread switch //opportunities while waitting for a load const long maxSleepUsec = 10000; //1/100 of a second const unsigned int userTimeout = 60000; WallClockTimer lastProgress; while(_running){ fillCacheNonBlocking(); if(_cached>=size || !_running) break; FD_ZERO(&readfd); FD_ZERO(&writefd); FD_ZERO(&exceptfd); mcode = curl_multi_fdset(_mCurlHandle, &readfd, &writefd, &exceptfd, &maxfd); if(mcode != CURLM_OK){ throw SnailException(curl_multi_strerror(mcode)); } if(maxfd<0){ //as of libcurl 7.21.x, the DNS resolving appears to be //going on in the background, so curl_multi_fdset fails to //return anything useful, So we use the user timeout value //to give DNS enough time to resolve the lookup if(userTimeout && lastProgress.elapsed()>userTimeout){ return ; }else{ continue; } }//if(maxfd<0) tv.tv_sec = 0; tv.tv_usec = maxSleepUsec; //wait for data on the filedescriptors until a timeout set in rc file int ret = select(maxfd+1, &readfd, &writefd, &exceptfd, &tv); #if !defined(WIN32) if(ret == -1){ if(errno == EINTR){ cout<<"select() was interrupted by a singal"<<endl; ret = 0; }else{ std::ostringstream os; os<<"error polling data from connection to"<<_url<<":"<<strerror(errno); throw SnailException(os.str()); } } #endif if(!ret){ //timeout check the clock to see //if we expired the user timeout if(userTimeout && lastProgress.elapsed() > userTimeout){ cout<<"timeout ("<<userTimeout<<") while loading from URL"<<_url<<endl; return ; } }else{ lastProgress.restart(); } }//while(.... processMessages(); #endif }