summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLu <[email protected]>2018-06-11 10:51:11 +0800
committerLu <[email protected]>2018-06-11 10:51:11 +0800
commit72bca3159ec93e2e7d6a9612d8601fe7d40b07f6 (patch)
tree45315131f609097296997d5079eb651fc452222a
parentfe5d92850822671a2988048cdd0ed9e1bc619812 (diff)
增加Forge Socket的Listener
-rw-r--r--.idea/codeStyles/Project.xml1
-rw-r--r--.idea/inspectionProfiles/Project_Default.xml8
-rw-r--r--src/CMakeLists.txt7
-rw-r--r--src/cfgparser.cc42
-rw-r--r--src/cfgparser.h37
-rw-r--r--src/compat.h162
-rw-r--r--src/connection.cc141
-rw-r--r--src/http.h34
-rw-r--r--src/http1.cc141
-rw-r--r--src/http2.cc159
-rw-r--r--src/httpscan.cc80
-rw-r--r--src/httpscan.h1
-rw-r--r--src/logger.cc1
-rw-r--r--src/main.cc44
-rw-r--r--src/opts.h5
-rw-r--r--src/proxy.cc644
-rw-r--r--src/pxyconn.cc573
-rw-r--r--src/pxyconn.h15
18 files changed, 1331 insertions, 764 deletions
diff --git a/.idea/codeStyles/Project.xml b/.idea/codeStyles/Project.xml
index b5725b7..1245a4c 100644
--- a/.idea/codeStyles/Project.xml
+++ b/.idea/codeStyles/Project.xml
@@ -17,7 +17,6 @@
<option name="CLASS_CONSTRUCTOR_INIT_LIST_WRAP" value="5" />
<option name="SUPERCLASS_LIST_BEFORE_COLON" value="0" />
<option name="ALIGN_INIT_LIST_IN_COLUMNS" value="false" />
- <option name="INSERT_OVERRIDE" value="false" />
<option name="ADD_BRIEF_TAG" value="true" />
</Objective-C>
<Objective-C-extensions>
diff --git a/.idea/inspectionProfiles/Project_Default.xml b/.idea/inspectionProfiles/Project_Default.xml
new file mode 100644
index 0000000..a4d36d3
--- /dev/null
+++ b/.idea/inspectionProfiles/Project_Default.xml
@@ -0,0 +1,8 @@
+<component name="InspectionProjectProfileManager">
+ <profile version="1.0">
+ <option name="myName" value="Project Default" />
+ <inspection_tool class="ClangTidyInspection" enabled="true" level="WARNING" enabled_by_default="true">
+ <option name="clangTidyChecks" value="*,-android-*,-bugprone-bool-pointer-implicit-conversion,-cert-env33-c,-cert-dcl50-cpp,-cert-dcl59-cpp,-cppcoreguidelines-no-malloc,-cppcoreguidelines-owning-memory,-cppcoreguidelines-pro-bounds-array-to-pointer-decay,-cppcoreguidelines-pro-bounds-constant-array-index,-cppcoreguidelines-pro-bounds-pointer-arithmetic,-cppcoreguidelines-pro-type-const-cast,-cppcoreguidelines-pro-type-cstyle-cast,-cppcoreguidelines-pro-type-reinterpret-cast,-cppcoreguidelines-pro-type-union-access,-cppcoreguidelines-pro-type-vararg,-cppcoreguidelines-special-member-functions,-fuchsia-*,-google-*,google-default-arguments,google-explicit-constructor,google-runtime-member-string-references,google-runtime-operator,-hicpp-braces-around-statements,-hicpp-named-parameter,-hicpp-no-array-decay,-hicpp-no-assembler,-hicpp-no-malloc,-hicpp-function-size,-hicpp-special-member-functions,-hicpp-vararg,-llvm-*,-objc-*,-readability-else-after-return,-readability-implicit-bool-conversion,-readability-named-parameter,-readability-simplify-boolean-expr,-readability-braces-around-statements,-readability-identifier-naming,-readability-function-size,-readability-redundant-member-init,-misc-bool-pointer-implicit-conversion,-misc-definitions-in-headers,-misc-unused-alias-decls,-misc-unused-parameters,-misc-unused-using-decls,-modernize-use-using,-modernize-use-default-member-init,-clang-diagnostic-*,-clang-analyzer-*,-readability-redundant-control-flow" />
+ </inspection_tool>
+ </profile>
+</component> \ No newline at end of file
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index e227370..f4ed9e7 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -1,8 +1,8 @@
find_package(OpenSSL REQUIRED)
add_library(tfe-library base64.cc build.cc cache.cc cachemgr.cc cachessess.cc compat.cc easylogging++.cc
- cachedsess.cc cachetgcrt.cc cachefkcrt.cc cert.cc certstore.cc logger.cc
- dynbuf.cc nat.cc opts.cc privsep.cc proxy.cc pxythrmgr.cc pxysslshut.cc
+ cachedsess.cc cachetgcrt.cc cachefkcrt.cc cert.cc certstore.cc logger.cc cfgparser.cc
+ dynbuf.cc nat.cc opts.cc privsep.cc proxy.cc pxythrmgr.cc pxysslshut.cc pxyconn.cc
ssl.cc sys.cc thrqueue.cc url.cc util.cc httpscan.cc httpaction.cc http2.cc http1.cc http.cc)
#pxyconn.cc
@@ -16,7 +16,8 @@ target_link_libraries(tfe-library
libevent-static-pthreads
http-parser-static
nghttp2-static
- MESA_prof_load-static)
+ MESA_prof_load-static
+ jsoncpp rdkafka)
target_link_libraries(tfe-library maatframe MESA_handle_logger)
diff --git a/src/cfgparser.cc b/src/cfgparser.cc
new file mode 100644
index 0000000..27e9ccc
--- /dev/null
+++ b/src/cfgparser.cc
@@ -0,0 +1,42 @@
+//
+// Created by luqiu on 2018-6-7.
+//
+
+#include "cfgparser.h"
+
+template<>
+std::string TfeConfigParser::GetValue(const std::string &str_section, const std::string &str_entry)
+{
+ char __str_buffer[TFE_STRING_MAX];
+ memset(__str_buffer, 0, sizeof(__str_buffer));
+
+ int ret = MESA_load_profile_string_nodef(str_cfgfile_.c_str(), str_section.c_str(), str_entry.c_str(),
+ __str_buffer, sizeof(__str_buffer));
+
+ if (ret < 0)
+ throw cfg_lost_entry(str_cfgfile_, str_section, str_entry, "");
+
+ return std::string(__str_buffer);
+}
+
+template<>
+unsigned long TfeConfigParser::GetValue(const std::string &str_section, const std::string &str_entry)
+{
+ char *__ptr = nullptr;
+ std::string __str_value = GetValue<std::string>(str_section, str_entry);
+
+ unsigned long __value = strtoul(__str_value.c_str(), &__ptr, 0);
+ if (__ptr == __str_value.c_str())
+ {
+ throw cfg_invalid_format(str_cfgfile_, str_section, str_entry,
+ __str_value + " is not valid unsigned number. ");
+ }
+
+ return __value;
+}
+
+template<>
+bool TfeConfigParser::GetValue(const std::string &str_section, const std::string &str_entry)
+{
+ return GetValue<unsigned long>(str_section, str_entry) != 0;
+} \ No newline at end of file
diff --git a/src/cfgparser.h b/src/cfgparser.h
index 4853ef2..c7e6729 100644
--- a/src/cfgparser.h
+++ b/src/cfgparser.h
@@ -40,43 +40,6 @@ private:
std::string str_cfgfile_;
};
-template<>
-std::string TfeConfigParser::GetValue(const std::string &str_section, const std::string &str_entry)
-{
- char __str_buffer[TFE_STRING_MAX];
- memset(__str_buffer, 0, sizeof(__str_buffer));
-
- int ret = MESA_load_profile_string_nodef(str_cfgfile_.c_str(), str_section.c_str(), str_entry.c_str(),
- __str_buffer, sizeof(__str_buffer));
-
- if (ret < 0)
- throw cfg_lost_entry(str_cfgfile_, str_section, str_entry, "");
-
- return std::string(__str_buffer);
-}
-
-template<>
-unsigned long TfeConfigParser::GetValue(const std::string &str_section, const std::string &str_entry)
-{
- char *__ptr = nullptr;
- std::string __str_value = GetValue<std::string>(str_section, str_entry);
-
- unsigned long __value = strtoul(__str_value.c_str(), &__ptr, 0);
- if (__ptr == __str_value.c_str())
- {
- throw cfg_invalid_format(str_cfgfile_, str_section, str_entry,
- __str_value + " is not valid unsigned number. ");
- }
-
- return __value;
-}
-
-template<>
-bool TfeConfigParser::GetValue(const std::string &str_section, const std::string &str_entry)
-{
- return GetValue<unsigned long>(str_section, str_entry) != 0;
-}
-
template<typename T>
T TfeConfigParser::GetValueWithDefault(
const std::string &str_section,
diff --git a/src/compat.h b/src/compat.h
index 1fcf1e0..5fd2b53 100644
--- a/src/compat.h
+++ b/src/compat.h
@@ -1,5 +1,6 @@
#pragma once
+#include <exception>
#include <memory>
#include <cstdio>
@@ -32,6 +33,163 @@ using evbuffer_unique_ptr_t = std::unique_ptr<struct evbuffer, EventDeleter>;
using file_unique_ptr_t = std::unique_ptr<FILE, FileDescriptorDeleter>;
using fd_unique_ptr_t = std::unique_ptr<int, FileDescriptorDeleter>;
+/* Bufferevent托管类
+ * Bufferevent指针用于构造本Class后,即失去对指针的所有权,指针的释放由本类的析构函数完成 */
+class BufferEvent
+{
+public:
+ explicit BufferEvent(struct bufferevent *bev)
+ { bev_.reset(bev); }
+
+ using data_cb_t = std::function<int(struct bufferevent *bev)>;
+ using event_cb_t = std::function<int(struct bufferevent *bev, short what)>;
+ using exception_cb_t = std::function<int(std::exception_ptr ex_ptr)>;
+
+ void SetReadCallback(data_cb_t cb)
+ { read_cb_ = cb; }
+ void SetWriteCallback(data_cb_t cb)
+ { write_cb_ = cb; }
+ void SetEventCallback(event_cb_t cb)
+ { event_cb_ = cb; }
+ void SetExceptionCallback(exception_cb_t cb)
+ { exception_cb_ = cb; }
+
+ void Enable(short what)
+ { bufferevent_enable(bev_.get(), what); }
+ void Disable(short what)
+ { bufferevent_disable(bev_.get(), what); }
+ struct bufferevent *Raw()
+ { return bev_.get(); }
+
+private:
+ data_cb_t read_cb_;
+ data_cb_t write_cb_;
+ event_cb_t event_cb_;
+ exception_cb_t exception_cb_;
+
+ struct __bufferevent_deleter
+ {
+ void operator()(struct bufferevent *bev)
+ { bufferevent_free(bev); }
+ };
+
+ std::unique_ptr<struct bufferevent, __bufferevent_deleter> bev_;
+
+private:
+ static int __wrapper_cb_read(struct bufferevent *bev, void *user)
+ {
+ auto *__this = static_cast<BufferEvent *>(user);
+ std::exception_ptr exp_ptr;
+
+ try
+ {
+ return __this->read_cb_(bev);
+ }
+ catch (const std::exception & e)
+ {
+ exp_ptr = std::current_exception();
+ }
+
+ if(__this->exception_cb_ == nullptr)
+ {
+ std::rethrow_exception(exp_ptr);
+ }
+
+ if (__this->exception_cb_ != nullptr && __this->exception_cb_(exp_ptr) != 0)
+ {
+ std::rethrow_exception(exp_ptr);
+ }
+
+ return 0;
+ }
+
+ static int __wrapper_cb_write(struct bufferevent *bev, void *user)
+ {
+ auto *__this = static_cast<BufferEvent *>(user);
+ std::exception_ptr exp_ptr;
+
+ try
+ {
+ return __this->write_cb_(bev);
+ }
+ catch (const std::exception & e)
+ {
+ exp_ptr = std::current_exception();
+ }
+
+ if(__this->exception_cb_ == nullptr)
+ {
+ std::rethrow_exception(exp_ptr);
+ }
+
+ if (__this->exception_cb_ != nullptr && __this->exception_cb_(exp_ptr) != 0)
+ {
+ std::rethrow_exception(exp_ptr);
+ }
+
+ return 0;
+ }
+
+ static int __wrapper_cb_event(struct bufferevent *bev, short what, void *user)
+ {
+ auto *__this = static_cast<BufferEvent *>(user);
+ std::exception_ptr exp_ptr;
+
+ try
+ {
+ return __this->event_cb_(bev, what);
+ }
+ catch (const std::exception & e)
+ {
+ exp_ptr = std::current_exception();
+ }
+
+ if(__this->exception_cb_ == nullptr)
+ {
+ std::rethrow_exception(exp_ptr);
+ }
+
+ if (__this->exception_cb_ != nullptr && __this->exception_cb_(exp_ptr) != 0)
+ {
+ std::rethrow_exception(exp_ptr);
+ }
+
+ return 0;
+ }
+};
+
+/* Event托管类
+ * Bufferevent指针用于构造本Class后,即失去对指针的所有权,指针的释放由本类的析构函数完成 */
+class Event
+{
+public:
+ explicit Event() = default;
+ virtual ~Event() = default;
+
+ using event_cb_t = std::function<void(evutil_socket_t fd, short what)>;
+ void Init(struct event_base * ev_base, evutil_socket_t fd, short en_event, event_cb_t cb)
+ {
+ ev_.reset(event_new(ev_base, fd, en_event, __wrapper_event, this));
+ }
+
+private:
+ event_cb_t event_cb_;
+ struct __event_deleter
+ {
+ void operator()(struct event *ev)
+ { event_free(ev); }
+ };
+
+ std::unique_ptr<struct event, __event_deleter> ev_;
+
+private:
+ static void __wrapper_event(evutil_socket_t fd, short what, void * user)
+ {
+ auto *__this = static_cast<Event *>(user);
+ return __this->event_cb_(fd, what);
+ }
+};
+
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// Stream.h内的数据结构转换工具
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
@@ -39,7 +197,7 @@ using fd_unique_ptr_t = std::unique_ptr<int, FileDescriptorDeleter>;
struct SappIpAddrDeleter
{
- void operator()(struct ipaddr * ptr_addr)
+ void operator()(struct ipaddr *ptr_addr)
{
if (ptr_addr->addrtype == ADDR_TYPE_IPV4) delete ptr_addr->v4;
if (ptr_addr->addrtype == ADDR_TYPE_IPV6) delete ptr_addr->v6;
@@ -48,7 +206,7 @@ struct SappIpAddrDeleter
};
using sapp_ip_addr_ptr_t = std::unique_ptr<struct ipaddr, SappIpAddrDeleter>;
-sapp_ip_addr_ptr_t sockaddr_to_sapp_ipaddr(const struct sockaddr * sk_addr_src, const struct sockaddr * sk_addr_dst);
+sapp_ip_addr_ptr_t sockaddr_to_sapp_ipaddr(const struct sockaddr *sk_addr_src, const struct sockaddr *sk_addr_dst);
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
diff --git a/src/connection.cc b/src/connection.cc
new file mode 100644
index 0000000..1dbf2f9
--- /dev/null
+++ b/src/connection.cc
@@ -0,0 +1,141 @@
+
+#include <cassert>
+#include "compat.h"
+
+extern "C"
+{
+#include <event2/event.h>
+#include <event2/bufferevent.h>
+#include <openssl/ossl_typ.h>
+}
+
+enum
+{
+ kDirectionDownstream,
+ kDirectionUpstream
+};
+
+class Connection
+{
+
+};
+
+class ConnectionDownstream : std::enable_shared_from_this<ConnectionDownstream>
+{
+public:
+ /* 应用层协议选项 */
+ struct option
+ {
+ /* 是否自动识别SSL */
+ bool can_upgrade_to_ssl;
+ /* 是否自动识别HttpV1 */
+ bool can_upgrade_to_http_v1;
+ /* 是否自动识别HttpV2,即HttpV2的引导区域 */
+ bool can_upgrade_to_http_v2;
+ };
+
+ explicit ConnectionDownstream(struct event_base *evbase, evutil_socket_t fd,
+ const struct option &upgrade_option);
+
+ void Setup();
+ void Shutdown();
+
+private:
+ struct option options;
+
+ struct sockaddr_storage local_addr_;
+ socklen_t local_addrlen_;
+ struct sockaddr_storage peer_addr_;
+ socklen_t peer_addrlen_;
+
+ std::unique_ptr<BufferEvent> bev_ptr_;
+ std::unique_ptr<Event> ev_ptr_;
+
+ evutil_socket_t fd_;
+ struct event_base * evbase_;
+
+private:
+ int cb_read(struct bufferevent *bev);
+ int cb_write(struct bufferevent *bev);
+ int cb_event(struct bufferevent *bev, short events);
+ int cb_exception(std::exception_ptr ex_ptr);
+
+ void cb_scan_clienthello(struct event * ev, short what);
+
+private:
+ /* Setup函数,对于SSL需要根据Raw的内容解析SNI */
+ void __setup_autograde_callback();
+ void __setup_bev_callback();
+};
+
+ConnectionDownstream::ConnectionDownstream(struct event_base *evbase, evutil_socket_t fd,
+ const struct option &upgrade_option) : fd_(fd), options(upgrade_option), evbase_(evbase)
+{}
+
+void ConnectionDownstream::Setup()
+{
+ return options.can_upgrade_to_ssl ? __setup_autograde_callback() : __setup_bev_callback();
+}
+
+void ConnectionDownstream::__setup_autograde_callback()
+{
+ auto shared_this_ptr = shared_from_this();
+ ev_ptr_ = std::make_unique<Event>();
+
+ /* 初始化一个Event,处理TCP上的原始数据,解析SSL ClientHello中的SNI选项 */
+ ev_ptr_->Init(evbase_, fd_, EV_READ, [shared_this_ptr](struct event * ev, short what)
+ {
+ auto __this_ptr = shared_this_ptr;
+ return __this_ptr->cb_scan_clienthello(ev, what);
+ });
+
+ return;
+}
+
+void ConnectionDownstream::__setup_bev_callback()
+{
+ /* 对于Plain TCP,创建Bufferevent,调用ReadCb/EventCb直接处理 */
+ struct bufferevent *bev_raw = bufferevent_socket_new(evbase_, fd_, BEV_OPT_DEFER_CALLBACKS);
+
+ if (unlikely(bev_raw == nullptr))
+ {
+ throw std::runtime_error("Error creating bufferevent socket");
+ }
+
+ /* 托管给Bufferevent */
+ bev_ptr_ = std::make_unique<BufferEvent>(bev_raw);
+ auto shared_this_ptr = shared_from_this();
+
+ /* 在Callback中保存ConnectionDownstream的指针,当所有回调函数清除时,ConnectionDownstream析构 */
+ bev_ptr_->SetReadCallback([shared_this_ptr](struct bufferevent *bev) -> int
+ {
+ auto __this_ptr = shared_this_ptr;
+ return __this_ptr->cb_read(bev);
+ });
+
+ bev_ptr_->SetWriteCallback([shared_this_ptr](struct bufferevent *bev) -> int
+ {
+ auto __this_ptr = shared_this_ptr;
+ return __this_ptr->cb_write(bev);
+ });
+
+ bev_ptr_->SetEventCallback([shared_this_ptr](struct bufferevent *bev, short what) -> int
+ {
+ auto __this_ptr = shared_this_ptr;
+ return __this_ptr->cb_event(bev, what);
+ });
+
+ bev_ptr_->SetExceptionCallback([shared_this_ptr](std::exception_ptr exp_ptr)->int
+ {
+ auto __this_ptr = shared_this_ptr;
+ return __this_ptr->cb_exception(exp_ptr);
+ });
+
+ /* 注册EV_READ、EV_WRITE事件,当事件发生时调用cb_read、cb_write处理 */
+ bev_ptr_->Enable(EV_READ | EV_WRITE);
+}
+
+void ConnectionDownstream::cb_scan_clienthello(struct event *ev, short what)
+{
+
+}
diff --git a/src/http.h b/src/http.h
index e895772..482d6f2 100644
--- a/src/http.h
+++ b/src/http.h
@@ -1,9 +1,10 @@
#ifndef TFE_HTTP_H
#define TFE_HTTP_H
+#include <memory>
#include <map>
#include <string>
-#include <memory>
+#include <list>
class HttpConnection;
class HttpSession;
@@ -55,7 +56,7 @@ class HttpSession
{
public:
explicit HttpSession(HttpConnection &connection) : http_connection_(connection) {}
- ~HttpSession() = default;
+ virtual ~HttpSession() = default;
using http_session_cb_t = std::function<void(HttpSession &)>;
@@ -174,4 +175,33 @@ public:
std::unique_ptr<HttpRequest> HttpRequestFactory(int primary_version, int second_version);
std::unique_ptr<HttpResponse> HttpResponseFactory(int primary_version, int second_version);
+#include "pxyconn.h"
+
+class Http1Connection : public HttpConnection
+{
+public:
+ Http1Connection() = default;
+ ~Http1Connection() = default;
+
+ void Close() override
+ { need_to_close_ = true; };
+
+ int on_connection_read_request(pxy_conn_ctx_t *conn_ctx, pxy_conn_desc_t *conn_this, pxy_conn_desc_t *conn_other);
+ int on_connection_read_response(pxy_conn_ctx_t *conn_ctx, struct bufferevent *bev);
+ int on_connection_close(pxy_conn_ctx_t *conn_ctx, struct bufferevent *bev);
+ const sockaddr *SockAddrSource() const override;
+ const sockaddr *SockAddrDest() const override;
+
+private:
+ using http_sessions_t = std::list<std::unique_ptr<HttpSession>>;
+ http_sessions_t http_sessions_;
+
+ HttpSession &create_new_session();
+ HttpSession &last_uncomplete_session();
+
+ void drop_last_session();
+ void drop_first_session();
+ bool need_to_close_{false};
+};
+
#endif //TFE_HTTP_H
diff --git a/src/http1.cc b/src/http1.cc
index 68934cb..950ff77 100644
--- a/src/http1.cc
+++ b/src/http1.cc
@@ -1,7 +1,3 @@
-//
-// Created by luqiu on 2018-5-22.
-//
-
/* HTTP/HTTP2 Protocol Handler
*
* Author: Lu Qiuwen<[email protected]>
@@ -27,30 +23,6 @@
#include "util.h"
#include "easylogging++.h"
-class Http1Connection : public HttpConnection
-{
-public:
- Http1Connection() = default;
- ~Http1Connection() = default;
-
- void Close() override { need_to_close_ = true;} ;
-
- int on_connection_read_request(pxy_conn_ctx_t *conn_ctx, pxy_conn_desc_t *conn_this, pxy_conn_desc_t *conn_other);
- int on_connection_read_response(pxy_conn_ctx_t *conn_ctx, struct bufferevent *bev);
- int on_connection_close(pxy_conn_ctx_t *conn_ctx, struct bufferevent *bev);
-
-private:
- using http_sessions_t = std::list<std::unique_ptr<HttpSession>>;
- http_sessions_t http_sessions_;
-
- HttpSession &create_new_session();
- HttpSession &last_uncomplete_session();
-
- void drop_last_session();
- void drop_first_session();
- bool need_to_close_{false};
-};
-
class Http1Request : public HttpRequest
{
public:
@@ -75,6 +47,10 @@ public:
virtual void ForEachHeader(for_each_header_cb_t cb);
bool Complete() override
{ return request_complete_; }
+ const std::string &Url() const override;
+ void Url(const std::string &url) override;
+ const std::string &HeaderValue(const std::string &field) override;
+ void HeaderValue(const std::string &field, const std::string &value) override;
private:
std::string str_uri{};
@@ -92,7 +68,7 @@ private:
evbuffer_unique_ptr_t evbuf_content_raw_{evbuffer_unique_ptr_t(evbuffer_new())};
};
-Http1Request::Http1Request()
+ Http1Request::Http1Request()
{
http_parser_init(parser_.get(), HTTP_REQUEST);
}
@@ -128,16 +104,16 @@ ssize_t Http1Request::ConstructFromMemory(const char *buf, size_t buflen)
};
static struct http_parser_settings __parser_setting =
- {
- nullptr, /* on_message_begin */
- __http_parser_cb_on_uri, /* on_url */
- nullptr, /* on_status */
- __http_parser_cb_on_header_field, /* on_header_field */
- __http_parser_cb_on_header_value, /* on_header_value */
- __http_parser_cb_on_message_complete, /* on_headers_complete */
- nullptr, /* on_body */
- nullptr /* on_message_complete */
- };
+ {
+ nullptr, /* on_message_begin */
+ __http_parser_cb_on_uri, /* on_url */
+ nullptr, /* on_status */
+ __http_parser_cb_on_header_field, /* on_header_field */
+ __http_parser_cb_on_header_value, /* on_header_value */
+ __http_parser_cb_on_message_complete, /* on_headers_complete */
+ nullptr, /* on_body */
+ nullptr /* on_message_complete */
+ };
parser_->data = this;
size_t sz_parsed = http_parser_execute(parser_.get(), &__parser_setting, buf, buflen);
@@ -184,6 +160,25 @@ void Http1Request::ForEachHeader(HttpRequest::for_each_header_cb_t cb)
return;
}
+const std::string &Http1Request::Url() const
+{
+ return str_headers["Host"] + str_uri;
+}
+
+void Http1Request::Url(const std::string &url)
+{
+ str_uri = url;
+}
+
+const std::string &Http1Request::HeaderValue(const std::string &field)
+{
+ return str_headers[field];
+}
+
+void Http1Request::HeaderValue(const std::string &field, const std::string &value)
+{
+ str_headers[field] = value;
+}
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// HTTP Response Parser Implementation for HTTP 1.0/1.1
@@ -279,6 +274,10 @@ public:
virtual bool Complete() final
{ return parse_complete_; }
virtual void Construct() final;
+ void ResponseCode(int code) override;
+ const std::string &HeaderValue(const std::string &field) override;
+ void HeaderValue(const std::string &field, const std::string &value) override;
+ void ForEachHeader(for_each_header_cb_t cb) override;
private:
int resp_code_;
@@ -388,26 +387,46 @@ void Http1Response::Construct()
evbuf_content_raw_ = std::move(evbuf_construct);
}
+void Http1Response::ResponseCode(int code)
+{
+ resp_code_ = code;
+}
+
+const std::string &Http1Response::HeaderValue(const std::string &field)
+{
+ return str_headers[field];
+}
+
+void Http1Response::HeaderValue(const std::string &field, const std::string &value)
+{
+ str_headers[field] = value;
+}
+
+void Http1Response::ForEachHeader(HttpResponse::for_each_header_cb_t cb)
+{
+ return;
+}
+
int Http1Connection::on_connection_close(pxy_conn_ctx_t *conn_ctx, struct bufferevent *bev)
{
return 0;
}
-int Http1Connection::on_connection_read_request(
- pxy_conn_ctx_t *conn_ctx,
- pxy_conn_desc_t *conn_this, pxy_conn_desc_t *conn_other)
+int Http1Connection::on_connection_read_request(pxy_conn_ctx_t *conn_ctx, pxy_conn_desc_t *conn_this,
+ pxy_conn_desc_t *conn_other)
{
/* Get the last session */
- auto http_session_ctx = last_uncomplete_session();
+ auto & http_session = last_uncomplete_session();
+ auto & request = dynamic_cast<Http1Request &>(http_session.request());
- auto *request = reinterpret_cast<Http1Request *>(http_session_ctx.request());
auto *downstream_evbuf = bufferevent_get_input(conn_this->bev);
auto *upstream_evbuf = bufferevent_get_output(conn_other->bev);
- ssize_t forward_len = request->ConstructFromEvBuf(downstream_evbuf);
+ ssize_t forward_len = request.ConstructFromEvBuf(downstream_evbuf);
if (forward_len < 0)
{
+ LOG(DEBUG) << "RequestConstructFromEvBuf Failed, connection turns to passthrough";
conn_ctx->passthrough = 1;
return 0;
}
@@ -418,24 +437,24 @@ int Http1Connection::on_connection_read_request(
return 0;
}
- if (request->Complete())
+ if (request.Complete())
{
- http_session_ctx.CallRequestHeaderCallback();
- http_session_ctx.CallRequestBodyCallback();
+ http_session.CallRequestHeaderCallback();
+ http_session.CallRequestBodyCallback();
/* 转发请求 */
- if (request->Forward())
+ if (request.Forward())
{
- auto stolen_raw_evbuf = request->StolenEvbuf();
+ auto stolen_raw_evbuf = request.StolenEvbuf();
evbuffer_add_buffer(upstream_evbuf, stolen_raw_evbuf.release());
}
return 0;
}
- if (request->ReadOnly())
+ if (request.ReadOnly())
{
- evbuffer_add_buffer(upstream_evbuf, request->StolenEvbuf().release());
+ evbuffer_add_buffer(upstream_evbuf, request.StolenEvbuf().release());
return 0;
}
@@ -454,7 +473,7 @@ HttpSession &Http1Connection::create_new_session()
__http_session->request(HttpRequestFactory(1, 0));
/* Add to the last record */
- http_sessions_.push_back(__http_session);
+ http_sessions_.push_back(std::move(__http_session));
return *__http_session;
}
@@ -464,12 +483,13 @@ HttpSession &Http1Connection::last_uncomplete_session()
return create_new_session();
/* 最后一个Session已经处理结束了,新建一个Session */
- auto __session = http_sessions_.back();
- if (__session->request()->request_complete)
+ auto & __session = http_sessions_.back();
+
+ if (__session->request().Complete())
return create_new_session();
/* 否则,返回最后一个没有完全处理结束的Session */
- return __session;
+ return *__session;
}
void Http1Connection::drop_last_session()
@@ -484,6 +504,15 @@ void Http1Connection::drop_first_session()
http_sessions_.pop_front();
}
+const sockaddr *Http1Connection::SockAddrSource() const
+{
+ return nullptr;
+}
+const sockaddr *Http1Connection::SockAddrDest() const
+{
+ return nullptr;
+}
+
std::unique_ptr<HttpRequest> HttpRequestFactory(int primary_version, int second_version)
{
if (primary_version == 1 && second_version == 0)
diff --git a/src/http2.cc b/src/http2.cc
index 2003826..3ef07b8 100644
--- a/src/http2.cc
+++ b/src/http2.cc
@@ -43,6 +43,16 @@ class Http2Request : public HttpRequest
public:
void Serialize(std::vector<nghttp2_nv> &nv_array_output, nghttp2_data_provider *data_prd);
void ConstructContent(const char *content, size_t content_len, bool is_append);
+ const std::string &Url() const override;
+ void Url(const std::string &url) override;
+ const std::string &HeaderValue(const std::string &field) override;
+ void HeaderValue(const std::string &field, const std::string &value) override;
+ void ForEachHeader(for_each_header_cb_t cb) override;
+ bool ReadOnly() override;
+ void ReadOnly(bool is_readonly) override;
+ bool Forward() override;
+ void Forward(bool is_forward) override;
+ bool Complete() override;
private:
using header_kv_t = std::pair<std::string, std::string>;
@@ -56,7 +66,7 @@ private:
void Http2Request::Serialize(std::vector<nghttp2_nv> &nv_array_output, nghttp2_data_provider *data_prd)
{
/* HTTP2头部序列化 */
- for (auto kv_iterater : header_kv_store_)
+ for (auto & kv_iterater : header_kv_store_)
{
const auto &header_k = kv_iterater->first;
const auto &header_v = kv_iterater->second;
@@ -64,8 +74,8 @@ void Http2Request::Serialize(std::vector<nghttp2_nv> &nv_array_output, nghttp2_d
nghttp2_nv __nv;
/* 构建NV对,应用程序需保证Name, Value均为小写 */
- __nv.name = static_cast<uint8_t *>(header_k.c_str());
- __nv.value = static_cast<uint8_t *>(header_v.c_str());
+ __nv.name = reinterpret_cast<uint8_t *>(const_cast<char *>(header_k.c_str()));
+ __nv.value = reinterpret_cast<uint8_t *>(const_cast<char *>(header_v.c_str()));
__nv.namelen = header_k.length();
__nv.valuelen = header_v.length();
@@ -102,12 +112,10 @@ void Http2Request::Serialize(std::vector<nghttp2_nv> &nv_array_output, nghttp2_d
/* 复制到目的缓冲区,并删除缓冲区的已经发送的内容 */
std::copy_n(header_content_ptr->cbegin(), sz_want_to_send, buf);
- header_content_ptr->erase(header_content_ptr->cbegin(), header_content_ptr->cbegin() + sz_want_to_send);
+ header_content_ptr->erase(header_content_ptr->begin(), header_content_ptr->begin() + sz_want_to_send);
return sz_want_to_send;
};
-
- return;
}
void Http2Request::ConstructContent(const char *content, size_t content_len, bool is_append)
@@ -126,19 +134,129 @@ void Http2Request::ConstructContent(const char *content, size_t content_len, boo
return;
}
+const std::string &Http2Request::Url() const
+{
+ return "";
+}
+
+void Http2Request::Url(const std::string &url)
+{
+
+}
+
+const std::string &Http2Request::HeaderValue(const std::string &field)
+{
+ return "";
+}
+
+void Http2Request::HeaderValue(const std::string &field, const std::string &value)
+{
+
+}
+
+void Http2Request::ForEachHeader(HttpRequest::for_each_header_cb_t cb)
+{
+
+}
+
+bool Http2Request::ReadOnly()
+{
+ return false;
+}
+
+void Http2Request::ReadOnly(bool is_readonly)
+{
+
+}
+
+bool Http2Request::Forward()
+{
+ return false;
+}
+
+void Http2Request::Forward(bool is_forward)
+{
+
+}
+
+bool Http2Request::Complete()
+{
+ return false;
+}
+
class Http2Response : public HttpResponse
{
+public:
+ int ResponseCode() override;
+ void ResponseCode(int code) override;
+ const std::string &HeaderValue(const std::string &field) override;
+ void HeaderValue(const std::string &field, const std::string &value) override;
+ void ForEachHeader(for_each_header_cb_t cb) override;
+ bool ReadOnly() override;
+ void ReadOnly(bool is_readonly) override;
+ bool Forward() override;
+ void Forward(bool is_forward) override;
+ bool Complete() override;
+ void Construct() override;
private:
using header_kv_t = std::pair<std::string, std::string>;
std::vector<std::unique_ptr<header_kv_t>> header_kv_store_{};
std::map<std::string, header_kv_t &> header_kv_lookup_{};
};
+int Http2Response::ResponseCode()
+{
+ return 0;
+}
+
+void Http2Response::ResponseCode(int code)
+{
+
+}
+
+const std::string &Http2Response::HeaderValue(const std::string &field)
+{
+ return "";
+}
+
+void Http2Response::HeaderValue(const std::string &field, const std::string &value)
+{
+
+}
+void Http2Response::ForEachHeader(HttpResponse::for_each_header_cb_t cb)
+{
+
+}
+bool Http2Response::ReadOnly()
+{
+ return false;
+}
+void Http2Response::ReadOnly(bool is_readonly)
+{
+
+}
+bool Http2Response::Forward()
+{
+ return false;
+}
+void Http2Response::Forward(bool is_forward)
+{
+
+}
+bool Http2Response::Complete()
+{
+ return false;
+}
+void Http2Response::Construct()
+{
+
+}
+
class Http2Session : public HttpSession
{
public:
explicit Http2Session(Http2Connection &conn) : HttpSession(conn) {}
- virtual Http2Session() = default;
+ virtual ~Http2Session() = default;
int32_t stream_id_upstream{0};
int32_t stream_id_downstream{0};
@@ -230,7 +348,7 @@ h2_downstream::h2_downstream(Http2Connection &conn) : conn_(conn)
ssize_t h2_downstream::cb_on_send(nghttp2_session *session, const uint8_t *data,
size_t length, int flags, void *user_data)
{
- auto *this_ptr = dynamic_cast<h2_downstream *>(user_data);
+ auto *this_ptr = static_cast<h2_downstream *>(user_data);
struct bufferevent *h2_bev = this_ptr->conn_.bev_downstream_;
if (bufferevent_write(h2_bev, data, length) < 0)
@@ -246,8 +364,8 @@ ssize_t h2_downstream::cb_on_send(nghttp2_session *session, const uint8_t *data,
/* Downstream实现 */
int h2_downstream::cb_on_header_begin(nghttp2_session *session, const nghttp2_frame *frame, void *user_data)
{
- auto *this_ptr = dynamic_cast<h2_downstream *>(user_data);
- auto h2_connection = this_ptr->conn_;
+ auto *this_ptr = static_cast<h2_downstream *>(user_data);
+ auto & h2_connection = this_ptr->conn_;
/* 对于Downstream->Upstream的报文,在HTTP Request时建立新上下文 */
if (frame->hd.type != NGHTTP2_HEADERS || frame->headers.cat != NGHTTP2_HCAT_REQUEST)
@@ -264,31 +382,28 @@ int h2_downstream::cb_on_header_begin(nghttp2_session *session, const nghttp2_fr
int h2_downstream::cb_on_header(nghttp2_session *session, const nghttp2_frame *frame, const uint8_t *name,
size_t namelen, const uint8_t *value, size_t valuelen, uint8_t flags, void *user_data)
{
- auto *this_ptr = dynamic_cast<h2_downstream *>(user_data);
+ auto *this_ptr = static_cast<h2_downstream *>(user_data);
auto *h2_session = (Http2Session *) nghttp2_session_get_stream_user_data(session, frame->hd.stream_id);
assert(this_ptr != nullptr);
assert(h2_session != nullptr);
- std::string str_header_name;
- std::string str_header_value;
-
- std::copy_n(name, std::back_inserter(str_header_name), namelen);
- std::copy_n(value, std::back_inserter(str_header_value), valuelen);
+ std::string str_header_name{reinterpret_cast<const char *>(name), namelen};
+ std::string str_header_value{reinterpret_cast<const char *>(value), valuelen};
if (frame->hd.type == NGHTTP2_HCAT_REQUEST)
{
- auto request = h2_session->request();
+ auto & request = h2_session->request();
request.HeaderValue(str_header_name, str_header_value);
}
else if (frame->hd.type == NGHTTP2_HCAT_RESPONSE)
{
- auto response = h2_session->response();
+ auto & response = h2_session->response();
response.HeaderValue(str_header_name, str_header_value);
}
else if (frame->hd.type == NGHTTP2_HCAT_PUSH_RESPONSE)
{
- auto response = h2_session->response();
+ auto & response = h2_session->response();
response.HeaderValue(str_header_name, str_header_value);
}
else
@@ -333,8 +448,8 @@ int h2_downstream::cb_on_data_chunk_recv(nghttp2_session *session, uint8_t flags
/* 构建Http请求内容,由于可能存在Content分为多个DATA帧传输的情况,
* 将每片数据采用Append的方式构建HttpRequest对象 */
- auto h2_request = dynamic_cast<Http2Request &>(h2_session->request());
- h2_request.ConstructContent(static_cast<const char *>(data), len, true);
+ auto & h2_request = dynamic_cast<Http2Request &>(h2_session->request());
+ h2_request.ConstructContent(reinterpret_cast<const char *>(data), len, true);
return 0;
}
@@ -347,6 +462,7 @@ h2_upstream::h2_upstream(Http2Connection &conn) : conn_(conn)
nghttp2_session_callbacks *callbacks;
nghttp2_session_callbacks_new(&callbacks);
+#if 0
nghttp2_session_callbacks_set_send_callback(callbacks, cb_on_send);
nghttp2_session_callbacks_set_on_frame_recv_callback(callbacks, cb_on_frame_recv);
@@ -355,6 +471,7 @@ h2_upstream::h2_upstream(Http2Connection &conn) : conn_(conn)
nghttp2_session_callbacks_set_on_begin_headers_callback(callbacks, cb_on_header_begin);
nghttp2_session_callbacks_set_on_header_callback(callbacks, cb_on_header);
+#endif
nghttp2_session *__tmp_session_ptr = nullptr;
nghttp2_session_client_new(&__tmp_session_ptr, callbacks, this);
diff --git a/src/httpscan.cc b/src/httpscan.cc
index 8273b02..0ca8b70 100644
--- a/src/httpscan.cc
+++ b/src/httpscan.cc
@@ -39,24 +39,21 @@ HttpScan::HttpScan(struct tfe_instance *instance, struct tfe_config *config)
table_id_ctrl_http_res_body = __maat_table_register_or_throw(maat_feather_ref, "PXY_CTRL_HTTP_RES_BODY");
auto http_module = instance->http_module;
-
- http_module->SetHttpConnectionNewCallback([this](Http &ht, HttpConnection & ct)->void
+ http_module->SetHttpConnectionNewCallback([this](Http &ht, HttpConnection &ct) -> void
{
this->handlerConnectionCreate(ct);
});
- http_module->SetHttpConnectionCloseCallback([this](Http & ht, HttpConnection & ct)->void
+ http_module->SetHttpConnectionCloseCallback([this](Http &ht, HttpConnection &ct) -> void
{
this->handlerConnectionClose(ct);
});
-
- return;
}
void HttpScan::handlerConnectionCreate(HttpConnection &ct)
{
/* 新Session的创建处理函数 */
- ct.SetSessionNewCallback([this](HttpSession & session)->void
+ ct.SetSessionNewCallback([this](HttpSession &session) -> void
{
/* 创建HttpScan的Session Ctx */
auto __scan_ctx = std::make_shared<HttpScanSession>(*this);
@@ -66,25 +63,25 @@ void HttpScan::handlerConnectionCreate(HttpConnection &ct)
* 这样,回调时始终保持__scan_ctx的引用计数大于等于1,
* 避免在回调过程中变更回调函数导致ctx析构。
*/
- session.SetRequestHeaderCallback([__scan_ctx](HttpSession & session)
+ session.SetRequestHeaderCallback([__scan_ctx](HttpSession &session)
{
auto __scan_ctx_stack = __scan_ctx;
__scan_ctx_stack->ScanRequestHeader(&session);
});
- session.SetRequestBodyCallback([__scan_ctx](HttpSession & session)
+ session.SetRequestBodyCallback([__scan_ctx](HttpSession &session)
{
auto __scan_ctx_stack = __scan_ctx;
__scan_ctx->ScanRequestBody(&session);
});
- session.SetResponseHeaderCallback([__scan_ctx](HttpSession & session)
+ session.SetResponseHeaderCallback([__scan_ctx](HttpSession &session)
{
auto __scan_ctx_stack = __scan_ctx;
__scan_ctx->ScanResponseHeader(&session);
});
- session.SetResponseBodyCallback([__scan_ctx](HttpSession & session)
+ session.SetResponseBodyCallback([__scan_ctx](HttpSession &session)
{
auto __scan_ctx_stack = __scan_ctx;
__scan_ctx->ScanResponseBody(&session);
@@ -93,6 +90,30 @@ void HttpScan::handlerConnectionCreate(HttpConnection &ct)
/* 不设置SessionClose的回调函数,相应的逻辑在HttpScanSession的析构函数中处理 */
ct.SetSessionCloseCallback(nullptr);
+}
+
+void HttpScan::handlerConnectionClose(HttpConnection &ct)
+{
+ return;
+}
+
+int HttpScan::connection_bypass_scan()
+{
+ return 0;
+}
+
+int HttpScan::connection_bypass_do_action()
+{
+ return 0;
+}
+
+std::unique_ptr<HttpScan> HttpScan::HttpScanFactory(struct tfe_instance *instance, struct tfe_config *config)
+{
+ std::unique_ptr<HttpScan> __this_ptr = std::make_unique<HttpScan>(instance, config);
+
+
+
+ return std::move(__this_ptr);
};
HttpScanSession::HttpScanSession(const HttpScan &httpscan_module) :
@@ -107,13 +128,13 @@ HttpScanSession::~HttpScanSession()
void HttpScanSession::ScanRequestHeader(HttpSession *http_session_ctx)
{
- auto & http_request = http_session_ctx->request();
+ auto &http_request = http_session_ctx->request();
int dummy[MAAT_SCAN_RESULT_];
/* 扫描IP地址,获取连接对应的四元组 */
- const auto & connection = http_session_ctx->connection();
- const auto * sockaddr_src = connection.SockAddrSource();
- const auto * sockaddr_dst = connection.SockAddrDest();
+ const auto &connection = http_session_ctx->connection();
+ const auto *sockaddr_src = connection.SockAddrSource();
+ const auto *sockaddr_dst = connection.SockAddrDest();
/* 转换为Sapp中的四元组结构体 */
auto sapp_tuple4_ptr = sockaddr_to_sapp_ipaddr(sockaddr_src, sockaddr_dst);
@@ -129,7 +150,7 @@ void HttpScanSession::ScanRequestHeader(HttpSession *http_session_ctx)
return hit_scan_error();
/* 扫描HTTP URL */
- const auto & __url = http_request.Url();
+ const auto &__url = http_request.Url();
nr_maat_scan_result_ = Maat_full_scan_string(httpscan_module_ref_.maat_feather_ref,
httpscan_module_ref_.table_id_ctrl_http_url, CHARSET_UTF8, __url.c_str(), (int) __url.length(),
@@ -141,7 +162,7 @@ void HttpScanSession::ScanRequestHeader(HttpSession *http_session_ctx)
return hit_scan_error();
/* 未命中HTTP URL,继续扫描其他HTTP头部字段 */
- http_request.ForEachHeader([this, http_session_ctx](const std::string & field, const std::string & value)
+ http_request.ForEachHeader([this, http_session_ctx](const std::string &field, const std::string &value)
{
/* 增强字符串表,设置区域字段,即Header字段 */
int ret = Maat_set_scan_status(httpscan_module_ref_.maat_feather_ref, &maat_scan_mid_,
@@ -192,9 +213,9 @@ void HttpScanSession::hit_config_and_do_action(HttpSession *http_session_ctx)
if (maat_scan_result_[i].action <= action_type) do_action_id = i;
}
- Maat_rule_t * hit_maat_rule = &maat_scan_result_[do_action_id];
- auto __action_type = (enum HttpActionType)hit_maat_rule->action;
- const char * __action_string = hit_maat_rule->service_defined;
+ Maat_rule_t *hit_maat_rule = &maat_scan_result_[do_action_id];
+ auto __action_type = (enum HttpActionType) hit_maat_rule->action;
+ const char *__action_string = hit_maat_rule->service_defined;
/* 创建HttpAction的对象 */
auto action_object = HttpActionFactory(__action_type, __action_string);
@@ -204,25 +225,25 @@ void HttpScanSession::hit_config_and_do_action(HttpSession *http_session_ctx)
action_object->service_id(hit_maat_rule->service_id);
/* 替换HttpSession的事件处理函数,以后的事件由HttpAction处理 */
- http_session_ctx->SetRequestHeaderCallback([action_object](HttpSession & session)
+ http_session_ctx->SetRequestHeaderCallback([action_object](HttpSession &session)
{
auto __action_object = action_object;
__action_object->OnRequestHeader(&session);
});
- http_session_ctx->SetRequestBodyCallback([action_object](HttpSession & session)
+ http_session_ctx->SetRequestBodyCallback([action_object](HttpSession &session)
{
auto __action_object = action_object;
__action_object->OnRequestBody(&session);
});
- http_session_ctx->SetResponseHeaderCallback([action_object](HttpSession & session)
+ http_session_ctx->SetResponseHeaderCallback([action_object](HttpSession &session)
{
auto __action_object = action_object;
__action_object->OnResponseHeader(&session);
});
- http_session_ctx->SetResponseBodyCallback([action_object](HttpSession & session)
+ http_session_ctx->SetResponseBodyCallback([action_object](HttpSession &session)
{
auto __action_object = action_object;
__action_object->OnResponseBody(&session);
@@ -232,21 +253,10 @@ void HttpScanSession::hit_config_and_do_action(HttpSession *http_session_ctx)
log_dbg_printf("hit rule: service_id = %d, config_id = %d, action = %d\n",
hit_maat_rule->service_id, hit_maat_rule->config_id, hit_maat_rule->action);
- if (hit_maat_rule->do_blacklist)
- {
-
- }
-
- if (hit_maat_rule->do_log)
- {
-
- }
-
return;
}
void HttpScanSession::hit_scan_error()
{
return;
-}
-#pragma clang diagnostic pop \ No newline at end of file
+} \ No newline at end of file
diff --git a/src/httpscan.h b/src/httpscan.h
index 2665084..bef19ae 100644
--- a/src/httpscan.h
+++ b/src/httpscan.h
@@ -20,7 +20,6 @@ class HttpScan
public:
HttpScan(struct tfe_instance * instance, struct tfe_config *config);
~HttpScan() = default;
-
void handlerConnectionCreate(HttpConnection & ct);
void handlerConnectionClose(HttpConnection & ct);
diff --git a/src/logger.cc b/src/logger.cc
index eba741d..17cec5e 100644
--- a/src/logger.cc
+++ b/src/logger.cc
@@ -8,6 +8,7 @@ extern "C"
#include "logger.h"
static std::vector<std::string> g_structlogger_topic;
+std::vector<std::string> StructLoggerTopicRegister::topic_;
void StructLogger::Log(const std::string &topic, Json::Value &struct_log)
{
diff --git a/src/main.cc b/src/main.cc
index 65486af..f5882f0 100644
--- a/src/main.cc
+++ b/src/main.cc
@@ -48,6 +48,10 @@
#include <openssl/x509.h>
#include "httpscan.h"
+#include "compat.h"
+
+#include "easylogging++.h"
+INITIALIZE_EASYLOGGINGPP
/*
* Print version information to stderr.
@@ -263,6 +267,7 @@ oom_die(const char *argv0)
}
struct tfe_instance * g_tfe_instance = new tfe_instance;
+struct tfe_config * g_tfe_config = nullptr;
/*
* Main entry point.
@@ -281,11 +286,15 @@ main(int argc, char *argv[])
argv0 = argv[0];
opts = tfe_config_new();
- if (nat_getdefaultname()) {
+ g_tfe_config = opts;
+
+ if (nat_getdefaultname())
+ {
natengine = strdup(nat_getdefaultname());
if (!natengine)
oom_die(argv0);
- } else {
+ } else
+ {
natengine = NULL;
}
@@ -571,6 +580,8 @@ main(int argc, char *argv[])
free(opts->contentlog_basedir);
if (opts->contentlog)
free(opts->contentlog);
+
+#if 0
if (log_content_split_pathspec(optarg, &lhs,
&rhs) == -1) {
fprintf(stderr, "%s: Failed to split "
@@ -580,6 +591,8 @@ main(int argc, char *argv[])
strerror(errno), errno);
exit(EXIT_FAILURE);
}
+#endif
+
/* eliminate %% from lhs */
for (p = q = lhs; *p; p++, q++) {
if (q < p)
@@ -666,10 +679,12 @@ main(int argc, char *argv[])
case 'd':
opts->detach = 1;
break;
+#if 0
case 'D':
log_dbg_mode(LOG_DBG_MODE_ERRLOG);
opts->debug = 1;
break;
+#endif
case 'V':
main_version();
exit(EXIT_SUCCESS);
@@ -741,14 +756,6 @@ main(int argc, char *argv[])
exit(EXIT_FAILURE);
}
}
-#ifdef __APPLE__
- if (opts->dropuser && !!strcmp(opts->dropuser, "root") &&
- nat_used("pf")) {
- fprintf(stderr, "%s: cannot use 'pf' proxyspec with -u due "
- "to Apple bug\n", argv0);
- exit(EXIT_FAILURE);
- }
-#endif /* __APPLE__ */
/* prevent multiple instances running */
if (opts->pidfile) {
@@ -869,10 +876,14 @@ main(int argc, char *argv[])
fprintf(stderr, "%s: failed to preinit cachemgr.\n", argv0);
exit(EXIT_FAILURE);
}
+
+#if 0
if (log_preinit(opts) == -1) {
fprintf(stderr, "%s: failed to preinit logging.\n", argv0);
exit(EXIT_FAILURE);
}
+#endif
+
if (nat_preinit() == -1) {
fprintf(stderr, "%s: failed to preinit NAT lookup.\n", argv0);
exit(EXIT_FAILURE);
@@ -900,7 +911,11 @@ main(int argc, char *argv[])
argv0, strerror(errno));
exit(EXIT_FAILURE);
}
+
+#if 0
log_err_mode(LOG_ERR_MODE_SYSLOG);
+#endif
+
}
if (opts->pidfile && (sys_pidf_write(pidfd) == -1)) {
@@ -909,7 +924,8 @@ main(int argc, char *argv[])
return -1;
}
- g_tfe_instance->http_scan_module = new HttpScan(g_tfe_instance, opts);
+ g_tfe_instance->http_module = std::make_unique<Http>(g_tfe_instance, g_tfe_config);
+ g_tfe_instance->http_scan_module = std::make_unique<HttpScan>(g_tfe_instance, g_tfe_config);
/* Fork into parent monitor process and (potentially unprivileged)
* child process doing the actual work. We request 3 privsep client
@@ -949,12 +965,16 @@ main(int argc, char *argv[])
goto out_sslreinit_failed;
}
+#if 0
/* Post-privdrop/chroot/detach initialization, thread spawning */
if (log_init(opts, proxy, clisock[1], clisock[2]) == -1) {
fprintf(stderr, "%s: failed to init log facility: %s\n",
argv0, strerror(errno));
goto out_log_failed;
}
+
+#endif
+
if (cachemgr_init() == -1) {
log_err_printf("Failed to init cache manager.\n");
goto out_cachemgr_failed;
@@ -972,7 +992,9 @@ main(int argc, char *argv[])
out_nat_failed:
cachemgr_fini();
out_cachemgr_failed:
+#if 0
log_fini();
+#endif
out_sslreinit_failed:
out_log_failed:
out_parent:
diff --git a/src/opts.h b/src/opts.h
index 5ff3ac1..aec7064 100644
--- a/src/opts.h
+++ b/src/opts.h
@@ -37,6 +37,7 @@
#include <sys/socket.h>
#include <Maat_rule.h>
#include <string>
+#include <memory>
class HttpScan;
class Http;
@@ -70,9 +71,9 @@ struct tfe_instance
void * maat_logger;
/* HTTPSCAN */
- HttpScan * http_scan_module;
+ std::unique_ptr<HttpScan> http_scan_module;
/* Http */
- Http * http_module;
+ std::unique_ptr<Http> http_module;
};
struct tfe_maat_config
diff --git a/src/proxy.cc b/src/proxy.cc
index 93bd621..80ce3fd 100644
--- a/src/proxy.cc
+++ b/src/proxy.cc
@@ -51,22 +51,152 @@
#include <event2/bufferevent_ssl.h>
#include <event2/buffer.h>
#include <event2/thread.h>
+#include <sys/un.h>
+#include <cassert>
/*
* Proxy engine, built around libevent 2.x.
*/
-static int signals[] = { SIGTERM, SIGQUIT, SIGHUP, SIGINT, SIGPIPE, SIGUSR1 };
+#define TFE_STRING_MAX 2048
+#define TFE_BACKLOG_DEFAULT 20
+
+class ForgeSocketListener
+{
+public:
+ explicit ForgeSocketListener(struct event_base *evbase, const std::string &str_unix_domain);
+ virtual ~ForgeSocketListener();
+
+ using fds_arrive_cb_t = std::function<void(int fd1, int fd2)>;
+ void SetFdsArriveCallback(fds_arrive_cb_t cb) {}
+
+private:
+ struct event_base *ev_base_{nullptr};
+ struct evconnlistener *ev_listener_{nullptr};
+ std::map<evutil_socket_t, std::unique_ptr<Event>> ev_lookup_;
+ fds_arrive_cb_t fds_arrive_cb_;
+
+private:
+ void EventCallback(evutil_socket_t fd, short what);
+
+private:
+ /* 回调函数,listener发生错误时回调 */
+ static void __listener_cb_error(struct evconnlistener *listener, void *user);
+ /* 回调函数,listener建立新的unix连接,即处理KNI启动的事件 */
+ static void __listener_cb_new_connection(struct evconnlistener *listener, evutil_socket_t fd,
+ struct sockaddr *sk_addr, int sk_len, void *user);
+};
+
+ForgeSocketListener::ForgeSocketListener(struct event_base *evbase, const std::string &str_unix_domain) : ev_base_(
+ evbase)
+{
+ struct sockaddr_un __sockaddr_un{.sun_family = AF_UNIX};
+ str_unix_domain.copy(__sockaddr_un.sun_path, sizeof(__sockaddr_un.sun_path), 0);
+
+ ev_listener_ = evconnlistener_new_bind(ev_base_, __listener_cb_new_connection, this, 0,
+ TFE_BACKLOG_DEFAULT, static_cast<struct sockaddr *>(&__sockaddr_un), sizeof(__sockaddr_un));
+
+ if (ev_listener_ == nullptr)
+ {
+ throw std::runtime_error(string_format("Failed at create evconnlistener for unix domain socket: %s",
+ str_unix_domain.c_str()));
+ }
+
+ return;
+}
+
+ForgeSocketListener::~ForgeSocketListener()
+{
+ if (ev_listener_ != nullptr) evconnlistener_free(ev_listener_);
+}
+
+void ForgeSocketListener::__listener_cb_new_connection(struct evconnlistener *listener, evutil_socket_t fd,
+ struct sockaddr *sk_addr, int sk_len, void *user)
+{
+ auto *__this_ptr = static_cast<ForgeSocketListener *>(user);
+ std::unique_ptr<Event> ev_ptr = std::make_unique<Event>();
+
+ ev_ptr->Init(__this_ptr->ev_base_, fd, EV_READ, [__this_ptr](evutil_socket_t fd, short what)
+ {
+ __this_ptr->EventCallback(fd, what);
+ });
+
+ __this_ptr->ev_lookup_[fd] = std::move(ev_ptr);
+ return;
+}
+
+void ForgeSocketListener::__listener_cb_error(struct evconnlistener *listener, void *user)
+{
+ return;
+}
+
+void ForgeSocketListener::EventCallback(evutil_socket_t fd, short what)
+{
+ assert(what & EV_READ);
+ assert(fds_arrive_cb_ != nullptr);
+
+ /* 使用IOVEC,接收KNI传来的文件描述符
+ * 这是一种特殊的文件描述符传递技巧,可以在多进程之间共享同一个Socket句柄
+ */
+ constexpr static auto __TRANS_FDS_MAX = 2;
+ constexpr static auto __CONTROLLEN = CMSG_SPACE(__TRANS_FDS_MAX * sizeof(int));
+
+ struct iovec __iovec[1];
+ char __cmptr[__CONTROLLEN];
+
+ struct msghdr __msghdr =
+ {
+ .msg_iov = __iovec,
+ .msg_iovlen = 1,
+ .msg_name = nullptr,
+ .msg_namelen = 0,
+ .msg_control = static_cast<void *>(__cmptr),
+ .msg_controllen = __CONTROLLEN
+ };
+
+ ssize_t rd = recvmsg(fd, &__msghdr, 0);
+
+ /* fd的常规套路 */
+ if (rd < 0 && errno == EWOULDBLOCK)
+ {
+ return;
+ }
+ else if (rd < 0)
+ {
+ PLOG(ERROR) << string_format("Forge socket connection breaked, conn fd = %d", fd);
+ goto __close_this_connection;
+ }
+ else if (rd == 0)
+ {
+ PLOG(INFO) << string_format("Forge socket connection closed, conn fd = %d", fd);
+ goto __close_this_connection;
+ }
+
+ struct cmsghdr * __cmsghdr = CMSG_FIRSTHDR(&__msghdr);
+ assert(__cmsghdr != nullptr);
+
+ /* 接收到的FD对,调用用户注册函数 */
+ int * __fds = (int *)(CMSG_DATA(__cmsghdr));
+
+ LOG(DEBUG) << string_format("Forge Socket FD recieved, fds[0] = %d, fds[1] = %d", __fds[0], __fds[1]);
+ fds_arrive_cb_(__fds[0], __fds[1]);
+
+__close_this_connection:
+ ev_lookup_.erase(fd);
+ return;
+}
+
+static int signals[] = {SIGTERM, SIGQUIT, SIGHUP, SIGINT, SIGPIPE, SIGUSR1};
struct proxy_ctx
{
tfe_thread_manager_ctx *thrmgr;
- struct event_base *evbase;
- struct event *sev[sizeof(signals)/sizeof(int)];
- struct event *gcev;
- struct proxy_listener_ctx *lctx;
- struct tfe_config *opts;
+ struct event_base *evbase;
+ struct event *sev[sizeof(signals) / sizeof(int)];
+ struct event *gcev;
+ struct proxy_listener_ctx *lctx;
+ struct tfe_config *opts;
};
/*
@@ -75,29 +205,27 @@ struct proxy_ctx
typedef struct proxy_listener_ctx
{
tfe_thread_manager_ctx *thrmgr;
- struct proxyspec *spec;
- struct tfe_config *opts;
- struct evconnlistener *evcl;
- struct proxy_listener_ctx *next;
-
+ struct proxyspec *spec;
+ struct tfe_config *opts;
+ struct evconnlistener *evcl;
+ struct proxy_listener_ctx *next;
} proxy_listener_ctx_t;
static proxy_listener_ctx_t *
proxy_listener_ctx_new(tfe_thread_manager_ctx *thrmgr, proxyspec *spec,
- tfe_config *opts) MALLOC;
+ tfe_config *opts) MALLOC;
-static proxy_listener_ctx_t *
-proxy_listener_ctx_new(tfe_thread_manager_ctx *thrmgr, proxyspec *spec,
- tfe_config *opts)
+static proxy_listener_ctx_t * proxy_listener_ctx_new(
+ tfe_thread_manager_ctx *thrmgr, proxyspec *spec, tfe_config *opts)
{
- proxy_listener_ctx_t *ctx = (proxy_listener_ctx_t *)malloc(sizeof(proxy_listener_ctx_t));
- if (!ctx)
- return NULL;
- memset(ctx, 0, sizeof(proxy_listener_ctx_t));
- ctx->thrmgr = thrmgr;
- ctx->spec = spec;
- ctx->opts = opts;
- return ctx;
+ proxy_listener_ctx_t *ctx = (proxy_listener_ctx_t *) malloc(sizeof(proxy_listener_ctx_t));
+ if (!ctx)
+ return NULL;
+ memset(ctx, 0, sizeof(proxy_listener_ctx_t));
+ ctx->thrmgr = thrmgr;
+ ctx->spec = spec;
+ ctx->opts = opts;
+ return ctx;
}
static void
@@ -105,13 +233,15 @@ proxy_listener_ctx_free(proxy_listener_ctx_t *ctx) NONNULL(1);
static void
proxy_listener_ctx_free(proxy_listener_ctx_t *ctx)
{
- if (ctx->evcl) {
- evconnlistener_free(ctx->evcl);
- }
- if (ctx->next) {
- proxy_listener_ctx_free(ctx->next);
- }
- free(ctx);
+ if (ctx->evcl)
+ {
+ evconnlistener_free(ctx->evcl);
+ }
+ if (ctx->next)
+ {
+ proxy_listener_ctx_free(ctx->next);
+ }
+ free(ctx);
}
/*
@@ -119,14 +249,12 @@ proxy_listener_ctx_free(proxy_listener_ctx_t *ctx)
*/
static void
proxy_listener_acceptcb(UNUSED struct evconnlistener *listener,
- evutil_socket_t fd,
- struct sockaddr *peeraddr, int peeraddrlen,
- void *arg)
+ evutil_socket_t fd,
+ struct sockaddr *peeraddr, int peeraddrlen,
+ void *arg)
{
- proxy_listener_ctx_t *cfg = arg;
-
- pxy_conn_setup(fd, peeraddr, peeraddrlen, cfg->thrmgr,
- cfg->spec, cfg->opts);
+ proxy_listener_ctx_t *cfg = (proxy_listener_ctx_t *) arg;
+ pxy_conn_setup(fd, peeraddr, peeraddrlen, cfg->thrmgr, cfg->spec, cfg->opts);
}
/*
@@ -135,11 +263,11 @@ proxy_listener_acceptcb(UNUSED struct evconnlistener *listener,
static void
proxy_listener_errorcb(struct evconnlistener *listener, UNUSED void *ctx)
{
- struct event_base *evbase = evconnlistener_get_base(listener);
- int err = EVUTIL_SOCKET_ERROR();
- log_err_printf("Error %d on listener: %s\n", err,
- evutil_socket_error_to_string(err));
- event_base_loopbreak(evbase);
+ struct event_base *evbase = evconnlistener_get_base(listener);
+ int err = EVUTIL_SOCKET_ERROR();
+ log_err_printf("Error %d on listener: %s\n", err,
+ evutil_socket_error_to_string(err));
+ event_base_loopbreak(evbase);
}
/*
@@ -148,15 +276,15 @@ proxy_listener_errorcb(struct evconnlistener *listener, UNUSED void *ctx)
static void
proxy_debug_base(const struct event_base *ev_base)
{
- log_dbg_printf("Using libevent backend '%s'\n",
- event_base_get_method(ev_base));
-
- enum event_method_feature f;
- f = event_base_get_features(ev_base);
- log_dbg_printf("Event base supports: edge %s, O(1) %s, anyfd %s\n",
- ((f & EV_FEATURE_ET) ? "yes" : "no"),
- ((f & EV_FEATURE_O1) ? "yes" : "no"),
- ((f & EV_FEATURE_FDS) ? "yes" : "no"));
+ log_dbg_printf("Using libevent backend '%s'\n",
+ event_base_get_method(ev_base));
+
+ enum event_method_feature f;
+ f = event_base_get_features(ev_base);
+ log_dbg_printf("Event base supports: edge %s, O(1) %s, anyfd %s\n",
+ ((f & EV_FEATURE_ET) ? "yes" : "no"),
+ ((f & EV_FEATURE_O1) ? "yes" : "no"),
+ ((f & EV_FEATURE_FDS) ? "yes" : "no"));
}
/*
@@ -165,35 +293,38 @@ proxy_debug_base(const struct event_base *ev_base)
*/
static proxy_listener_ctx_t *
proxy_listener_setup(struct event_base *evbase, tfe_thread_manager_ctx *thrmgr,
- proxyspec *spec, tfe_config *opts, int clisock)
+ proxyspec *spec, tfe_config *opts, int clisock)
{
- proxy_listener_ctx_t *plc;
- int fd;
-
- if ((fd = privsep_client_opensock(clisock, spec)) == -1) {
- log_err_printf("Error opening socket: %s (%i)\n",
- strerror(errno), errno);
- return NULL;
- }
-
- plc = proxy_listener_ctx_new(thrmgr, spec, opts);
- if (!plc) {
- log_err_printf("Error creating listener context\n");
- evutil_closesocket(fd);
- return NULL;
- }
-
- plc->evcl = evconnlistener_new(evbase, proxy_listener_acceptcb,
- plc, LEV_OPT_CLOSE_ON_FREE, 1024, fd);
- if (!plc->evcl) {
- log_err_printf("Error creating evconnlistener: %s\n",
- strerror(errno));
- proxy_listener_ctx_free(plc);
- evutil_closesocket(fd);
- return NULL;
- }
- evconnlistener_set_error_cb(plc->evcl, proxy_listener_errorcb);
- return plc;
+ proxy_listener_ctx_t *plc;
+ int fd;
+
+ if ((fd = privsep_client_opensock(clisock, spec)) == -1)
+ {
+ log_err_printf("Error opening socket: %s (%i)\n",
+ strerror(errno), errno);
+ return NULL;
+ }
+
+ plc = proxy_listener_ctx_new(thrmgr, spec, opts);
+ if (!plc)
+ {
+ log_err_printf("Error creating listener context\n");
+ evutil_closesocket(fd);
+ return NULL;
+ }
+
+ plc->evcl = evconnlistener_new(evbase, proxy_listener_acceptcb,
+ plc, LEV_OPT_CLOSE_ON_FREE, 1024, fd);
+ if (!plc->evcl)
+ {
+ log_err_printf("Error creating evconnlistener: %s\n",
+ strerror(errno));
+ proxy_listener_ctx_free(plc);
+ evutil_closesocket(fd);
+ return NULL;
+ }
+ evconnlistener_set_error_cb(plc->evcl, proxy_listener_errorcb);
+ return plc;
}
/*
@@ -202,37 +333,36 @@ proxy_listener_setup(struct event_base *evbase, tfe_thread_manager_ctx *thrmgr,
static void
proxy_signal_cb(evutil_socket_t fd, UNUSED short what, void *arg)
{
- proxy_ctx_t *ctx = arg;
+ proxy_ctx_t *ctx = arg;
- if (OPTS_DEBUG(ctx->opts)) {
- log_dbg_printf("Received signal %i\n", fd);
- }
+ if (OPTS_DEBUG(ctx->opts))
+ {
+ log_dbg_printf("Received signal %i\n", fd);
+ }
- switch(fd) {
- case SIGTERM:
- case SIGQUIT:
- case SIGINT:
- case SIGHUP:
- proxy_loopbreak(ctx);
- break;
+ switch (fd)
+ {
+ case SIGTERM:
+ case SIGQUIT:
+ case SIGINT:
+ case SIGHUP: proxy_loopbreak(ctx);
+ break;
#if 0
- case SIGUSR1:
- if (log_reopen() == -1) {
- log_err_printf("Warning: Failed to reopen logs\n");
- } else {
- log_dbg_printf("Reopened log files\n");
- }
- break;
+ case SIGUSR1:
+ if (log_reopen() == -1) {
+ log_err_printf("Warning: Failed to reopen logs\n");
+ } else {
+ log_dbg_printf("Reopened log files\n");
+ }
+ break;
#endif
- case SIGPIPE:
- log_err_printf("Warning: Received SIGPIPE; ignoring.\n");
- break;
- default:
- log_err_printf("Warning: Received unexpected signal %i\n", fd);
- break;
- }
+ case SIGPIPE: log_err_printf("Warning: Received SIGPIPE; ignoring.\n");
+ break;
+ default: log_err_printf("Warning: Received unexpected signal %i\n", fd);
+ break;
+ }
}
/*
@@ -241,15 +371,15 @@ proxy_signal_cb(evutil_socket_t fd, UNUSED short what, void *arg)
static void
proxy_gc_cb(UNUSED evutil_socket_t fd, UNUSED short what, void *arg)
{
- proxy_ctx_t *ctx = arg;
+ proxy_ctx_t *ctx = (proxy_ctx_t *) arg;
- if (OPTS_DEBUG(ctx->opts))
- log_dbg_printf("Garbage collecting caches started.\n");
+ if (OPTS_DEBUG(ctx->opts))
+ log_dbg_printf("Garbage collecting caches started.\n");
- cachemgr_gc();
+ cachemgr_gc();
- if (OPTS_DEBUG(ctx->opts))
- log_dbg_printf("Garbage collecting caches done.\n");
+ if (OPTS_DEBUG(ctx->opts))
+ log_dbg_printf("Garbage collecting caches done.\n");
}
/*
@@ -257,122 +387,135 @@ proxy_gc_cb(UNUSED evutil_socket_t fd, UNUSED short what, void *arg)
* Socket clisock is the privsep client socket used for binding to ports.
* Returns ctx on success, or NULL on error.
*/
-proxy_ctx_t *
-proxy_new(tfe_config *opts, int clisock)
+proxy_ctx_t *proxy_new(tfe_config *opts, int clisock)
{
- proxy_listener_ctx_t *head;
- proxy_ctx_t *ctx;
- struct evdns_base *dnsbase;
- int rc;
+ proxy_listener_ctx_t *head;
+ proxy_ctx_t *ctx;
+ struct evdns_base *dnsbase;
+ int rc;
- struct timeval gc_delay = {60, 0};
+ struct timeval gc_delay = {60, 0};
- /* adds locking, only required if accessed from separate threads */
- evthread_use_pthreads();
+ /* adds locking, only required if accessed from separate threads */
+ evthread_use_pthreads();
#ifndef PURIFY
- if (OPTS_DEBUG(opts)) {
- event_enable_debug_mode();
- }
+ if (OPTS_DEBUG(opts))
+ {
+ event_enable_debug_mode();
+ }
#endif /* PURIFY */
- ctx = malloc(sizeof(proxy_ctx_t));
- if (!ctx) {
- log_err_printf("Error allocating memory\n");
- goto leave0;
- }
- memset(ctx, 0, sizeof(proxy_ctx_t));
-
- ctx->opts = opts;
- ctx->evbase = event_base_new();
- if (!ctx->evbase) {
- log_err_printf("Error getting event base\n");
- goto leave1;
- }
-
- if (tfe_config_has_dns_spec(opts)) {
- /* create a dnsbase here purely for being able to test parsing
- * resolv.conf while we can still alert the user about it. */
- dnsbase = evdns_base_new(ctx->evbase, 0);
- if (!dnsbase) {
- log_err_printf("Error creating dns event base\n");
- goto leave1b;
- }
- rc = evdns_base_resolv_conf_parse(dnsbase, DNS_OPTIONS_ALL,
- "/etc/resolv.conf");
- evdns_base_free(dnsbase, 0);
- if (rc != 0) {
- log_err_printf("evdns cannot parse resolv.conf: "
- "%s (%d)\n",
- rc == 1 ? "failed to open file" :
- rc == 2 ? "failed to stat file" :
- rc == 3 ? "file too large" :
- rc == 4 ? "out of memory" :
- rc == 5 ? "short read from file" :
- rc == 6 ? "no nameservers in file" :
- "unknown error", rc);
- goto leave1b;
- }
- }
-
- if (OPTS_DEBUG(opts)) {
- proxy_debug_base(ctx->evbase);
- }
-
- ctx->thrmgr = tfe_thread_manager_new(opts);
- if (!ctx->thrmgr) {
- log_err_printf("Error creating thread manager\n");
- goto leave1b;
- }
-
- head = ctx->lctx = NULL;
- for (proxyspec *spec = opts->spec; spec; spec = spec->next) {
- head = proxy_listener_setup(ctx->evbase, ctx->thrmgr,
- spec, opts, clisock);
- if (!head)
- goto leave2;
- head->next = ctx->lctx;
- ctx->lctx = head;
- }
-
- for (size_t i = 0; i < (sizeof(signals) / sizeof(int)); i++) {
- ctx->sev[i] = evsignal_new(ctx->evbase, signals[i],
- proxy_signal_cb, ctx);
- if (!ctx->sev[i])
- goto leave3;
- evsignal_add(ctx->sev[i], NULL);
- }
-
- ctx->gcev = event_new(ctx->evbase, -1, EV_PERSIST, proxy_gc_cb, ctx);
- if (!ctx->gcev)
- goto leave4;
- evtimer_add(ctx->gcev, &gc_delay);
-
- privsep_client_close(clisock);
- return ctx;
+ ctx = malloc(sizeof(proxy_ctx_t));
+ if (!ctx)
+ {
+ log_err_printf("Error allocating memory\n");
+ goto leave0;
+ }
+ memset(ctx, 0, sizeof(proxy_ctx_t));
+
+ ctx->opts = opts;
+ ctx->evbase = event_base_new();
+ if (!ctx->evbase)
+ {
+ log_err_printf("Error getting event base\n");
+ goto leave1;
+ }
+
+ if (tfe_config_has_dns_spec(opts))
+ {
+ /* create a dnsbase here purely for being able to test parsing
+ * resolv.conf while we can still alert the user about it. */
+ dnsbase = evdns_base_new(ctx->evbase, 0);
+ if (!dnsbase)
+ {
+ log_err_printf("Error creating dns event base\n");
+ goto leave1b;
+ }
+ rc = evdns_base_resolv_conf_parse(dnsbase, DNS_OPTIONS_ALL,
+ "/etc/resolv.conf");
+ evdns_base_free(dnsbase, 0);
+ if (rc != 0)
+ {
+ log_err_printf("evdns cannot parse resolv.conf: "
+ "%s (%d)\n",
+ rc == 1 ? "failed to open file" :
+ rc == 2 ? "failed to stat file" :
+ rc == 3 ? "file too large" :
+ rc == 4 ? "out of memory" :
+ rc == 5 ? "short read from file" :
+ rc == 6 ? "no nameservers in file" :
+ "unknown error", rc);
+ goto leave1b;
+ }
+ }
+
+ if (OPTS_DEBUG(opts))
+ {
+ proxy_debug_base(ctx->evbase);
+ }
+
+ ctx->thrmgr = tfe_thread_manager_new(opts);
+ if (!ctx->thrmgr)
+ {
+ log_err_printf("Error creating thread manager\n");
+ goto leave1b;
+ }
+
+ head = ctx->lctx = NULL;
+ for (proxyspec *spec = opts->spec; spec; spec = spec->next)
+ {
+ head = proxy_listener_setup(ctx->evbase, ctx->thrmgr,
+ spec, opts, clisock);
+ if (!head)
+ goto leave2;
+ head->next = ctx->lctx;
+ ctx->lctx = head;
+ }
+
+ for (size_t i = 0; i < (sizeof(signals) / sizeof(int)); i++)
+ {
+ ctx->sev[i] = evsignal_new(ctx->evbase, signals[i],
+ proxy_signal_cb, ctx);
+ if (!ctx->sev[i])
+ goto leave3;
+ evsignal_add(ctx->sev[i], NULL);
+ }
+
+ ctx->gcev = event_new(ctx->evbase, -1, EV_PERSIST, proxy_gc_cb, ctx);
+ if (!ctx->gcev)
+ goto leave4;
+ evtimer_add(ctx->gcev, &gc_delay);
+
+ privsep_client_close(clisock);
+ return ctx;
leave4:
- if (ctx->gcev) {
- event_free(ctx->gcev);
- }
+ if (ctx->gcev)
+ {
+ event_free(ctx->gcev);
+ }
leave3:
- for (size_t i = 0; i < (sizeof(ctx->sev) / sizeof(ctx->sev[0])); i++) {
- if (ctx->sev[i]) {
- event_free(ctx->sev[i]);
- }
- }
+ for (size_t i = 0; i < (sizeof(ctx->sev) / sizeof(ctx->sev[0])); i++)
+ {
+ if (ctx->sev[i])
+ {
+ event_free(ctx->sev[i]);
+ }
+ }
leave2:
- if (ctx->lctx) {
- proxy_listener_ctx_free(ctx->lctx);
- }
+ if (ctx->lctx)
+ {
+ proxy_listener_ctx_free(ctx->lctx);
+ }
tfe_thread_manager_free(ctx->thrmgr);
leave1b:
- event_base_free(ctx->evbase);
+ event_base_free(ctx->evbase);
leave1:
- free(ctx);
+ free(ctx);
leave0:
- return NULL;
+ return NULL;
}
/*
@@ -382,25 +525,30 @@ leave0:
void
proxy_run(proxy_ctx_t *ctx)
{
- if (ctx->opts->detach) {
- event_reinit(ctx->evbase);
- }
+ if (ctx->opts->detach)
+ {
+ event_reinit(ctx->evbase);
+ }
#ifndef PURIFY
- if (OPTS_DEBUG(ctx->opts)) {
- event_base_dump_events(ctx->evbase, stderr);
- }
+ if (OPTS_DEBUG(ctx->opts))
+ {
+ event_base_dump_events(ctx->evbase, stderr);
+ }
#endif /* PURIFY */
- if (tfe_thread_manager_run(ctx->thrmgr) == -1) {
- log_err_printf("Failed to start thread manager\n");
- return;
- }
- if (OPTS_DEBUG(ctx->opts)) {
- log_dbg_printf("Starting main event loop.\n");
- }
- event_base_dispatch(ctx->evbase);
- if (OPTS_DEBUG(ctx->opts)) {
- log_dbg_printf("Main event loop stopped.\n");
- }
+ if (tfe_thread_manager_run(ctx->thrmgr) == -1)
+ {
+ log_err_printf("Failed to start thread manager\n");
+ return;
+ }
+ if (OPTS_DEBUG(ctx->opts))
+ {
+ log_dbg_printf("Starting main event loop.\n");
+ }
+ event_base_dispatch(ctx->evbase);
+ if (OPTS_DEBUG(ctx->opts))
+ {
+ log_dbg_printf("Main event loop stopped.\n");
+ }
}
/*
@@ -409,7 +557,7 @@ proxy_run(proxy_ctx_t *ctx)
void
proxy_loopbreak(proxy_ctx_t *ctx)
{
- event_base_loopbreak(ctx->evbase);
+ event_base_loopbreak(ctx->evbase);
}
/*
@@ -418,24 +566,30 @@ proxy_loopbreak(proxy_ctx_t *ctx)
void
proxy_free(proxy_ctx_t *ctx)
{
- if (ctx->gcev) {
- event_free(ctx->gcev);
- }
- if (ctx->lctx) {
- proxy_listener_ctx_free(ctx->lctx);
- }
- for (size_t i = 0; i < (sizeof(ctx->sev) / sizeof(ctx->sev[0])); i++) {
- if (ctx->sev[i]) {
- event_free(ctx->sev[i]);
- }
- }
- if (ctx->thrmgr) {
+ if (ctx->gcev)
+ {
+ event_free(ctx->gcev);
+ }
+ if (ctx->lctx)
+ {
+ proxy_listener_ctx_free(ctx->lctx);
+ }
+ for (size_t i = 0; i < (sizeof(ctx->sev) / sizeof(ctx->sev[0])); i++)
+ {
+ if (ctx->sev[i])
+ {
+ event_free(ctx->sev[i]);
+ }
+ }
+ if (ctx->thrmgr)
+ {
tfe_thread_manager_free(ctx->thrmgr);
- }
- if (ctx->evbase) {
- event_base_free(ctx->evbase);
- }
- free(ctx);
+ }
+ if (ctx->evbase)
+ {
+ event_base_free(ctx->evbase);
+ }
+ free(ctx);
}
/* vim: set noet ft=c: */
diff --git a/src/pxyconn.cc b/src/pxyconn.cc
index 6833865..28d9469 100644
--- a/src/pxyconn.cc
+++ b/src/pxyconn.cc
@@ -38,6 +38,7 @@
#include "url.h"
#include "compat.h"
#include "attrib.h"
+#include "http.h"
#include <netinet/in.h>
#include <stdlib.h>
@@ -76,35 +77,16 @@
static unsigned long ssl_session_context = 0x31415926;
#endif /* USE_SSL_SESSION_ID_CONTEXT */
-#ifdef HAVE_LOCAL_PROCINFO
-/* local process data - filled in iff pid != -1 */
-typedef struct pxy_conn_lproc_desc {
- struct sockaddr_storage srcaddr;
- socklen_t srcaddrlen;
-
- pid_t pid;
- uid_t uid;
- gid_t gid;
-
- /* derived log strings */
- char *exec_path;
- char *user;
- char *group;
-} pxy_conn_lproc_desc_t;
-#endif /* HAVE_LOCAL_PROCINFO */
-
#define WANT_CONNECT_LOG(ctx) ((ctx)->opts->connectlog||!(ctx)->opts->detach)
#define WANT_CONTENT_LOG(ctx) ((ctx)->opts->contentlog&&!(ctx)->passthrough)
static pxy_conn_ctx_t *
-pxy_conn_ctx_new(
- proxyspec *spec, tfe_config *opts,
- tfe_thread_manager_ctx *thrmgr, evutil_socket_t fd)
+pxy_conn_ctx_new(proxyspec *spec, tfe_config *opts, tfe_thread_manager_ctx *thrmgr, evutil_socket_t fd)
MALLOC NONNULL(1, 2, 3);
static pxy_conn_ctx_t *
pxy_conn_ctx_new(proxyspec *spec, tfe_config *opts, tfe_thread_manager_ctx *thrmgr, evutil_socket_t fd)
{
- pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *)malloc(sizeof(pxy_conn_ctx_t));
+ pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *) malloc(sizeof(pxy_conn_ctx_t));
if (!ctx) return NULL;
memset(ctx, 0, sizeof(pxy_conn_ctx_t));
@@ -127,19 +109,11 @@ pxy_conn_ctx_new(proxyspec *spec, tfe_config *opts, tfe_thread_manager_ctx *thrm
static void NONNULL(1)
pxy_conn_ctx_free(pxy_conn_ctx_t *ctx, int by_requestor)
{
-#ifdef DEBUG_PROXY
- if (OPTS_DEBUG(ctx->opts)) {
+ if (OPTS_DEBUG(ctx->opts))
+ {
log_dbg_printf("%p pxy_conn_ctx_free\n",
(void*)ctx);
}
-#endif /* DEBUG_PROXY */
- if (WANT_CONTENT_LOG(ctx) && ctx->logctx)
- {
- if (log_content_close(&ctx->logctx, by_requestor) == -1)
- {
- log_err_printf("Warning: Content log close failed\n");
- }
- }
tfe_thread_manager_detach(ctx->thrmgr, ctx->thridx);
@@ -211,6 +185,7 @@ pxy_conn_ctx_free(pxy_conn_ctx_t *ctx, int by_requestor)
{
free(ctx->sni);
}
+
free(ctx);
}
@@ -256,7 +231,8 @@ static void pxy_debug_crt(X509 *crt)
if (!(fpr = ssl_x509_fingerprint(crt, 1)))
{
log_err_printf("Warning: Error generating X509 fingerprint\n");
- } else
+ }
+ else
{
log_dbg_printf("Fingerprint: %s\n", fpr);
free(fpr);
@@ -273,27 +249,8 @@ static void
pxy_log_connect_nonhttp(pxy_conn_ctx_t *ctx)
{
char *msg;
-#ifdef HAVE_LOCAL_PROCINFO
- char *lpi = NULL;
-#endif /* HAVE_LOCAL_PROCINFO */
int rv;
-#ifdef HAVE_LOCAL_PROCINFO
- if (ctx->opts->lprocinfo) {
- rv = asprintf(&lpi, "lproc:%i:%s:%s:%s",
- ctx->lproc.pid,
- STRORDASH(ctx->lproc.user),
- STRORDASH(ctx->lproc.group),
- STRORDASH(ctx->lproc.exec_path));
- if ((rv < 0) || !lpi) {
- ctx->enomem = 1;
- goto out;
- }
- } else {
- lpi = "";
- }
-#endif /* HAVE_LOCAL_PROCINFO */
-
/*
* The following ifdef's within asprintf arguments list generates
* warnings with -Wembedded-directive on some compilers.
@@ -307,41 +264,32 @@ pxy_log_connect_nonhttp(pxy_conn_ctx_t *ctx)
" %s"
#endif /* HAVE_LOCAL_PROCINFO */
"\n",
- ctx->passthrough ? "passthrough" : "tcp",
- STRORDASH(ctx->srchost_str),
- STRORDASH(ctx->srcport_str),
- STRORDASH(ctx->dsthost_str),
- STRORDASH(ctx->dstport_str)
-#ifdef HAVE_LOCAL_PROCINFO
- , lpi
-#endif /* HAVE_LOCAL_PROCINFO */
+ ctx->passthrough ? "passthrough" : "tcp",
+ STRORDASH(ctx->srchost_str),
+ STRORDASH(ctx->srcport_str),
+ STRORDASH(ctx->dsthost_str),
+ STRORDASH(ctx->dstport_str)
);
- } else
+ }
+ else
{
rv = asprintf(&msg, "%s %s %s %s %s "
"sni:%s names:%s "
"sproto:%s:%s dproto:%s:%s "
- "origcrt:%s usedcrt:%s"
- #ifdef HAVE_LOCAL_PROCINFO
- " %s"
- #endif /* HAVE_LOCAL_PROCINFO */
- "\n",
- ctx->clienthello_found ? "upgrade" : "ssl",
- STRORDASH(ctx->srchost_str),
- STRORDASH(ctx->srcport_str),
- STRORDASH(ctx->dsthost_str),
- STRORDASH(ctx->dstport_str),
- STRORDASH(ctx->sni),
- STRORDASH(ctx->ssl_names),
- SSL_get_version(ctx->src.ssl),
- SSL_get_cipher(ctx->src.ssl),
- SSL_get_version(ctx->dst.ssl),
- SSL_get_cipher(ctx->dst.ssl),
- STRORDASH(ctx->origcrtfpr),
- STRORDASH(ctx->usedcrtfpr)
-#ifdef HAVE_LOCAL_PROCINFO
- , lpi
-#endif /* HAVE_LOCAL_PROCINFO */
+ "origcrt:%s usedcrt:%s\n",
+ ctx->clienthello_found ? "upgrade" : "ssl",
+ STRORDASH(ctx->srchost_str),
+ STRORDASH(ctx->srcport_str),
+ STRORDASH(ctx->dsthost_str),
+ STRORDASH(ctx->dstport_str),
+ STRORDASH(ctx->sni),
+ STRORDASH(ctx->ssl_names),
+ SSL_get_version(ctx->src.ssl),
+ SSL_get_cipher(ctx->src.ssl),
+ SSL_get_version(ctx->dst.ssl),
+ SSL_get_cipher(ctx->dst.ssl),
+ STRORDASH(ctx->origcrtfpr),
+ STRORDASH(ctx->usedcrtfpr)
);
}
if ((rv < 0) || !msg)
@@ -355,21 +303,12 @@ pxy_log_connect_nonhttp(pxy_conn_ctx_t *ctx)
}
if (ctx->opts->connectlog)
{
- if (log_connect_print_free(msg) == -1)
- {
- free(msg);
- log_err_printf("Warning: Connection logging failed\n");
- }
- } else
+ }
+ else
{
free(msg);
}
out:
-#ifdef HAVE_LOCAL_PROCINFO
- if (lpi && ctx->opts->lprocinfo) {
- free(lpi);
- }
-#endif /* HAVE_LOCAL_PROCINFO */
return;
}
@@ -397,17 +336,18 @@ pxy_log_connect_http(pxy_conn_ctx_t *ctx)
if (!ctx->spec->ssl)
{
rv = asprintf(&msg, "http %s %s %s %s %s %s %s %s %s %s\n",
- STRORDASH(ctx->srchost_str),
- STRORDASH(ctx->srcport_str),
- STRORDASH(ctx->dsthost_str),
- STRORDASH(ctx->dstport_str),
- STRORDASH(ctx->http_host),
- STRORDASH(ctx->http_method),
- STRORDASH(ctx->http_uri),
- STRORDASH(ctx->http_status_code),
- STRORDASH(ctx->http_content_length),
- ctx->ocsp_denied ? " ocsp:denied" : "");
- } else
+ STRORDASH(ctx->srchost_str),
+ STRORDASH(ctx->srcport_str),
+ STRORDASH(ctx->dsthost_str),
+ STRORDASH(ctx->dstport_str),
+ STRORDASH(ctx->http_host),
+ STRORDASH(ctx->http_method),
+ STRORDASH(ctx->http_uri),
+ STRORDASH(ctx->http_status_code),
+ STRORDASH(ctx->http_content_length),
+ ctx->ocsp_denied ? " ocsp:denied" : "");
+ }
+ else
{
rv = asprintf(&msg, "https %s %s %s %s %s %s %s %s %s "
"sni:%s names:%s "
@@ -417,24 +357,24 @@ pxy_log_connect_http(pxy_conn_ctx_t *ctx)
" %s"
#endif /* HAVE_LOCAL_PROCINFO */
"%s\n",
- STRORDASH(ctx->srchost_str),
- STRORDASH(ctx->srcport_str),
- STRORDASH(ctx->dsthost_str),
- STRORDASH(ctx->dstport_str),
- STRORDASH(ctx->http_host),
- STRORDASH(ctx->http_method),
- STRORDASH(ctx->http_uri),
- STRORDASH(ctx->http_status_code),
- STRORDASH(ctx->http_content_length),
- STRORDASH(ctx->sni),
- STRORDASH(ctx->ssl_names),
- SSL_get_version(ctx->src.ssl),
- SSL_get_cipher(ctx->src.ssl),
- SSL_get_version(ctx->dst.ssl),
- SSL_get_cipher(ctx->dst.ssl),
- STRORDASH(ctx->origcrtfpr),
- STRORDASH(ctx->usedcrtfpr),
- ctx->ocsp_denied ? " ocsp:denied" : "");
+ STRORDASH(ctx->srchost_str),
+ STRORDASH(ctx->srcport_str),
+ STRORDASH(ctx->dsthost_str),
+ STRORDASH(ctx->dstport_str),
+ STRORDASH(ctx->http_host),
+ STRORDASH(ctx->http_method),
+ STRORDASH(ctx->http_uri),
+ STRORDASH(ctx->http_status_code),
+ STRORDASH(ctx->http_content_length),
+ STRORDASH(ctx->sni),
+ STRORDASH(ctx->ssl_names),
+ SSL_get_version(ctx->src.ssl),
+ SSL_get_cipher(ctx->src.ssl),
+ SSL_get_version(ctx->dst.ssl),
+ SSL_get_cipher(ctx->dst.ssl),
+ STRORDASH(ctx->origcrtfpr),
+ STRORDASH(ctx->usedcrtfpr),
+ ctx->ocsp_denied ? " ocsp:denied" : "");
}
if ((rv < 0) || !msg)
{
@@ -447,12 +387,9 @@ pxy_log_connect_http(pxy_conn_ctx_t *ctx)
}
if (ctx->opts->connectlog)
{
- if (log_connect_print_free(msg) == -1)
- {
- free(msg);
- log_err_printf("Warning: Connection logging failed\n");
- }
- } else
+ }
+
+ else
{
free(msg);
}
@@ -539,7 +476,7 @@ pxy_ossl_sessget_cb(UNUSED SSL *ssl, const unsigned char *id, int idlen, int *co
#endif /* DEBUG_SESSION_CACHE */
*copy = 0; /* SSL should not increment reference count of session */
- sess = (SSL_SESSION *)cachemgr_ssess_get(id, idlen);
+ sess = (SSL_SESSION *) cachemgr_ssess_get(id, idlen);
#ifdef DEBUG_SESSION_CACHE
if (sess) {
@@ -619,7 +556,7 @@ pxy_sslctx_setoptions(SSL_CTX *sslctx, pxy_conn_ctx_t *ctx)
* Create and set up a new SSL_CTX instance for terminating SSL.
* Set up all the necessary callbacks, the certificate, the cert chain and key.
*/
-static SSL_CTX * pxy_srcsslctx_create(
+static SSL_CTX *pxy_srcsslctx_create(
pxy_conn_ctx_t *ctx, X509 *crt, STACK_OF(X509) *chain,
EVP_PKEY *key)
{
@@ -656,7 +593,8 @@ static SSL_CTX * pxy_srcsslctx_create(
if (ctx->opts->dh)
{
SSL_CTX_set_tmp_dh(sslctx, ctx->opts->dh);
- } else
+ }
+ else
{
SSL_CTX_set_tmp_dh_callback(sslctx, ssl_tmp_dh_callback);
}
@@ -667,7 +605,8 @@ static SSL_CTX * pxy_srcsslctx_create(
EC_KEY *ecdh = ssl_ec_by_name(ctx->opts->ecdhcurve);
SSL_CTX_set_tmp_ecdh(sslctx, ecdh);
EC_KEY_free(ecdh);
- } else
+ }
+ else
{
EC_KEY *ecdh = ssl_ec_by_name(NULL);
SSL_CTX_set_tmp_ecdh(sslctx, ecdh);
@@ -716,20 +655,21 @@ pxy_srccert_write_to_gendir(pxy_conn_ctx_t *ctx, X509 *crt, int is_orig)
if (is_orig)
{
rv = asprintf(&fn, "%s/%s.crt", ctx->opts->certgendir,
- ctx->origcrtfpr);
- } else
+ ctx->origcrtfpr);
+ }
+ else
{
if (!ctx->usedcrtfpr)
return -1;
rv = asprintf(&fn, "%s/%s-%s.crt", ctx->opts->certgendir,
- ctx->origcrtfpr, ctx->usedcrtfpr);
+ ctx->origcrtfpr, ctx->usedcrtfpr);
}
if (rv == -1)
{
ctx->enomem = 1;
return -1;
}
- rv = log_cert_submit(fn, crt);
+
free(fn);
return rv;
}
@@ -739,7 +679,7 @@ static void pxy_srccert_write(pxy_conn_ctx_t *ctx)
if (ctx->opts->certgen_writeall || ctx->generated_cert)
{
if (pxy_srccert_write_to_gendir(ctx,
- SSL_get_certificate(ctx->src.ssl), 0) == -1)
+ SSL_get_certificate(ctx->src.ssl), 0) == -1)
{
log_err_printf("Failed to write used certificate\n");
}
@@ -753,14 +693,14 @@ static void pxy_srccert_write(pxy_conn_ctx_t *ctx)
}
}
-static cert_t * pxy_srccert_create(pxy_conn_ctx_t *ctx)
+static cert_t *pxy_srccert_create(pxy_conn_ctx_t *ctx)
{
cert_t *cert = NULL;
if (ctx->opts->tgcrtdir)
{
if (ctx->sni)
{
- cert = (cert_t *)cachemgr_tgcrt_get(ctx->sni);
+ cert = (cert_t *) cachemgr_tgcrt_get(ctx->sni);
if (!cert)
{
char *wildcarded = ssl_wildcardify(ctx->sni);
@@ -769,7 +709,7 @@ static cert_t * pxy_srccert_create(pxy_conn_ctx_t *ctx)
ctx->enomem = 1;
return NULL;
}
- cert = (cert_t *)cachemgr_tgcrt_get(wildcarded);
+ cert = (cert_t *) cachemgr_tgcrt_get(wildcarded);
free(wildcarded);
}
if (cert && OPTS_DEBUG(ctx->opts))
@@ -784,7 +724,7 @@ static cert_t * pxy_srccert_create(pxy_conn_ctx_t *ctx)
{
if (!cert)
{
- cert = (cert_t *)cachemgr_tgcrt_get(*p);
+ cert = (cert_t *) cachemgr_tgcrt_get(*p);
}
if (!cert)
{
@@ -792,7 +732,8 @@ static cert_t * pxy_srccert_create(pxy_conn_ctx_t *ctx)
if (!wildcarded)
{
ctx->enomem = 1;
- } else
+ }
+ else
{
cert = (cert_t *) (wildcarded);
free(wildcarded);
@@ -820,7 +761,7 @@ static cert_t * pxy_srccert_create(pxy_conn_ctx_t *ctx)
if (!cert && ctx->origcrt && ctx->opts->key)
{
cert = cert_new();
- cert->crt = (X509 *)cachemgr_fkcrt_get(ctx->origcrt);
+ cert->crt = (X509 *) cachemgr_fkcrt_get(ctx->origcrt);
if (cert->crt)
{
@@ -830,11 +771,11 @@ static cert_t * pxy_srccert_create(pxy_conn_ctx_t *ctx)
{
if (OPTS_DEBUG(ctx->opts)) log_dbg_printf("Certificate cache: MISS\n");
cert->crt = ssl_x509_forge(ctx->opts->cacrt,
- ctx->opts->cakey,
- ctx->origcrt,
- ctx->opts->key,
- NULL,
- ctx->opts->crlurl);
+ ctx->opts->cakey,
+ ctx->origcrt,
+ ctx->opts->key,
+ NULL,
+ ctx->opts->crlurl);
cachemgr_fkcrt_set(ctx->origcrt, cert->crt);
}
@@ -855,7 +796,7 @@ static cert_t * pxy_srccert_create(pxy_conn_ctx_t *ctx)
{
ctx->usedcrtfpr = ssl_x509_fingerprint(cert->crt, 0);
if (!ctx->usedcrtfpr)
- ctx->enomem = 1;
+ ctx->enomem = 1;
}
return cert;
@@ -866,13 +807,13 @@ static cert_t * pxy_srccert_create(pxy_conn_ctx_t *ctx)
* destination SSL certificate.
* Returns NULL if no suitable certificate could be found.
*/
-static SSL * pxy_srcssl_create(pxy_conn_ctx_t *ctx, SSL *origssl)
+static SSL *pxy_srcssl_create(pxy_conn_ctx_t *ctx, SSL *origssl)
{
cert_t *cert;
cachemgr_dsess_set((struct sockaddr *) &ctx->addr,
- ctx->addrlen, ctx->sni,
- SSL_get0_session(origssl));
+ ctx->addrlen, ctx->sni,
+ SSL_get0_session(origssl));
ctx->origcrt = SSL_get_peer_certificate(origssl);
@@ -882,7 +823,8 @@ static SSL * pxy_srcssl_create(pxy_conn_ctx_t *ctx, SSL *origssl)
{
log_dbg_printf("===> Original server certificate:\n");
pxy_debug_crt(ctx->origcrt);
- } else
+ }
+ else
{
log_dbg_printf("===> Original server has no cert!\n");
}
@@ -908,7 +850,7 @@ static SSL * pxy_srcssl_create(pxy_conn_ctx_t *ctx, SSL *origssl)
}
SSL_CTX *sslctx = pxy_srcsslctx_create(ctx, cert->crt, cert->chain,
- cert->key);
+ cert->key);
cert_free(cert);
if (!sslctx)
{
@@ -940,7 +882,7 @@ static SSL * pxy_srcssl_create(pxy_conn_ctx_t *ctx, SSL *origssl)
*/
static int pxy_ossl_servername_cb(SSL *ssl, UNUSED int *al, void *arg)
{
- pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *)arg;
+ pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *) arg;
const char *sn;
X509 *sslcrt;
@@ -996,8 +938,8 @@ static int pxy_ossl_servername_cb(SSL *ssl, UNUSED int *al, void *arg)
"(SNI mismatch)\n");
}
newcrt = ssl_x509_forge(ctx->opts->cacrt, ctx->opts->cakey,
- sslcrt, ctx->opts->key,
- sn, ctx->opts->crlurl);
+ sslcrt, ctx->opts->key,
+ sn, ctx->opts->crlurl);
if (!newcrt)
{
ctx->enomem = 1;
@@ -1037,7 +979,7 @@ static int pxy_ossl_servername_cb(SSL *ssl, UNUSED int *al, void *arg)
}
newsslctx = pxy_srcsslctx_create(ctx, newcrt, ctx->opts->chain,
- ctx->opts->key);
+ ctx->opts->key);
if (!newsslctx)
{
X509_free(newcrt);
@@ -1047,7 +989,8 @@ static int pxy_ossl_servername_cb(SSL *ssl, UNUSED int *al, void *arg)
SSL_set_SSL_CTX(ssl, newsslctx); /* decr's old incr new refc */
SSL_CTX_free(newsslctx);
X509_free(newcrt);
- } else if (OPTS_DEBUG(ctx->opts))
+ }
+ else if (OPTS_DEBUG(ctx->opts))
{
log_dbg_printf("Certificate cache: KEEP (SNI match or "
"target mode)\n");
@@ -1110,7 +1053,7 @@ pxy_dstssl_create(pxy_conn_ctx_t *ctx)
/* session resuming based on remote endpoint address and port */
sess = (SSL_SESSION *) cachemgr_dsess_get((struct sockaddr *) &ctx->addr,
- ctx->addrlen, ctx->sni); /* new sess inst */
+ ctx->addrlen, ctx->sni); /* new sess inst */
if (sess)
{
if (OPTS_DEBUG(ctx->opts))
@@ -1151,7 +1094,8 @@ bufferevent_free_and_close_fd(struct bufferevent *bev, pxy_conn_ctx_t *ctx)
if (ssl)
{
pxy_ssl_shutdown(ctx->opts, ctx->evbase, ssl, fd);
- } else
+ }
+ else
{
evutil_closesocket(fd);
}
@@ -1176,13 +1120,14 @@ pxy_bufferevent_setup(pxy_conn_ctx_t *ctx, evutil_socket_t fd, SSL *ssl)
if (ssl)
{
bev = bufferevent_openssl_socket_new(ctx->evbase, fd, ssl,
- ((fd == -1) ? BUFFEREVENT_SSL_CONNECTING
- : BUFFEREVENT_SSL_ACCEPTING),
- BEV_OPT_DEFER_CALLBACKS);
- } else
+ ((fd == -1) ? BUFFEREVENT_SSL_CONNECTING
+ : BUFFEREVENT_SSL_ACCEPTING),
+ BEV_OPT_DEFER_CALLBACKS);
+ }
+ else
{
bev = bufferevent_socket_new(ctx->evbase, fd,
- BEV_OPT_DEFER_CALLBACKS);
+ BEV_OPT_DEFER_CALLBACKS);
}
if (!bev)
{
@@ -1198,7 +1143,7 @@ pxy_bufferevent_setup(pxy_conn_ctx_t *ctx, evutil_socket_t fd, SSL *ssl)
}
#endif /* LIBEVENT_VERSION_NUMBER >= 0x02010000 */
bufferevent_setcb(bev, pxy_bev_readcb, pxy_bev_writecb,
- pxy_bev_eventcb, ctx);
+ pxy_bev_eventcb, ctx);
bufferevent_enable(bev, EV_READ | EV_WRITE);
#ifdef DEBUG_PROXY
if (OPTS_DEBUG(ctx->opts)) {
@@ -1219,7 +1164,7 @@ static int pxy_ocsp_is_valid_uri(const char *uri, pxy_conn_ctx_t *ctx)
size_t sz_asn1;
int ret;
- buf_url = (char *)strrchr(uri, '/');
+ buf_url = (char *) strrchr(uri, '/');
if (!buf_url)
return 0;
buf_url++;
@@ -1287,7 +1232,7 @@ static void pxy_ocsp_deny(pxy_conn_ctx_t *ctx)
if (!strncasecmp(ctx->http_method, "POST", 4) &&
ctx->http_content_type &&
!strncasecmp(ctx->http_content_type,
- "application/ocsp-request", 24))
+ "application/ocsp-request", 24))
goto deny;
return;
@@ -1297,46 +1242,14 @@ deny:
if (evbuffer_get_length(inbuf) > 0)
{
- if (WANT_CONTENT_LOG(ctx))
- {
- logbuf_t *lb;
- lb = logbuf_new_alloc(evbuffer_get_length(inbuf),
- NULL, NULL);
- if (lb &&
- (evbuffer_copyout(inbuf, lb->buf, lb->sz) != -1))
- {
- if (log_content_submit(ctx->logctx, lb,
- 1/*req*/) == -1)
- {
- logbuf_free(lb);
- log_err_printf("Warning: Content log "
- "submission failed\n");
- }
- }
- }
evbuffer_drain(inbuf, evbuffer_get_length(inbuf));
}
+
bufferevent_free_and_close_fd(ctx->dst.bev, ctx);
ctx->dst.bev = NULL;
ctx->dst.closed = 1;
evbuffer_add_printf(outbuf, ocspresp);
ctx->ocsp_denied = 1;
- if (WANT_CONTENT_LOG(ctx))
- {
- logbuf_t *lb;
- lb = logbuf_new_copy(ocspresp, sizeof(ocspresp) - 1,
- NULL, NULL);
- if (lb)
- {
- if (log_content_submit(ctx->logctx, lb,
- 0/*resp*/) == -1)
- {
- logbuf_free(lb);
- log_err_printf("Warning: Content log "
- "submission failed\n");
- }
- }
- }
}
/*
@@ -1367,8 +1280,8 @@ pxy_conn_autossl_peek_and_upgrade(pxy_conn_ctx_t *ctx)
inbuf = bufferevent_get_input(ctx->src.bev);
if (evbuffer_peek(inbuf, 1024, 0, vec_out, 1))
{
- if (ssl_tls_clienthello_parse((const unsigned char *)vec_out[0].iov_base,
- vec_out[0].iov_len, 0, &chello, &ctx->sni) == 0)
+ if (ssl_tls_clienthello_parse((const unsigned char *) vec_out[0].iov_base,
+ vec_out[0].iov_len, 0, &chello, &ctx->sni) == 0)
{
if (OPTS_DEBUG(ctx->opts))
{
@@ -1390,19 +1303,20 @@ pxy_conn_autossl_peek_and_upgrade(pxy_conn_ctx_t *ctx)
return 0;
}
bufferevent_setcb(ctx->dst.bev, pxy_bev_readcb,
- pxy_bev_writecb, pxy_bev_eventcb,
- ctx);
+ pxy_bev_writecb, pxy_bev_eventcb,
+ ctx);
bufferevent_enable(ctx->dst.bev, EV_READ | EV_WRITE);
if (OPTS_DEBUG(ctx->opts))
{
log_err_printf("Replaced dst bufferevent, new "
"one is %p\n",
- (void *) ctx->dst.bev);
+ (void *) ctx->dst.bev);
}
ctx->clienthello_search = 0;
ctx->clienthello_found = 1;
return 1;
- } else
+ }
+ else
{
if (OPTS_DEBUG(ctx->opts))
{
@@ -1418,7 +1332,7 @@ static void
pxy_conn_terminate_free(pxy_conn_ctx_t *ctx, int is_requestor)
{
log_err_printf("Terminating connection%s!\n",
- ctx->enomem ? " (out of memory)" : "");
+ ctx->enomem ? " (out of memory)" : "");
if (ctx->dst.bev && !ctx->dst.closed)
{
bufferevent_free_and_close_fd(ctx->dst.bev, ctx);
@@ -1440,16 +1354,14 @@ extern int pxy_http_read_cb(pxy_conn_ctx_t *ctx, struct bufferevent *bev);
*/
static void pxy_bev_readcb(struct bufferevent *bev, void *arg)
{
- pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *)arg;
+ pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *) arg;
- pxy_conn_desc_t * conn_this = (bev == ctx->src.bev) ? &ctx->src : &ctx->dst;
- pxy_conn_desc_t * conn_other = (bev == ctx->src.bev) ? &ctx->dst : &ctx->src;
+ pxy_conn_desc_t *conn_this = (bev == ctx->src.bev) ? &ctx->src : &ctx->dst;
+ pxy_conn_desc_t *conn_other = (bev == ctx->src.bev) ? &ctx->dst : &ctx->src;
if (!ctx->connected)
{
- log_err_printf("readcb called when other end not connected - "
- "aborting.\n");
- log_exceptcb();
+ log_err_printf("readcb called when other end not connected - aborting.\n");
return;
}
@@ -1475,13 +1387,13 @@ static void pxy_bev_readcb(struct bufferevent *bev, void *arg)
if (ctx->spec->http && (bev == ctx->src.bev) && !ctx->passthrough)
{
- auto * http1_connection = reinterpret_cast<Http1Connection *>(ctx->protocol_conn_ctx);
+ auto *http1_connection = reinterpret_cast<Http1Connection *>(ctx->protocol_conn_ctx);
http1_connection->on_connection_read_request(ctx, conn_this, conn_other);
}
if (ctx->spec->http && (bev == ctx->dst.bev) && !ctx->passthrough)
{
- auto * http1_connection = reinterpret_cast<Http1Connection *>(ctx->protocol_conn_ctx);
+ auto *http1_connection = reinterpret_cast<Http1Connection *>(ctx->protocol_conn_ctx);
http1_connection->on_connection_read_response(ctx, bev);
}
@@ -1496,28 +1408,13 @@ static void pxy_bev_readcb(struct bufferevent *bev, void *arg)
if (evbuffer_get_length(inbuf) == 0)
return;
- if (WANT_CONTENT_LOG(ctx))
- {
- logbuf_t *lb;
- lb = logbuf_new_alloc(evbuffer_get_length(inbuf), NULL, NULL);
- if (lb && (evbuffer_copyout(inbuf, lb->buf, lb->sz) != -1))
- {
- if (log_content_submit(ctx->logctx, lb,
- (bev == ctx->src.bev)) == -1)
- {
- logbuf_free(lb);
- log_err_printf("Warning: Content log "
- "submission failed\n");
- }
- }
- }
evbuffer_add_buffer(outbuf, inbuf);
if (evbuffer_get_length(outbuf) >= OUTBUF_LIMIT)
{
/* temporarily disable data source;
* set an appropriate watermark. */
bufferevent_setwatermark(conn_other->bev, EV_WRITE,
- OUTBUF_LIMIT / 2, OUTBUF_LIMIT);
+ OUTBUF_LIMIT / 2, OUTBUF_LIMIT);
bufferevent_disable(bev, EV_READ);
}
}
@@ -1530,7 +1427,7 @@ static void pxy_bev_readcb(struct bufferevent *bev, void *arg)
static void
pxy_bev_writecb(struct bufferevent *bev, void *arg)
{
- pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *)arg;
+ pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *) arg;
pxy_conn_desc_t *other = (bev == ctx->src.bev) ? &ctx->dst : &ctx->src;
#ifdef DEBUG_PROXY
@@ -1568,7 +1465,7 @@ pxy_bev_writecb(struct bufferevent *bev, void *arg)
*/
static void pxy_bev_eventcb(struct bufferevent *bev, short events, void *arg)
{
- pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *)arg;
+ pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *) arg;
pxy_conn_desc_t *this_conn = (bev == ctx->src.bev) ? &ctx->src : &ctx->dst;
pxy_conn_desc_t *other_conn = (bev == ctx->src.bev) ? &ctx->dst : &ctx->src;
@@ -1636,20 +1533,21 @@ static void pxy_bev_eventcb(struct bufferevent *bev, short events, void *arg)
ctx->evbase, ctx->src.bev, ctx->src.ssl,
BUFFEREVENT_SSL_ACCEPTING,
BEV_OPT_DEFER_CALLBACKS);
+
if (ctx->src.bev)
{
bufferevent_setcb(ctx->src.bev,
- pxy_bev_readcb,
- pxy_bev_writecb,
- pxy_bev_eventcb,
- ctx);
- bufferevent_enable(ctx->src.bev,
- EV_READ | EV_WRITE);
+ pxy_bev_readcb,
+ pxy_bev_writecb,
+ pxy_bev_eventcb,
+ ctx);
+ bufferevent_enable(ctx->src.bev, EV_READ | EV_WRITE);
}
- } else
+ }
+ else
{
ctx->src.bev = pxy_bufferevent_setup(ctx, ctx->fd,
- ctx->src.ssl);
+ ctx->src.ssl);
}
if (!ctx->src.bev)
{
@@ -1668,9 +1566,9 @@ static void pxy_bev_eventcb(struct bufferevent *bev, short events, void *arg)
if (WANT_CONNECT_LOG(ctx) || WANT_CONTENT_LOG(ctx))
{
if (sys_sockaddr_str((struct sockaddr *)
- &ctx->addr, ctx->addrlen,
- &ctx->dsthost_str,
- &ctx->dstport_str) != 0)
+ &ctx->addr, ctx->addrlen,
+ &ctx->dsthost_str,
+ &ctx->dstport_str) != 0)
{
ctx->enomem = 1;
pxy_conn_terminate_free(ctx, 1);
@@ -1678,18 +1576,6 @@ static void pxy_bev_eventcb(struct bufferevent *bev, short events, void *arg)
}
}
- if (WANT_CONTENT_LOG(ctx))
- {
- if (log_content_open(&ctx->logctx, ctx->opts,
- ctx->srchost_str, ctx->srcport_str,
- ctx->dsthost_str, ctx->dstport_str, NULL, NULL, NULL) == -1)
- {
- if (errno == ENOMEM)
- ctx->enomem = 1;
- pxy_conn_terminate_free(ctx, 1);
- return;
- }
- }
connected:
/* log connection if we don't analyze any headers */
@@ -1713,11 +1599,9 @@ connected:
{
char *keystr;
keystr = ssl_ssl_masterkey_to_str(this_conn->ssl);
- if ((keystr == NULL) ||
- (log_masterkey_print_free(keystr) == -1))
+ if ((keystr == NULL))
{
- if (errno == ENOMEM)
- ctx->enomem = 1;
+ if (errno == ENOMEM) ctx->enomem = 1;
pxy_conn_terminate_free(ctx, 1);
return;
}
@@ -1732,23 +1616,24 @@ connected:
/* for SSL, we get two connect events */
log_dbg_printf("SSL connected %s [%s]:%s"
" %s %s\n",
- bev == ctx->dst.bev ?
- "to" : "from",
- bev == ctx->dst.bev ?
- ctx->dsthost_str :
- ctx->srchost_str,
- bev == ctx->dst.bev ?
- ctx->dstport_str :
- ctx->srcport_str,
- SSL_get_version(this_conn->ssl),
- SSL_get_cipher(this_conn->ssl), this_conn);
+ bev == ctx->dst.bev ?
+ "to" : "from",
+ bev == ctx->dst.bev ?
+ ctx->dsthost_str :
+ ctx->srchost_str,
+ bev == ctx->dst.bev ?
+ ctx->dstport_str :
+ ctx->srcport_str,
+ SSL_get_version(this_conn->ssl),
+ SSL_get_cipher(this_conn->ssl), this_conn);
keystr = ssl_ssl_masterkey_to_str(this_conn->ssl);
if (keystr)
{
log_dbg_print_free(keystr);
}
- } else
+ }
+ else
{
/* for TCP, we get only a dst connect event,
* since src was already connected from the
@@ -1756,11 +1641,11 @@ connected:
* in order not to confuse anyone who might be
* looking closely at the output */
log_dbg_printf("TCP connected to [%s]:%s\n",
- ctx->dsthost_str,
- ctx->dstport_str);
+ ctx->dsthost_str,
+ ctx->dstport_str);
log_dbg_printf("TCP connected from [%s]:%s\n",
- ctx->srchost_str,
- ctx->srcport_str);
+ ctx->srchost_str,
+ ctx->srcport_str);
}
}
@@ -1790,67 +1675,69 @@ connected:
log_dbg_printf("Unclean SSL shutdown.\n");
}
#endif /* LIBEVENT_VERSION_NUMBER < 0x02010000 */
- } else if (ERR_GET_REASON(sslerr) ==
+ }
+ else if (ERR_GET_REASON(sslerr) ==
SSL_R_SSLV3_ALERT_HANDSHAKE_FAILURE)
{
/* these can happen due to client cert auth,
* only log error if debugging is activated */
log_dbg_printf("Error from %s bufferevent: "
"%i:%s %lu:%i:%s:%i:%s:%i:%s\n",
- (bev == ctx->src.bev) ? "src" : "dst",
- errno,
- errno ? strerror(errno) : "-",
- sslerr,
- ERR_GET_REASON(sslerr),
- sslerr ?
- ERR_reason_error_string(sslerr) : "-",
- ERR_GET_LIB(sslerr),
- sslerr ?
- ERR_lib_error_string(sslerr) : "-",
- ERR_GET_FUNC(sslerr),
- sslerr ?
- ERR_func_error_string(sslerr) : "-");
+ (bev == ctx->src.bev) ? "src" : "dst",
+ errno,
+ errno ? strerror(errno) : "-",
+ sslerr,
+ ERR_GET_REASON(sslerr),
+ sslerr ?
+ ERR_reason_error_string(sslerr) : "-",
+ ERR_GET_LIB(sslerr),
+ sslerr ?
+ ERR_lib_error_string(sslerr) : "-",
+ ERR_GET_FUNC(sslerr),
+ sslerr ?
+ ERR_func_error_string(sslerr) : "-");
while ((sslerr = bufferevent_get_openssl_error(bev)))
{
log_dbg_printf("Additional SSL error: "
"%lu:%i:%s:%i:%s:%i:%s\n",
- sslerr,
- ERR_GET_REASON(sslerr),
- ERR_reason_error_string(sslerr),
- ERR_GET_LIB(sslerr),
- ERR_lib_error_string(sslerr),
- ERR_GET_FUNC(sslerr),
- ERR_func_error_string(sslerr));
+ sslerr,
+ ERR_GET_REASON(sslerr),
+ ERR_reason_error_string(sslerr),
+ ERR_GET_LIB(sslerr),
+ ERR_lib_error_string(sslerr),
+ ERR_GET_FUNC(sslerr),
+ ERR_func_error_string(sslerr));
}
- } else
+ }
+ else
{
/* real errors */
log_err_printf("Error from %s bufferevent: "
"%i:%s %lu:%i:%s:%i:%s:%i:%s\n",
- (bev == ctx->src.bev) ? "src" : "dst",
- errno,
- errno ? strerror(errno) : "-",
- sslerr,
- ERR_GET_REASON(sslerr),
- sslerr ?
- ERR_reason_error_string(sslerr) : "-",
- ERR_GET_LIB(sslerr),
- sslerr ?
- ERR_lib_error_string(sslerr) : "-",
- ERR_GET_FUNC(sslerr),
- sslerr ?
- ERR_func_error_string(sslerr) : "-");
+ (bev == ctx->src.bev) ? "src" : "dst",
+ errno,
+ errno ? strerror(errno) : "-",
+ sslerr,
+ ERR_GET_REASON(sslerr),
+ sslerr ?
+ ERR_reason_error_string(sslerr) : "-",
+ ERR_GET_LIB(sslerr),
+ sslerr ?
+ ERR_lib_error_string(sslerr) : "-",
+ ERR_GET_FUNC(sslerr),
+ sslerr ?
+ ERR_func_error_string(sslerr) : "-");
while ((sslerr = bufferevent_get_openssl_error(bev)))
{
log_err_printf("Additional SSL error: "
"%lu:%i:%s:%i:%s:%i:%s\n",
- sslerr,
- ERR_GET_REASON(sslerr),
- ERR_reason_error_string(sslerr),
- ERR_GET_LIB(sslerr),
- ERR_lib_error_string(sslerr),
- ERR_GET_FUNC(sslerr),
- ERR_func_error_string(sslerr));
+ sslerr,
+ ERR_GET_REASON(sslerr),
+ ERR_reason_error_string(sslerr),
+ ERR_GET_LIB(sslerr),
+ ERR_lib_error_string(sslerr),
+ ERR_GET_FUNC(sslerr),
+ ERR_func_error_string(sslerr));
}
}
@@ -1875,7 +1762,8 @@ connected:
}
evutil_closesocket(ctx->fd);
other_conn->closed = 1;
- } else if (!other_conn->closed)
+ }
+ else if (!other_conn->closed)
{
/* if the other end is still open and doesn't have data
* to send, close it, otherwise its writecb will close
@@ -1917,7 +1805,8 @@ connected:
"connection establishment\n");
evutil_closesocket(ctx->fd);
other_conn->closed = 1;
- } else if (!other_conn->closed)
+ }
+ else if (!other_conn->closed)
{
/* if there is data pending in the closed connection,
* handle it here, otherwise it will be lost. */
@@ -1948,11 +1837,11 @@ leave:
if (OPTS_DEBUG(ctx->opts))
{
log_dbg_printf("%s disconnected to [%s]:%s\n",
- this_conn->ssl ? "SSL" : "TCP",
- ctx->dsthost_str, ctx->dstport_str);
+ this_conn->ssl ? "SSL" : "TCP",
+ ctx->dsthost_str, ctx->dstport_str);
log_dbg_printf("%s disconnected from [%s]:%s\n",
- this_conn->ssl ? "SSL" : "TCP",
- ctx->srchost_str, ctx->srcport_str);
+ this_conn->ssl ? "SSL" : "TCP",
+ ctx->srchost_str, ctx->srcport_str);
}
this_conn->closed = 1;
@@ -2007,10 +1896,11 @@ static void pxy_conn_connect(pxy_conn_ctx_t *ctx)
{
char *host, *port;
if (sys_sockaddr_str((struct sockaddr *) &ctx->addr,
- ctx->addrlen, &host, &port) != 0)
+ ctx->addrlen, &host, &port) != 0)
{
log_dbg_printf("Connecting to [?]:?\n");
- } else
+ }
+ else
{
log_dbg_printf("Connecting to [%s]:%s\n", host, port);
free(host);
@@ -2020,8 +1910,8 @@ static void pxy_conn_connect(pxy_conn_ctx_t *ctx)
/* initiate connection */
bufferevent_socket_connect(ctx->dst.bev,
- (struct sockaddr *) &ctx->addr,
- ctx->addrlen);
+ (struct sockaddr *) &ctx->addr,
+ ctx->addrlen);
}
/*
@@ -2030,12 +1920,12 @@ static void pxy_conn_connect(pxy_conn_ctx_t *ctx)
*/
static void pxy_sni_resolve_cb(int errcode, struct evutil_addrinfo *ai, void *arg)
{
- pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *)arg;
+ pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *) arg;
if (errcode)
{
log_err_printf("Cannot resolve SNI hostname '%s': %s\n",
- ctx->sni, evutil_gai_strerror(errcode));
+ ctx->sni, evutil_gai_strerror(errcode));
evutil_closesocket(ctx->fd);
pxy_conn_ctx_free(ctx, 1);
return;
@@ -2055,7 +1945,7 @@ static void pxy_sni_resolve_cb(int errcode, struct evutil_addrinfo *ai, void *ar
*/
static void pxy_fd_readcb(evutil_socket_t fd, short what, void *arg)
{
- pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *)arg;
+ pxy_conn_ctx_t *ctx = (pxy_conn_ctx_t *) arg;
/* for SSL, peek ClientHello and parse SNI from it */
if (ctx->spec->ssl && !ctx->passthrough /*&& ctx->ev*/)
@@ -2095,9 +1985,9 @@ static void pxy_fd_readcb(evutil_socket_t fd, short what, void *arg)
if (OPTS_DEBUG(ctx->opts))
{
log_dbg_printf("SNI peek: [%s] [%s]\n",
- ctx->sni ? ctx->sni : "n/a",
- ((rv == 1) && chello) ?
- "incomplete" : "complete");
+ ctx->sni ? ctx->sni : "n/a",
+ ((rv == 1) && chello) ?
+ "incomplete" : "complete");
}
if ((rv == 1) && chello && (ctx->sni_peek_retries++ < 50))
{
@@ -2113,7 +2003,7 @@ static void pxy_fd_readcb(evutil_socket_t fd, short what, void *arg)
event_free(ctx->ev);
ctx->ev = event_new(ctx->evbase, fd, 0,
- pxy_fd_readcb, ctx);
+ pxy_fd_readcb, ctx);
if (!ctx->ev)
{
log_err_printf("Error creating retry "
@@ -2143,7 +2033,7 @@ static void pxy_fd_readcb(evutil_socket_t fd, short what, void *arg)
snprintf(sniport, sizeof(sniport), "%i", ctx->spec->sni_port);
evdns_getaddrinfo(ctx->dnsbase, ctx->sni, sniport, &hints,
- pxy_sni_resolve_cb, ctx);
+ pxy_sni_resolve_cb, ctx);
return;
}
@@ -2183,7 +2073,7 @@ void pxy_conn_setup(evutil_socket_t fd, struct sockaddr *peeraddr, int peeraddrl
/* NAT engine lookup */
ctx->addrlen = sizeof(struct sockaddr_storage);
if (spec->natlookup((struct sockaddr *) &ctx->addr, &ctx->addrlen,
- fd, peeraddr, peeraddrlen) == -1)
+ fd, peeraddr, peeraddrlen) == -1)
{
log_err_printf("Connection not found in NAT "
"state table, aborting connection\n");
@@ -2216,8 +2106,8 @@ void pxy_conn_setup(evutil_socket_t fd, struct sockaddr *peeraddr, int peeraddrl
if (WANT_CONNECT_LOG(ctx) || WANT_CONTENT_LOG(ctx))
{
if (sys_sockaddr_str(peeraddr, peeraddrlen,
- &ctx->srchost_str,
- &ctx->srcport_str) != 0)
+ &ctx->srchost_str,
+ &ctx->srcport_str) != 0)
goto memout;
}
@@ -2225,11 +2115,12 @@ void pxy_conn_setup(evutil_socket_t fd, struct sockaddr *peeraddr, int peeraddrl
if (ctx->spec->ssl)
{
ctx->ev = event_new(ctx->evbase, fd, EV_READ, pxy_fd_readcb,
- ctx);
+ ctx);
if (!ctx->ev)
goto memout;
event_add(ctx->ev, NULL);
- } else
+ }
+ else
{
pxy_fd_readcb(fd, 0, ctx);
}
diff --git a/src/pxyconn.h b/src/pxyconn.h
index ca09a24..d7e4691 100644
--- a/src/pxyconn.h
+++ b/src/pxyconn.h
@@ -48,7 +48,8 @@
*/
/* single dst or src socket bufferevent descriptor */
-typedef struct pxy_conn_desc {
+typedef struct pxy_conn_desc
+{
struct bufferevent *bev;
SSL *ssl;
unsigned int closed : 1;
@@ -57,7 +58,8 @@ typedef struct pxy_conn_desc {
/* actual proxy connection state consisting of two connection descriptors,
* connection-wide state and the specs and options */
-typedef struct pxy_conn_ctx {
+typedef struct pxy_conn_ctx
+{
/* per-connection state */
struct pxy_conn_desc src;
struct pxy_conn_desc dst;
@@ -122,15 +124,14 @@ typedef struct pxy_conn_ctx {
proxyspec *spec;
tfe_config *opts;
- tfe_instance * instance;
+ tfe_instance *instance;
/* Protocol Ctxs*/
- void * protocol_conn_ctx;
+ void *protocol_conn_ctx;
} pxy_conn_ctx_t;
-void pxy_conn_setup(evutil_socket_t, struct sockaddr *, int,
- tfe_thread_manager_ctx *, proxyspec *, tfe_config *)
- NONNULL(2,4,5,6);
+void pxy_conn_setup(evutil_socket_t fd, struct sockaddr *peeraddr, int peeraddrlen,
+ tfe_thread_manager_ctx *thrmgr, proxyspec *spec, tfe_config *opts);
#endif /* !PXYCONN_H */