Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029 #ifndef __TLS_TUNNEL_H__
00030 #define __TLS_TUNNEL_H__
00031
00032 #include <boost/bind.hpp>
00033 #include <boost/function.hpp>
00034 #include <boost/lexical_cast.hpp>
00035 #include <boost/enable_shared_from_this.hpp>
00036 #include <asio.hpp>
00037 #include <string>
00038 #include <vector>
00039 #ifdef _MSC_VER
00040 typedef long ssize_t;
00041 typedef int pid_t;
00042 #endif
00043 #include <gcrypt.h>
00044 #include <gnutls/gnutls.h>
00045 #include <gnutls/x509.h>
00046
00047 namespace tls_tunnel {
00048
00049 typedef boost::shared_ptr<asio::ip::tcp::socket> socket_ptr_t;
00050 typedef boost::shared_ptr<gnutls_session_t> session_ptr_t;
00051 typedef boost::shared_ptr< std::vector<char> > buffer_ptr_t;
00052
00053 class Exception {
00054 public:
00055 Exception(const std::string& message);
00056 const std::string& message() const;
00057 private:
00058 std::string message_;
00059 };
00060
00061 class Transport : public boost::enable_shared_from_this<Transport> {
00062 public:
00063 asio::io_service& io_service();
00064 void run();
00065 void stop();
00066
00067 protected:
00068 Transport();
00069 virtual ~Transport();
00070
00071 private:
00072 asio::io_service io_service_;
00073 asio::io_service::work work_;
00074 };
00075
00076 typedef boost::shared_ptr<Transport> transport_ptr_t;
00077
00078 class ClientTransport : public Transport {
00079 public:
00080 ClientTransport(const std::string& host, unsigned short port,
00081 boost::function<void (transport_ptr_t, socket_ptr_t)> on_connect);
00082 void connect();
00083 private:
00084 std::string host_;
00085 unsigned short port_;
00086 boost::function<void (transport_ptr_t, socket_ptr_t)> on_connect_;
00087 };
00088
00089
00090 class ServerTransport : public Transport {
00091 public:
00092 ServerTransport(const std::string& ip, unsigned short port,
00093 boost::function<void (transport_ptr_t, socket_ptr_t)> on_connect);
00094 void accept();
00095 private:
00096 void on_accept(const asio::error_code& error, socket_ptr_t socket_ptr);
00097
00098 asio::ip::tcp::acceptor acceptor_;
00099 boost::function<void (transport_ptr_t, socket_ptr_t)> on_connect_;
00100 };
00101
00102 class Proxy {
00103 public:
00104 virtual ~Proxy();
00105 static bool tls_tunnel_init();
00106 static void tls_tunnel_deinit();
00107 virtual void setup() = 0;
00108 void run();
00109 virtual void stop();
00110
00111 protected:
00112 Proxy(const std::string& ca_file);
00113
00114 void on_local_read(const asio::error_code& error, std::size_t bytes_transferred,
00115 transport_ptr_t transport_ptr, session_ptr_t session_ptr, socket_ptr_t local_socket_ptr,
00116 buffer_ptr_t local_buffer_ptr, socket_ptr_t remote_socket_ptr);
00117 void tunnel(transport_ptr_t transport_ptr, session_ptr_t session_ptr,
00118 socket_ptr_t local_socket_ptr, socket_ptr_t remote_socket_ptr);
00119 void disconnect_(transport_ptr_t transport_ptr, session_ptr_t session_ptr,
00120 socket_ptr_t local_socket_ptr, socket_ptr_t remote_socket_ptr);
00121
00122 gnutls_certificate_credentials_t x509cred;
00123
00124 transport_ptr_t transport_ptr_;
00125
00126 private:
00127 void tunnel_(transport_ptr_t transport_ptr, session_ptr_t session_ptr,
00128 socket_ptr_t local_socket_ptr, buffer_ptr_t local_buffer_ptr,
00129 socket_ptr_t remote_socket);
00130
00131 asio::thread* t;
00132 };
00133
00134
00135 class ClientProxy : public Proxy {
00136 public:
00137 ClientProxy(const std::string& connect_address, unsigned short connect_port,
00138 const std::string& ca_file, bool check_hostname);
00139
00140 virtual void setup();
00141 virtual void stop();
00142
00143 const std::string& local_address() const;
00144 unsigned short local_port() const;
00145
00146 private:
00147 void on_transport_connect(transport_ptr_t transport_ptr, socket_ptr_t remote_socket_ptr);
00148 void on_client_connect(const asio::error_code& error, transport_ptr_t transport_ptr,
00149 session_ptr_t session_ptr, socket_ptr_t local_socket_ptr, socket_ptr_t remote_socket_ptr);
00150 session_ptr_t setup_tls_session(socket_ptr_t remote_socket_ptr);
00151
00152 std::string local_address_;
00153 unsigned short local_port_;
00154 std::string connect_address_;
00155 unsigned short connect_port_;
00156 boost::shared_ptr<asio::ip::tcp::acceptor> acceptor_ptr;
00157 bool check_hostname_;
00158 };
00159
00160 class ServerProxy : public Proxy {
00161 public:
00162 ServerProxy(const std::string& bind_ip, unsigned short bind_port, unsigned short local_port,
00163 const std::string& ca_file, const std::string& cert_file, const std::string& key_file);
00164
00165 virtual void setup();
00166
00167 private:
00168 void on_transport_connect(transport_ptr_t transport_ptr, socket_ptr_t remote_socket_ptr);
00169 session_ptr_t setup_tls_session(socket_ptr_t remote_socket_ptr);
00170
00171 std::string bind_ip_;
00172 unsigned short bind_port_;
00173 unsigned short local_port_;
00174 gnutls_dh_params_t dh_params;
00175 };
00176
00177 }
00178
00179 #endif