summaryrefslogtreecommitdiff
path: root/openvpn/src/openvpn/init.c
diff options
context:
space:
mode:
Diffstat (limited to 'openvpn/src/openvpn/init.c')
-rw-r--r--openvpn/src/openvpn/init.c246
1 files changed, 92 insertions, 154 deletions
diff --git a/openvpn/src/openvpn/init.c b/openvpn/src/openvpn/init.c
index a25de5d2..993a1f27 100644
--- a/openvpn/src/openvpn/init.c
+++ b/openvpn/src/openvpn/init.c
@@ -111,102 +111,99 @@ update_options_ce_post (struct options *options)
#endif
}
-#if HTTP_PROXY_FALLBACK
-
+#ifdef ENABLE_MANAGEMENT
static bool
-ce_http_proxy_fallback_defined(const struct context *c)
+management_callback_proxy_cmd (void *arg, const char **p)
{
- const struct connection_list *l = c->options.connection_list;
- if (l && l->current == 0)
- {
- int i;
- for (i = 0; i < l->len; ++i)
- {
- const struct connection_entry *ce = l->array[i];
- if (ce->flags & CE_HTTP_PROXY_FALLBACK)
- return true;
- }
- }
- return false;
-}
+ struct context *c = arg;
+ struct connection_entry *ce = &c->options.ce;
+ struct gc_arena *gc = &c->c2.gc;
+ bool ret = false;
-static void
-ce_http_proxy_fallback_start(struct context *c, const char *remote_ip_hint)
-{
- const struct connection_list *l = c->options.connection_list;
- if (l)
- {
- int i;
- for (i = 0; i < l->len; ++i)
- {
- struct connection_entry *ce = l->array[i];
- if (ce->flags & CE_HTTP_PROXY_FALLBACK)
- {
- ce->http_proxy_options = NULL;
- ce->ce_http_proxy_fallback_timestamp = 0;
- if (!remote_ip_hint)
- remote_ip_hint = ce->remote;
- }
- }
+ update_time();
+ if (streq (p[1], "NONE"))
+ ret = true;
+ else if (p[2] && p[3])
+ {
+ const int port = atoi(p[3]);
+ if (!legal_ipv4_port (port))
+ {
+ msg (M_WARN, "Bad proxy port number: %s", p[3]);
+ return false;
+ }
+
+ if (streq (p[1], "HTTP"))
+ {
+#ifndef ENABLE_HTTP_PROXY
+ msg (M_WARN, "HTTP proxy support is not available");
+#else
+ struct http_proxy_options *ho;
+ if (ce->proto != PROTO_TCPv4 && ce->proto != PROTO_TCPv4_CLIENT &&
+ ce->proto != PROTO_TCPv6 && ce->proto != PROTO_TCPv6_CLIENT)
+ {
+ msg (M_WARN, "HTTP proxy support only works for TCP based connections");
+ return false;
+ }
+ ho = init_http_proxy_options_once (ce->http_proxy_options, gc);
+ ho->server = string_alloc (p[2], gc);
+ ho->port = port;
+ ho->retry = true;
+ ho->auth_retry = (p[4] && streq (p[4], "nct") ? PAR_NCT : PAR_ALL);
+ ce->http_proxy_options = ho;
+ ret = true;
+#endif
+ }
+ else if (streq (p[1], "SOCKS"))
+ {
+#ifndef ENABLE_SOCKS
+ msg (M_WARN, "SOCKS proxy support is not available");
+#else
+ ce->socks_proxy_server = string_alloc (p[2], gc);
+ ce->socks_proxy_port = port;
+ ret = true;
+#endif
+ }
}
+ else
+ msg (M_WARN, "Bad proxy command");
- if (management)
- management_http_proxy_fallback_notify(management, "NEED_LATER", remote_ip_hint);
-}
-
-static bool
-ce_http_proxy_fallback (struct context *c, volatile const struct connection_entry *ce)
-{
- const int proxy_info_expire = 120; /* seconds before proxy info expires */
+ ce->flags &= ~CE_MAN_QUERY_PROXY;
- update_time();
- if (management)
- {
- if (!ce->ce_http_proxy_fallback_timestamp)
- {
- management_http_proxy_fallback_notify(management, "NEED_NOW", NULL);
- while (!ce->ce_http_proxy_fallback_timestamp)
- {
- management_event_loop_n_seconds (management, 1);
- if (IS_SIG (c))
- return false;
- }
- }
- return (now < ce->ce_http_proxy_fallback_timestamp + proxy_info_expire && ce->http_proxy_options);
- }
- return false;
+ return ret;
}
static bool
-management_callback_http_proxy_fallback_cmd (void *arg, const char *server, const char *port, const char *flags)
+ce_management_query_proxy (struct context *c)
{
- struct context *c = (struct context *) arg;
const struct connection_list *l = c->options.connection_list;
- int ret = false;
- struct http_proxy_options *ho = parse_http_proxy_fallback (c, server, port, flags, M_WARN);
+ struct connection_entry *ce = &c->options.ce;
+ struct gc_arena gc;
+ bool ret = true;
update_time();
- if (l)
+ if (management)
{
- int i;
- for (i = 0; i < l->len; ++i)
- {
- struct connection_entry *ce = l->array[i];
- if (ce->flags & CE_HTTP_PROXY_FALLBACK)
- {
- ce->http_proxy_options = ho;
- ce->ce_http_proxy_fallback_timestamp = now;
- ret = true;
- }
- }
+ gc = gc_new ();
+ struct buffer out = alloc_buf_gc (256, &gc);
+ buf_printf (&out, ">PROXY:%u,%s,%s", (l ? l->current : 0) + 1,
+ (proto_is_udp (ce->proto) ? "UDP" : "TCP"), np (ce->remote));
+ management_notify_generic (management, BSTR (&out));
+ ce->flags |= CE_MAN_QUERY_PROXY;
+ while (ce->flags & CE_MAN_QUERY_PROXY)
+ {
+ management_event_loop_n_seconds (management, 1);
+ if (IS_SIG (c))
+ {
+ ret = false;
+ break;
+ }
+ }
+ gc_free (&gc);
}
-
+
return ret;
}
-#endif
-
-#if MANAGEMENT_QUERY_REMOTE
static bool
management_callback_remote_cmd (void *arg, const char **p)
@@ -287,8 +284,7 @@ ce_management_query_remote (struct context *c, const char *remote_ip_hint)
gc_free (&gc);
return ret;
}
-
-#endif
+#endif /* ENABLE_MANAGEMENT */
/*
* Initialize and possibly randomize connection list.
@@ -296,7 +292,6 @@ ce_management_query_remote (struct context *c, const char *remote_ip_hint)
static void
init_connection_list (struct context *c)
{
-#ifdef ENABLE_CONNECTION
struct connection_list *l = c->options.connection_list;
if (l)
{
@@ -317,32 +312,7 @@ init_connection_list (struct context *c)
}
}
}
-#endif
-}
-
-#if 0 /* fixme -- disable for production */
-static void
-show_connection_list (const struct connection_list *l)
-{
- int i;
- dmsg (M_INFO, "CONNECTION_LIST len=%d current=%d",
- l->len, l->current);
- for (i = 0; i < l->len; ++i)
- {
- dmsg (M_INFO, "[%d] %s:%d proto=%s http_proxy=%d",
- i,
- l->array[i]->remote,
- l->array[i]->remote_port,
- proto2ascii(l->array[i]->proto, true),
- BOOL_CAST(l->array[i]->http_proxy_options));
- }
-}
-#else
-static inline void
-show_connection_list (const struct connection_list *l)
-{
}
-#endif
/*
* Increment to next connection entry
@@ -350,7 +320,6 @@ show_connection_list (const struct connection_list *l)
static void
next_connection_entry (struct context *c)
{
-#ifdef ENABLE_CONNECTION
struct connection_list *l = c->options.connection_list;
if (l)
{
@@ -379,7 +348,6 @@ next_connection_entry (struct context *c)
if (l->current == 0)
newcycle = true;
- show_connection_list(l);
}
ce = l->array[l->current];
@@ -387,44 +355,33 @@ next_connection_entry (struct context *c)
if (c->options.remote_ip_hint && !l->n_cycles)
remote_ip_hint = c->options.remote_ip_hint;
-#if HTTP_PROXY_FALLBACK
- if (newcycle && ce_http_proxy_fallback_defined(c))
- ce_http_proxy_fallback_start(c, remote_ip_hint);
-
- if (ce->flags & CE_HTTP_PROXY_FALLBACK)
- {
- ce_defined = ce_http_proxy_fallback(c, ce);
- if (IS_SIG (c))
- break;
- }
-#endif
-
if (ce->flags & CE_DISABLED)
ce_defined = false;
c->options.ce = *ce;
-
-#if MANAGEMENT_QUERY_REMOTE
+#ifdef ENABLE_MANAGEMENT
if (ce_defined && management && management_query_remote_enabled(management))
{
/* allow management interface to override connection entry details */
ce_defined = ce_management_query_remote(c, remote_ip_hint);
if (IS_SIG (c))
break;
- } else
+ }
+ else
#endif
if (remote_ip_hint)
c->options.ce.remote = remote_ip_hint;
-#if 0 /* fixme -- disable for production, this code simulates a network where proxy fallback is the only method to reach the OpenVPN server */
- if (!(c->options.ce.flags & CE_HTTP_PROXY_FALLBACK))
- {
- c->options.ce.remote = "10.10.0.1"; /* use an unreachable address here */
- }
+#ifdef ENABLE_MANAGEMENT
+ if (ce_defined && management && management_query_proxy_enabled (management))
+ {
+ ce_defined = ce_management_query_proxy (c);
+ if (IS_SIG (c))
+ break;
+ }
#endif
} while (!ce_defined);
}
-#endif
update_options_ce_post (&c->options);
}
@@ -498,11 +455,10 @@ init_proxy_dowork (struct context *c)
uninit_proxy_dowork (c);
#ifdef ENABLE_HTTP_PROXY
- if (c->options.ce.http_proxy_options || c->options.auto_proxy_info)
+ if (c->options.ce.http_proxy_options)
{
/* Possible HTTP proxy user/pass input */
- c->c1.http_proxy = http_proxy_new (c->options.ce.http_proxy_options,
- c->options.auto_proxy_info);
+ c->c1.http_proxy = http_proxy_new (c->options.ce.http_proxy_options);
if (c->c1.http_proxy)
{
did_http = true;
@@ -512,13 +468,12 @@ init_proxy_dowork (struct context *c)
#endif
#ifdef ENABLE_SOCKS
- if (!did_http && (c->options.ce.socks_proxy_server || c->options.auto_proxy_info))
+ if (!did_http && c->options.ce.socks_proxy_server)
{
c->c1.socks_proxy = socks_proxy_new (c->options.ce.socks_proxy_server,
c->options.ce.socks_proxy_port,
c->options.ce.socks_proxy_authfile,
- c->options.ce.socks_proxy_retry,
- c->options.auto_proxy_info);
+ c->options.ce.socks_proxy_retry);
if (c->c1.socks_proxy)
{
c->c1.socks_proxy_owned = true;
@@ -1251,10 +1206,7 @@ do_init_route_ipv6_list (const struct options *options,
{
const char *gw = NULL;
int dev = dev_type_enum (options->dev, options->dev_type);
- int metric = 0;
-
- if (dev != DEV_TYPE_TUN )
- msg( M_WARN, "IPv6 routes on TAP devices are going to fail on some platforms (need gateway spec)" ); /* TODO-GERT */
+ int metric = -1; /* no metric set */
gw = options->ifconfig_ipv6_remote; /* default GW = remote end */
#if 0 /* not yet done for IPv6 - TODO!*/
@@ -2065,13 +2017,11 @@ do_init_crypto_static (struct context *c, const unsigned int flags)
unsigned int rkf_flags = RKF_MUST_SUCCEED;
const char *rkf_file = options->shared_secret_file;
-#if ENABLE_INLINE_FILES
if (options->shared_secret_file_inline)
{
rkf_file = options->shared_secret_file_inline;
rkf_flags |= RKF_INLINE;
}
-#endif
read_key_file (&key2, rkf_file, rkf_flags);
}
@@ -2165,13 +2115,11 @@ do_init_crypto_tls_c1 (struct context *c)
unsigned int flags = 0;
const char *file = options->tls_auth_file;
-#if ENABLE_INLINE_FILES
if (options->tls_auth_file_inline)
{
flags |= GHK_INLINE;
file = options->tls_auth_file_inline;
}
-#endif
get_tls_handshake_key (&c->c1.ks.key_type,
&c->c1.ks.tls_auth_key,
file,
@@ -2474,12 +2422,6 @@ do_option_warnings (struct context *c)
{
const struct options *o = &c->options;
-#if 1 /* JYFIXME -- port warning */
- if (!o->ce.port_option_used && (o->ce.local_port == OPENVPN_PORT && o->ce.remote_port == OPENVPN_PORT))
- msg (M_WARN, "IMPORTANT: OpenVPN's default port number is now %d, based on an official port number assignment by IANA. OpenVPN 2.0-beta16 and earlier used 5000 as the default port.",
- OPENVPN_PORT);
-#endif
-
if (o->ping_send_timeout && !o->ping_rec_timeout)
msg (M_WARN, "WARNING: --ping should normally be used with --ping-restart or --ping-exit");
@@ -3197,12 +3139,8 @@ init_management_callback_p2p (struct context *c)
cb.arg = c;
cb.status = management_callback_status_p2p;
cb.show_net = management_show_net_callback;
-#if HTTP_PROXY_FALLBACK
- cb.http_proxy_fallback_cmd = management_callback_http_proxy_fallback_cmd;
-#endif
-#if MANAGEMENT_QUERY_REMOTE
+ cb.proxy_cmd = management_callback_proxy_cmd;
cb.remote_cmd = management_callback_remote_cmd;
-#endif
management_set_callback (management, &cb);
}
#endif