diff options
Diffstat (limited to 'indra')
| -rw-r--r-- | indra/llcommon/CMakeLists.txt | 1 | ||||
| -rw-r--r-- | indra/llcommon/llsingleton.h | 24 | ||||
| -rw-r--r-- | indra/llcommon/tests/llsingleton_test.cpp | 75 | ||||
| -rw-r--r-- | indra/llmessage/llcurl.cpp | 12 | ||||
| -rw-r--r-- | indra/llmessage/llcurl.h | 8 | ||||
| -rw-r--r-- | indra/llmessage/llpacketring.cpp | 16 | ||||
| -rw-r--r-- | indra/llmessage/llpacketring.h | 3 | ||||
| -rw-r--r-- | indra/llmessage/llproxy.cpp | 102 | ||||
| -rw-r--r-- | indra/llmessage/llproxy.h | 107 | 
9 files changed, 232 insertions, 116 deletions
| diff --git a/indra/llcommon/CMakeLists.txt b/indra/llcommon/CMakeLists.txt index cc6bddc4da..60d4cfe6d3 100644 --- a/indra/llcommon/CMakeLists.txt +++ b/indra/llcommon/CMakeLists.txt @@ -322,6 +322,7 @@ if (LL_TESTS)    LL_ADD_INTEGRATION_TEST(llrand "" "${test_libs}")    LL_ADD_INTEGRATION_TEST(llsdserialize "" "${test_libs}"                            "${PYTHON_EXECUTABLE}" "${CMAKE_CURRENT_SOURCE_DIR}/tests/setpython.py") +  LL_ADD_INTEGRATION_TEST(llsingleton "" "${test_libs}")                              LL_ADD_INTEGRATION_TEST(llstring "" "${test_libs}")    LL_ADD_INTEGRATION_TEST(lltreeiterators "" "${test_libs}")    LL_ADD_INTEGRATION_TEST(lluri "" "${test_libs}") diff --git a/indra/llcommon/llsingleton.h b/indra/llcommon/llsingleton.h index 00757be277..49d99f2cd0 100644 --- a/indra/llcommon/llsingleton.h +++ b/indra/llcommon/llsingleton.h @@ -114,8 +114,7 @@ private:  		~SingletonInstanceData()  		{ -			SingletonInstanceData& data = getData(); -			if (data.mInitState != DELETED) +			if (mInitState != DELETED)  			{  				deleteSingleton();  			} @@ -130,7 +129,26 @@ public:  		data.mInitState = DELETED;  	} -	// Can be used to control when the singleton is deleted.  Not normally needed. +	/** +	 * @brief Immediately delete the singleton. +	 * +	 * A subsequent call to LLProxy::getInstance() will construct a new +	 * instance of the class. +	 * +	 * LLSingletons are normally destroyed after main() has exited and the C++ +	 * runtime is cleaning up statically-constructed objects. Some classes +	 * derived from LLSingleton have objects that are part of a runtime system +	 * that is terminated before main() exits. Calling the destructor of those +	 * objects after the termination of their respective systems can cause +	 * crashes and other problems during termination of the project. Using this +	 * method to destroy the singleton early can prevent these crashes. +	 * +	 * An example where this is needed is for a LLSingleton that has an APR +	 * object as a member that makes APR calls on destruction. The APR system is +	 * shut down explicitly before main() exits. This causes a crash on exit. +	 * Using this method before the call to apr_terminate() and NOT calling +	 * getInstance() again will prevent the crash. +	 */  	static void deleteSingleton()  	{  		delete getData().mSingletonInstance; diff --git a/indra/llcommon/tests/llsingleton_test.cpp b/indra/llcommon/tests/llsingleton_test.cpp new file mode 100644 index 0000000000..2e8b83fa2c --- /dev/null +++ b/indra/llcommon/tests/llsingleton_test.cpp @@ -0,0 +1,75 @@ +/**  + * @file llprocessor_test.cpp + * @date 2010-06-01 + * + * $LicenseInfo:firstyear=2010&license=viewerlgpl$ + * Second Life Viewer Source Code + * Copyright (C) 2010, Linden Research, Inc. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; + * version 2.1 of the License only. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA + * + * Linden Research, Inc., 945 Battery Street, San Francisco, CA  94111  USA + * $/LicenseInfo$ + */ + +#include "linden_common.h" + +#include "llsingleton.h" +#include "../test/lltut.h" + +namespace tut +{ +	struct singleton +	{ +		// We need a class created with the LLSingleton template to test with. +		class LLSingletonTest: public LLSingleton<LLSingletonTest> +		{ + +		}; +	}; + +	typedef test_group<singleton> singleton_t; +	typedef singleton_t::object singleton_object_t; +	tut::singleton_t tut_singleton("LLSingleton"); + +	template<> template<> +	void singleton_object_t::test<1>() +	{ + +	} +	template<> template<> +	void singleton_object_t::test<2>() +	{ +		LLSingletonTest* singleton_test = LLSingletonTest::getInstance(); +		ensure(singleton_test); +	} +	template<> template<> +	void singleton_object_t::test<3>() +	{ +		//Construct the instance +		LLSingletonTest::getInstance(); +		ensure(LLSingletonTest::instanceExists()); + +		//Delete the instance +		LLSingletonTest::deleteSingleton(); +		ensure(LLSingletonTest::destroyed()); +		ensure(!LLSingletonTest::instanceExists()); + +		//Construct it again. +		LLSingletonTest* singleton_test = LLSingletonTest::getInstance(); +		ensure(singleton_test); +		ensure(LLSingletonTest::instanceExists()); +	} +} diff --git a/indra/llmessage/llcurl.cpp b/indra/llmessage/llcurl.cpp index a3de178d78..14e169c6b1 100644 --- a/indra/llmessage/llcurl.cpp +++ b/indra/llmessage/llcurl.cpp @@ -499,7 +499,7 @@ void LLCurl::Easy::prepRequest(const std::string& url,  	//don't verify host name so urls with scrubbed host names will work (improves DNS performance)  	setopt(CURLOPT_SSL_VERIFYHOST, 0); -	setopt(CURLOPT_TIMEOUT, CURL_REQUEST_TIMEOUT); +	setopt(CURLOPT_TIMEOUT, llmax(time_out, CURL_REQUEST_TIMEOUT));  	setoptString(CURLOPT_URL, url); @@ -1213,3 +1213,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); +} diff --git a/indra/llmessage/llcurl.h b/indra/llmessage/llcurl.h index 5ab4dc35b9..213b281e72 100644 --- a/indra/llmessage/llcurl.h +++ b/indra/llmessage/llcurl.h @@ -371,7 +371,11 @@ private:  	bool mResultReturned;  }; -void check_curl_code(CURLcode code); -void check_curl_multi_code(CURLMcode code); +// Provide access to LLCurl free functions outside of llcurl.cpp without polluting the global namespace. +namespace LLCurlFF +{ +	void check_easy_code(CURLcode code); +	void check_multi_code(CURLMcode code); +}  #endif // LL_LLCURL_H diff --git a/indra/llmessage/llpacketring.cpp b/indra/llmessage/llpacketring.cpp index 7628984de4..fc6e9c5193 100644 --- a/indra/llmessage/llpacketring.cpp +++ b/indra/llmessage/llpacketring.cpp @@ -228,13 +228,13 @@ S32 LLPacketRing::receivePacket (S32 socket, char *datap)  		if (LLProxy::isSOCKSProxyEnabled())  		{  			U8 buffer[NET_BUFFER_SIZE + SOCKS_HEADER_SIZE]; -			packet_size = receive_packet(socket, reinterpret_cast<char *>(buffer)); +			packet_size = receive_packet(socket, static_cast<char*>(static_cast<void*>(buffer)));  			if (packet_size > SOCKS_HEADER_SIZE)  			{  				// *FIX We are assuming ATYP is 0x01 (IPv4), not 0x03 (hostname) or 0x04 (IPv6)  				memcpy(datap, buffer + SOCKS_HEADER_SIZE, packet_size - SOCKS_HEADER_SIZE); -				proxywrap_t * header = reinterpret_cast<proxywrap_t *>(buffer); +				proxywrap_t * header = static_cast<proxywrap_t*>(static_cast<void*>(buffer));  				mLastSender.setAddress(header->addr);  				mLastSender.setPort(ntohs(header->port)); @@ -353,14 +353,20 @@ BOOL LLPacketRing::sendPacketImpl(int h_socket, const char * send_buffer, S32 bu  		return send_packet(h_socket, send_buffer, buf_size, host.getAddress(), host.getPort());  	} -	proxywrap_t *socks_header = reinterpret_cast<proxywrap_t *>(&mProxyWrappedSendBuffer); +	char headered_send_buffer[NET_BUFFER_SIZE + SOCKS_HEADER_SIZE]; + +	proxywrap_t *socks_header = static_cast<proxywrap_t*>(static_cast<void*>(&headered_send_buffer));  	socks_header->rsv   = 0;  	socks_header->addr  = host.getAddress();  	socks_header->port  = htons(host.getPort());  	socks_header->atype = ADDRESS_IPV4;  	socks_header->frag  = 0; -	memcpy(mProxyWrappedSendBuffer + SOCKS_HEADER_SIZE, send_buffer, buf_size); +	memcpy(headered_send_buffer + SOCKS_HEADER_SIZE, send_buffer, buf_size); -	return send_packet(h_socket, (const char*) mProxyWrappedSendBuffer, buf_size + 10, LLProxy::getInstance()->getUDPProxy().getAddress(), LLProxy::getInstance()->getUDPProxy().getPort()); +	return send_packet(	h_socket, +						headered_send_buffer, +						buf_size + SOCKS_HEADER_SIZE, +						LLProxy::getInstance()->getUDPProxy().getAddress(), +						LLProxy::getInstance()->getUDPProxy().getPort());  } diff --git a/indra/llmessage/llpacketring.h b/indra/llmessage/llpacketring.h index 7edcc834db..b214271e78 100644 --- a/indra/llmessage/llpacketring.h +++ b/indra/llmessage/llpacketring.h @@ -83,9 +83,6 @@ protected:  	LLHost mLastSender;  	LLHost mLastReceivingIF; - -	U8 mProxyWrappedSendBuffer[NET_BUFFER_SIZE + SOCKS_HEADER_SIZE]; -  private:  	BOOL sendPacketImpl(int h_socket, const char * send_buffer, S32 buf_size, LLHost host);  }; diff --git a/indra/llmessage/llproxy.cpp b/indra/llmessage/llproxy.cpp index 19f1fc6545..3ffe6d2d3b 100644 --- a/indra/llmessage/llproxy.cpp +++ b/indra/llmessage/llproxy.cpp @@ -43,7 +43,7 @@  bool LLProxy::sUDPProxyEnabled = false;  // Some helpful TCP static functions. -static S32 tcp_handshake(LLSocket::ptr_t handle, char * dataout, apr_size_t outlen, char * datain, apr_size_t maxinlen); // Do a TCP data handshake +static apr_status_t tcp_blocking_handshake(LLSocket::ptr_t handle, char * dataout, apr_size_t outlen, char * datain, apr_size_t maxinlen); // Do a TCP data handshake  static LLSocket::ptr_t tcp_open_channel(LLHost host); // Open a TCP channel to a given host  static void tcp_close_channel(LLSocket::ptr_t* handle_ptr); // Close an open TCP channel @@ -63,14 +63,13 @@ LLProxy::LLProxy():  LLProxy::~LLProxy()  {  	stopSOCKSProxy(); -	sUDPProxyEnabled  = false; -	mHTTPProxyEnabled = false; +	disableHTTPProxy();  }  /**   * @brief Open the SOCKS 5 TCP control channel.   * - * Perform a SOCKS 5 authentication and UDP association to the proxy server. + * Perform a SOCKS 5 authentication and UDP association with the proxy server.   *   * @param proxy The SOCKS 5 server to connect to.   * @return SOCKS_OK if successful, otherwise a socks error code from llproxy.h. @@ -83,11 +82,15 @@ S32 LLProxy::proxyHandshake(LLHost proxy)  	socks_auth_request_t  socks_auth_request;  	socks_auth_response_t socks_auth_response; -	socks_auth_request.version     = SOCKS_VERSION;       // SOCKS version 5 -	socks_auth_request.num_methods = 1;                   // Sending 1 method. -	socks_auth_request.methods     = getSelectedAuthMethod(); // Send only the selected method. +	socks_auth_request.version		= SOCKS_VERSION;				// SOCKS version 5 +	socks_auth_request.num_methods	= 1;							// Sending 1 method. +	socks_auth_request.methods		= getSelectedAuthMethod();		// Send only the selected method. -	result = tcp_handshake(mProxyControlChannel, (char*)&socks_auth_request, sizeof(socks_auth_request), (char*)&socks_auth_response, sizeof(socks_auth_response)); +	result = tcp_blocking_handshake(mProxyControlChannel, +									static_cast<char*>(static_cast<void*>(&socks_auth_request)), +									sizeof(socks_auth_request), +									static_cast<char*>(static_cast<void*>(&socks_auth_response)), +									sizeof(socks_auth_response));  	if (result != APR_SUCCESS)  	{  		LL_WARNS("Proxy") << "SOCKS authentication request failed, error on TCP control channel : " << result << LL_ENDL; @@ -97,12 +100,12 @@ S32 LLProxy::proxyHandshake(LLHost proxy)  	if (socks_auth_response.method == AUTH_NOT_ACCEPTABLE)  	{ -		LL_WARNS("Proxy") << "SOCKS 5 server refused all our authentication methods" << LL_ENDL; +		LL_WARNS("Proxy") << "SOCKS 5 server refused all our authentication methods." << LL_ENDL;  		stopSOCKSProxy();  		return SOCKS_NOT_ACCEPTABLE;  	} -	// SOCKS 5 USERNAME/PASSWORD authentication +	/* SOCKS 5 USERNAME/PASSWORD authentication */  	if (socks_auth_response.method == METHOD_PASSWORD)  	{  		// The server has requested a username/password combination @@ -114,11 +117,15 @@ S32 LLProxy::proxyHandshake(LLHost proxy)  		password_auth[1] = socks_username.size();  		memcpy(&password_auth[2], socks_username.c_str(), socks_username.size());  		password_auth[socks_username.size() + 2] = socks_password.size(); -		memcpy(&password_auth[socks_username.size()+3], socks_password.c_str(), socks_password.size()); +		memcpy(&password_auth[socks_username.size() + 3], socks_password.c_str(), socks_password.size());  		authmethod_password_reply_t password_reply; -		result = tcp_handshake(mProxyControlChannel, password_auth, request_size, (char*)&password_reply, sizeof(password_reply)); +		result = tcp_blocking_handshake(mProxyControlChannel, +										password_auth, +										request_size, +										static_cast<char*>(static_cast<void*>(&password_reply)), +										sizeof(password_reply));  		delete[] password_auth;  		if (result != APR_SUCCESS) @@ -150,7 +157,11 @@ S32 LLProxy::proxyHandshake(LLHost proxy)  	// "If the client is not in possession of the information at the time of the UDP ASSOCIATE,  	//  the client MUST use a port number and address of all zeros. RFC 1928" -	result = tcp_handshake(mProxyControlChannel, (char*)&connect_request, sizeof(connect_request), (char*)&connect_reply, sizeof(connect_reply)); +	result = tcp_blocking_handshake(mProxyControlChannel, +									static_cast<char*>(static_cast<void*>(&connect_request)), +									sizeof(connect_request), +									static_cast<char*>(static_cast<void*>(&connect_reply)), +									sizeof(connect_reply));  	if (result != APR_SUCCESS)  	{  		LL_WARNS("Proxy") << "SOCKS connect request failed, error on TCP control channel : " << result << LL_ENDL; @@ -169,6 +180,8 @@ S32 LLProxy::proxyHandshake(LLHost proxy)  	mUDPProxy.setAddress(proxy.getAddress());  	// The connection was successful. We now have the UDP port to send requests that need forwarding to.  	LL_INFOS("Proxy") << "SOCKS 5 UDP proxy connected on " << mUDPProxy << LL_ENDL; +	sUDPProxyEnabled = true; +  	return SOCKS_OK;  } @@ -176,7 +189,8 @@ S32 LLProxy::proxyHandshake(LLHost proxy)   * @brief Initiates a SOCKS 5 proxy session.   *   * Performs basic checks on host to verify that it is a valid address. Opens the control channel - * and then negotiates the proxy connection with the server. + * and then negotiates the proxy connection with the server. Closes any existing SOCKS + * connection before proceeding. Also disables an HTTP proxy if it is using SOCKS as the proxy.   *   *   * @param host Socks server to connect to. @@ -184,43 +198,32 @@ S32 LLProxy::proxyHandshake(LLHost proxy)   */  S32 LLProxy::startSOCKSProxy(LLHost host)  { -	S32 status = SOCKS_OK; -  	if (host.isOk())  	{  		mTCPProxy = host;  	}  	else  	{ -		status = SOCKS_INVALID_HOST; +		return SOCKS_INVALID_HOST;  	} -	if (mProxyControlChannel && status == SOCKS_OK) -	{ -		tcp_close_channel(&mProxyControlChannel); -	} +	// Close any running SOCKS connection. +	stopSOCKSProxy(); -	if (status == SOCKS_OK) +	mProxyControlChannel = tcp_open_channel(mTCPProxy); +	if (!mProxyControlChannel)  	{ -		mProxyControlChannel = tcp_open_channel(mTCPProxy); -		if (!mProxyControlChannel) -		{ -			status = SOCKS_HOST_CONNECT_FAILED; -		} +		return SOCKS_HOST_CONNECT_FAILED;  	} -	if (status == SOCKS_OK) -	{ -		status = proxyHandshake(mTCPProxy); -	} -	if (status == SOCKS_OK) -	{ -		sUDPProxyEnabled = true; -	} -	else +	S32 status = proxyHandshake(mTCPProxy); + +	if (status != SOCKS_OK)  	{ +		// Shut down the proxy if any of the above steps failed.  		stopSOCKSProxy();  	} +  	return status;  } @@ -241,7 +244,7 @@ void LLProxy::stopSOCKSProxy()  	if (LLPROXY_SOCKS == getHTTPProxyType())  	{ -		void disableHTTPProxy(); +		disableHTTPProxy();  	}  	if (mProxyControlChannel) @@ -350,16 +353,6 @@ void LLProxy::disableHTTPProxy()  }  /** - * @brief Get the HTTP proxy address and port - */ -// -LLHost LLProxy::getHTTPProxy() const -{ -	LLMutexLock lock(&mProxyMutex); -	return mHTTPProxy; -} - -/**   * @brief Get the currently selected HTTP proxy type   */  LLHttpProxyType LLProxy::getHTTPProxyType() const @@ -440,21 +433,21 @@ void LLProxy::applyProxySettings(CURL* handle)  		// Now test again to verify that the proxy wasn't disabled between the first check and the lock.  		if (mHTTPProxyEnabled)  		{ -			check_curl_code(curl_easy_setopt(handle, CURLOPT_PROXY, mHTTPProxy.getIPString().c_str())); -			check_curl_code(curl_easy_setopt(handle, CURLOPT_PROXYPORT, mHTTPProxy.getPort())); +			LLCurlFF::check_easy_code(curl_easy_setopt(handle, CURLOPT_PROXY, mHTTPProxy.getIPString().c_str())); +			LLCurlFF::check_easy_code(curl_easy_setopt(handle, CURLOPT_PROXYPORT, mHTTPProxy.getPort()));  			if (mProxyType == LLPROXY_SOCKS)  			{ -				check_curl_code(curl_easy_setopt(handle, CURLOPT_PROXYTYPE, CURLPROXY_SOCKS5)); +				LLCurlFF::check_easy_code(curl_easy_setopt(handle, CURLOPT_PROXYTYPE, CURLPROXY_SOCKS5));  				if (mAuthMethodSelected == METHOD_PASSWORD)  				{  					std::string auth_string = mSocksUsername + ":" + mSocksPassword; -					check_curl_code(curl_easy_setopt(handle, CURLOPT_PROXYUSERPWD, auth_string.c_str())); +					LLCurlFF::check_easy_code(curl_easy_setopt(handle, CURLOPT_PROXYUSERPWD, auth_string.c_str()));  				}  			}  			else  			{ -				check_curl_code(curl_easy_setopt(handle, CURLOPT_PROXYTYPE, CURLPROXY_HTTP)); +				LLCurlFF::check_easy_code(curl_easy_setopt(handle, CURLOPT_PROXYTYPE, CURLPROXY_HTTP));  			}  		}  	} @@ -473,7 +466,7 @@ void LLProxy::applyProxySettings(CURL* handle)   * @param maxinlen		Maximum possible length of received data.  Short reads are allowed.   * @return 				Indicates APR status code of exchange. APR_SUCCESS if exchange was successful, -1 if invalid data length was received.   */ -static S32 tcp_handshake(LLSocket::ptr_t handle, char * dataout, apr_size_t outlen, char * datain, apr_size_t maxinlen) +static apr_status_t tcp_blocking_handshake(LLSocket::ptr_t handle, char * dataout, apr_size_t outlen, char * datain, apr_size_t maxinlen)  {  	apr_socket_t* apr_socket = handle->getSocket();  	apr_status_t rv = APR_SUCCESS; @@ -522,7 +515,6 @@ static S32 tcp_handshake(LLSocket::ptr_t handle, char * dataout, apr_size_t outl   *   * Checks for a successful connection, and makes sure the connection is closed if it fails.   * - * @param pool		APR pool to pass into the LLSocket.   * @param host		The host to open the connection to.   * @return			The created socket.  Will evaluate as NULL if the connection is unsuccessful.   */ @@ -541,7 +533,7 @@ static LLSocket::ptr_t tcp_open_channel(LLHost host)  /**   * @brief Close the socket.   * - * @param handle_ptr A pointer-to-pointer to avoid increasing the use count. + * @param handle_ptr The handle of the socket being closed. A pointer-to-pointer to avoid increasing the use count.   */  static void tcp_close_channel(LLSocket::ptr_t* handle_ptr)  { diff --git a/indra/llmessage/llproxy.h b/indra/llmessage/llproxy.h index 621debb61d..a919370540 100644 --- a/indra/llmessage/llproxy.h +++ b/indra/llmessage/llproxy.h @@ -36,7 +36,6 @@  #include <string>  // SOCKS error codes returned from the StartProxy method -  #define SOCKS_OK 0  #define SOCKS_CONNECT_ERROR (-1)  #define SOCKS_NOT_PERMITTED (-2) @@ -46,7 +45,6 @@  #define SOCKS_HOST_CONNECT_FAILED (-6)  #define SOCKS_INVALID_HOST (-7) -  #ifndef MAXHOSTNAMELEN  #define	MAXHOSTNAMELEN (255 + 1) /* socks5: 255, +1 for len. */  #endif @@ -225,62 +223,71 @@ class LLProxy: public LLSingleton<LLProxy>  {  	LOG_CLASS(LLProxy);  public: -	// METHODS THAT DO NOT LOCK mProxyMutex! - +	/*########################################################################################### +	METHODS THAT DO NOT LOCK mProxyMutex! +	###########################################################################################*/ +	// Constructor, cannot have parameters due to LLSingleton parent class. Call from main thread only.  	LLProxy(); -	// static check for enabled status for UDP packets +	// Static check for enabled status for UDP packets. Call from main thread only.  	static bool isSOCKSProxyEnabled() { return sUDPProxyEnabled; } -	// check for enabled status for HTTP packets -	// mHTTPProxyEnabled is atomic, so no locking is required for thread safety. -	bool isHTTPProxyEnabled() const { return mHTTPProxyEnabled; } - -	// Get the UDP proxy address and port +	// Get the UDP proxy address and port. Call from main thread only.  	LLHost getUDPProxy() const { return mUDPProxy; } -	// Get the SOCKS 5 TCP control channel address and port -	LLHost getTCPProxy() const { return mTCPProxy; } +	/*########################################################################################### +	END OF NON-LOCKING METHODS +	###########################################################################################*/ -	// END OF NON-LOCKING METHODS +	/*########################################################################################### +	METHODS THAT LOCK mProxyMutex! DO NOT CALL WHILE mProxyMutex IS LOCKED! +	###########################################################################################*/ +	// Destructor, closes open connections. Do not call directly, use cleanupClass(). +	~LLProxy(); -	// METHODS THAT DO LOCK mProxyMutex! DO NOT CALL WHILE mProxyMutex IS LOCKED! +	// Delete LLProxy singleton. Allows the apr_socket used in the SOCKS 5 control channel to be +	// destroyed before the call to apr_terminate. Call from main thread only. +	static void cleanupClass(); -	~LLProxy(); +	// Apply the current proxy settings to a curl request. Doesn't do anything if mHTTPProxyEnabled is false. +	// Safe to call from any thread. +	void applyProxySettings(CURL* handle); +	void applyProxySettings(LLCurl::Easy* handle); +	void applyProxySettings(LLCurlEasyRequest* handle); -	// Start a connection to the SOCKS 5 proxy +	// Start a connection to the SOCKS 5 proxy. Call from main thread only.  	S32 startSOCKSProxy(LLHost host); -	// Disconnect and clean up any connection to the SOCKS 5 proxy +	// Disconnect and clean up any connection to the SOCKS 5 proxy. Call from main thread only.  	void stopSOCKSProxy(); -	// Delete LLProxy singleton, destroying the APR pool used by the control channel. -	static void cleanupClass(); - -	// Set up to use Password auth when connecting to the SOCKS proxy +	// Use Password auth when connecting to the SOCKS proxy. Call from main thread only.  	bool setAuthPassword(const std::string &username, const std::string &password); -	// Set up to use No Auth when connecting to the SOCKS proxy +	// Disable authentication when connecting to the SOCKS proxy. Call from main thread only.  	void setAuthNone(); -	// Get the currently selected auth method. -	LLSocks5AuthType getSelectedAuthMethod() const; - -	// Proxy HTTP packets via httpHost, which can be a SOCKS 5 or a HTTP proxy -	// as specified in type +	// Proxy HTTP packets via httpHost, which can be a SOCKS 5 or a HTTP proxy. +	// as specified in type. Call from main thread only.  	bool enableHTTPProxy(LLHost httpHost, LLHttpProxyType type);  	bool enableHTTPProxy(); -	// Stop proxying HTTP packets +	// Stop proxying HTTP packets. Call from main thread only.  	void disableHTTPProxy(); -	// Apply the current proxy settings to a curl request. Doesn't do anything if mHTTPProxyEnabled is false. -	void applyProxySettings(CURL* handle); -	void applyProxySettings(LLCurl::Easy* handle); -	void applyProxySettings(LLCurlEasyRequest* handle); +	/*########################################################################################### +	END OF LOCKING METHODS +	###########################################################################################*/ +private: +	/*########################################################################################### +	METHODS THAT LOCK mProxyMutex! DO NOT CALL WHILE mProxyMutex IS LOCKED! +	###########################################################################################*/ -	// Get the HTTP proxy address and port -	LLHost getHTTPProxy() const; +	// Perform a SOCKS 5 authentication and UDP association with the proxy server. +	S32 proxyHandshake(LLHost proxy); + +	// Get the currently selected auth method. +	LLSocks5AuthType getSelectedAuthMethod() const;  	// Get the currently selected HTTP proxy type  	LLHttpProxyType getHTTPProxyType() const; @@ -288,21 +295,21 @@ public:  	std::string getSocksPwd() const;  	std::string getSocksUser() const; -	// END OF LOCKING METHODS -private: -	// Open a communication channel to the SOCKS 5 proxy proxy, at port messagePort -	S32 proxyHandshake(LLHost proxy); +	/*########################################################################################### +	END OF LOCKING METHODS +	###########################################################################################*/  private: -	// Is the HTTP proxy enabled? -	// Safe to read in any thread, do not write directly, -	// use enableHTTPProxy() and disableHTTPProxy() instead. +	// Is the HTTP proxy enabled? Safe to read in any thread, but do not write directly. +	// Instead use enableHTTPProxy() and disableHTTPProxy() instead.  	mutable LLAtomic32<bool> mHTTPProxyEnabled; -	// Mutex to protect shared members in non-main thread calls to applyProxySettings() +	// Mutex to protect shared members in non-main thread calls to applyProxySettings().  	mutable LLMutex mProxyMutex; -	// MEMBERS READ AND WRITTEN ONLY IN THE MAIN THREAD. DO NOT SHARE! +	/*########################################################################################### +	MEMBERS READ AND WRITTEN ONLY IN THE MAIN THREAD. DO NOT SHARE! +	###########################################################################################*/  	// Is the UDP proxy enabled?  	static bool sUDPProxyEnabled; @@ -315,9 +322,13 @@ private:  	// socket handle to proxy TCP control channel  	LLSocket::ptr_t mProxyControlChannel; -	// END OF UNSHARED MEMBERS +	/*########################################################################################### +	END OF UNSHARED MEMBERS +	###########################################################################################*/ -	// MEMBERS WRITTEN IN MAIN THREAD AND READ IN ANY THREAD. ONLY READ OR WRITE AFTER LOCKING mProxyMutex! +	/*########################################################################################### +	MEMBERS WRITTEN IN MAIN THREAD AND READ IN ANY THREAD. ONLY READ OR WRITE AFTER LOCKING mProxyMutex! +	###########################################################################################*/  	// HTTP proxy address and port  	LLHost mHTTPProxy; @@ -325,7 +336,7 @@ private:  	// Currently selected HTTP proxy type. Can be web or socks.  	LLHttpProxyType mProxyType; -	// SOCKS 5 auth method selected +	// SOCKS 5 selected authentication method.  	LLSocks5AuthType mAuthMethodSelected;  	// SOCKS 5 username @@ -333,7 +344,9 @@ private:  	// SOCKS 5 password  	std::string mSocksPassword; -	// END OF SHARED MEMBERS +	/*########################################################################################### +	END OF SHARED MEMBERS +	###########################################################################################*/  };  #endif | 
