00001
00034 #ifndef LL_LLCURL_H
00035 #define LL_LLCURL_H
00036
00037 #include "linden_common.h"
00038
00039 #include <sstream>
00040 #include <string>
00041 #include <vector>
00042
00043 #include <boost/intrusive_ptr.hpp>
00044 #include <curl/curl.h>
00045
00046
00047
00048 class LLCurl
00049 {
00050 public:
00051 class Multi;
00052
00053 class Responder
00054 {
00055 public:
00056 Responder();
00057 virtual ~Responder();
00058
00059 virtual void error(U32 status, const std::stringstream& content);
00060
00061 virtual void result(const std::stringstream& content);
00062
00063 virtual void completed(U32 status, const std::stringstream& content);
00070 public:
00071 U32 mReferenceCount;
00072 };
00073 typedef boost::intrusive_ptr<Responder> ResponderPtr;
00074
00075 class Easy
00076 {
00077 public:
00078 Easy();
00079 ~Easy();
00080
00081 void get(const std::string& url, ResponderPtr);
00082 void getByteRange(const std::string& url, S32 offset, S32 length, ResponderPtr);
00083
00084 void perform();
00085
00086 private:
00087 void prep(const std::string& url, ResponderPtr);
00088 void report(CURLcode);
00089
00090 CURL* mHandle;
00091 struct curl_slist* mHeaders;
00092
00093 std::string mURL;
00094 std::string mRange;
00095 std::stringstream mRequest;
00096
00097 std::stringstream mOutput;
00098 char mErrorBuffer[CURL_ERROR_SIZE];
00099
00100 std::stringstream mHeaderOutput;
00101
00102 ResponderPtr mResponder;
00103
00104 friend class Multi;
00105 };
00106
00107
00108 class Multi
00109 {
00110 public:
00111 Multi();
00112 ~Multi();
00113
00114 void get(const std::string& url, ResponderPtr);
00115 void getByteRange(const std::string& url, S32 offset, S32 length, ResponderPtr);
00116
00117 void process();
00118
00119 private:
00120 Easy* easyAlloc();
00121 void easyFree(Easy*);
00122
00123 CURLM* mHandle;
00124
00125 typedef std::vector<Easy*> EasyList;
00126 EasyList mFreeEasy;
00127 };
00128
00129
00130 static void get(const std::string& url, ResponderPtr);
00131 static void getByteRange(const std::string& url, S32 offset, S32 length, ResponderPtr responder);
00132
00133 static void process();
00134 static void cleanup();
00135 };
00136
00137 namespace boost
00138 {
00139 void intrusive_ptr_add_ref(LLCurl::Responder* p);
00140 void intrusive_ptr_release(LLCurl::Responder* p);
00141 };
00142
00143 #endif // LL_LLCURL_H