Curl had some structures moved to the header. Also had an extra mutex added for locking multihandle. Includes MISC #include order cleanup.

This commit is contained in:
Shyotl
2011-09-22 23:59:44 -05:00
parent 381ef6fe70
commit c621cb7719
8 changed files with 173 additions and 137 deletions

View File

@@ -52,8 +52,8 @@
#endif
#include "llbufferstream.h"
#include "llstl.h"
#include "llsdserialize.h"
#include "llstl.h"
#include "llthread.h"
#include "llsocks5.h"
#include "lltimer.h"
@@ -81,6 +81,7 @@ static const S32 MULTI_PERFORM_CALL_REPEAT = 5;
static const S32 CURL_REQUEST_TIMEOUT = 30; // seconds
static const S32 MAX_ACTIVE_REQUEST_COUNT = 100;
static
// DEBUG //
S32 gCurlEasyCount = 0;
S32 gCurlMultiCount = 0;
@@ -223,77 +224,10 @@ namespace boost
//////////////////////////////////////////////////////////////////////////////
class LLCurl::Easy
{
LOG_CLASS(Easy);
private:
Easy();
public:
static Easy* getEasy();
~Easy();
CURL* getCurlHandle() const { return mCurlEasyHandle; }
void setErrorBuffer();
void setCA();
void setopt(CURLoption option, S32 value);
// These assume the setter does not free value!
void setopt(CURLoption option, void* value);
void setopt(CURLoption option, char* value);
// Copies the string so that it is gauranteed to stick around
void setoptString(CURLoption option, const std::string& value);
void slist_append(const char* str);
void setHeaders();
U32 report(CURLcode);
void getTransferInfo(LLCurl::TransferInfo* info);
void prepRequest(const std::string& url, const std::vector<std::string>& headers, ResponderPtr, S32 time_out = 0, bool post = false);
const char* getErrorBuffer();
std::stringstream& getInput() { return mInput; }
std::stringstream& getHeaderOutput() { return mHeaderOutput; }
LLIOPipe::buffer_ptr_t& getOutput() { return mOutput; }
const LLChannelDescriptors& getChannels() { return mChannels; }
void resetState();
static CURL* allocEasyHandle();
static void releaseEasyHandle(CURL* handle);
private:
friend class LLCurl;
CURL* mCurlEasyHandle;
struct curl_slist* mHeaders;
std::stringstream mRequest;
LLChannelDescriptors mChannels;
LLIOPipe::buffer_ptr_t mOutput;
std::stringstream mInput;
std::stringstream mHeaderOutput;
char mErrorBuffer[CURL_ERROR_SIZE];
// Note: char*'s not strings since we pass pointers to curl
std::vector<char*> mStrings;
ResponderPtr mResponder;
static std::set<CURL*> sFreeHandles;
static std::set<CURL*> sActiveHandles;
static LLMutex* sHandleMutex;
};
std::set<CURL*> LLCurl::Easy::sFreeHandles;
std::set<CURL*> LLCurl::Easy::sActiveHandles;
LLMutex* LLCurl::Easy::sHandleMutex = NULL;
LLMutex* LLCurl::Easy::sMultiMutex = NULL;
//static
CURL* LLCurl::Easy::allocEasyHandle()
@@ -558,7 +492,7 @@ void LLCurl::Easy::prepRequest(const std::string& url,
if (post) setoptString(CURLOPT_ENCODING, "");
// setopt(CURLOPT_VERBOSE, 1); // usefull for debugging
//setopt(CURLOPT_VERBOSE, 1); // useful for debugging
setopt(CURLOPT_NOSIGNAL, 1);
if (LLSocks::getInstance()->isHttpProxyEnabled())
@@ -623,56 +557,6 @@ void LLCurl::Easy::prepRequest(const std::string& url,
////////////////////////////////////////////////////////////////////////////
class LLCurl::Multi : public LLThread
{
LOG_CLASS(Multi);
public:
typedef enum
{
PERFORM_STATE_READY=0,
PERFORM_STATE_PERFORMING=1,
PERFORM_STATE_COMPLETED=2
} ePerformState;
Multi();
~Multi();
Easy* allocEasy();
bool addEasy(Easy* easy);
void removeEasy(Easy* easy);
S32 process();
void perform();
void doPerform();
virtual void run();
CURLMsg* info_read(S32* msgs_in_queue);
S32 mQueued;
S32 mErrorCount;
S32 mPerformState;
LLCondition* mSignal;
bool mQuitting;
bool mThreaded;
private:
void easyFree(Easy*);
CURLM* mCurlMultiHandle;
typedef std::set<Easy*> easy_active_list_t;
easy_active_list_t mEasyActiveList;
typedef std::map<CURL*, Easy*> easy_active_map_t;
easy_active_map_t mEasyActiveMap;
typedef std::set<Easy*> easy_free_list_t;
easy_free_list_t mEasyFreeList;
};
LLCurl::Multi::Multi()
: LLThread("Curl Multi"),
mQueued(0),
@@ -706,6 +590,11 @@ LLCurl::Multi::~Multi()
{
llassert(isStopped());
if (LLCurl::sMultiThreaded)
{
LLCurl::Easy::sMultiMutex->lock();
}
delete mSignal;
mSignal = NULL;
@@ -726,6 +615,11 @@ LLCurl::Multi::~Multi()
check_curl_multi_code(curl_multi_cleanup(mCurlMultiHandle));
--gCurlMultiCount;
if (LLCurl::sMultiThreaded)
{
LLCurl::Easy::sMultiMutex->unlock();
}
}
CURLMsg* LLCurl::Multi::info_read(S32* msgs_in_queue)
@@ -762,6 +656,7 @@ void LLCurl::Multi::run()
mPerformState = PERFORM_STATE_PERFORMING;
if (!mQuitting)
{
LLMutexLock lock(LLCurl::Easy::sMultiMutex);
doPerform();
}
}
@@ -1356,6 +1251,7 @@ void LLCurl::initClass(bool multi_threaded)
check_curl_code(code);
Easy::sHandleMutex = new LLMutex;
Easy::sMultiMutex = new LLMutex;
#if SAFE_SSL
S32 mutex_count = CRYPTO_num_locks();
@@ -1377,6 +1273,8 @@ void LLCurl::cleanupClass()
delete Easy::sHandleMutex;
Easy::sHandleMutex = NULL;
delete Easy::sMultiMutex;
Easy::sMultiMutex = NULL;
for (std::set<CURL*>::iterator iter = Easy::sFreeHandles.begin(); iter != Easy::sFreeHandles.end(); ++iter)
{
@@ -1390,3 +1288,13 @@ void LLCurl::cleanupClass()
}
const unsigned int LLCurl::MAX_REDIRECTS = 5;
// Provide access to LLCurl free functions outside of llcurl.cpp without polluting the global namespace.
void LLCurlFF::check_easy_code(CURLcode code)
{
check_curl_code(code);
}
void LLCurlFF::check_multi_code(CURLMcode code)
{
check_curl_multi_code(code);
}