Modern TLS libraries might drop Blowfish by default or distributions
might disable Blowfish in OpenSSL/mbed TLS. We still signal OCC
options with BF-CBC compatible strings. To avoid requiring BF-CBC
for this, special this one usage of BF-CBC enough to avoid a hard
requirement on Blowfish in the default configuration.
Signed-off-by: Arne Schwabe
Patch v2: add more clarifying comment, do not warn about OCC only insecure
ciphers, code improvements
Signed-off-by: Arne Schwabe
---
src/openvpn/init.c| 32 ++
src/openvpn/options.c | 46 +--
2 files changed, 64 insertions(+), 14 deletions(-)
diff --git a/src/openvpn/init.c b/src/openvpn/init.c
index c3493c42..df0c7ebc 100644
--- a/src/openvpn/init.c
+++ b/src/openvpn/init.c
@@ -2770,14 +2770,30 @@ do_init_crypto_tls_c1(struct context *c)
#endif /* if P2MP */
}
-/* Do not warn if we only have BF-CBC in options->ciphername
- * because it is still the default cipher */
-bool warn = !streq(options->ciphername, "BF-CBC")
- || options->enable_ncp_fallback;
-/* Get cipher & hash algorithms */
-init_key_type(>c1.ks.key_type, options->ciphername,
options->authname,
- options->keysize, true, warn);
-
+ /*
+* BF-CBC is allowed to be used only when explicitly configured
+* as NCP-fallback or when NCP has been disabled.
+* In all other cases don't attempt to initialize BF-CBC as it
+* may not even be supported by the underlying SSL library.
+*
+* Therefore, the key structure has to be initialized when:
+* - any non-BF-CBC cipher was selected; or
+* - BF-CBC is selected and NCP is disabled (explicit request to
+* use the BF-CBC cipher); or
+* - BF-CBC is selected, NCP is enabled and fallback is enabled
+* (BF-CBC will be the fallback).
+*
+* Note that BF-CBC will still be part of the OCC string to retain
+* backwards compatibility with older clients.
+*/
+if (!streq(options->ciphername, "BF-CBC") || !options->ncp_enabled
+|| options->enable_ncp_fallback)
+{
+/* Do not warn if the if the cipher is used only in OCC */
+bool warn = !options->ncp_enabled || options->enable_ncp_fallback;
+init_key_type(>c1.ks.key_type, options->ciphername,
options->authname,
+ options->keysize, true, warn);
+}
/* Initialize PRNG with config-specified digest */
prng_init(options->prng_hash, options->prng_nonce_secret_len);
diff --git a/src/openvpn/options.c b/src/openvpn/options.c
index b81137cf..d52057cc 100644
--- a/src/openvpn/options.c
+++ b/src/openvpn/options.c
@@ -3664,9 +3664,29 @@ calc_options_string_link_mtu(const struct options *o,
const struct frame *frame)
{
struct frame fake_frame = *frame;
struct key_type fake_kt;
-init_key_type(_kt, o->ciphername, o->authname, o->keysize, true,
- false);
+
frame_remove_from_extra_frame(_frame, crypto_max_overhead());
+
+
+/* o->ciphername might be BF-CBC even though the underlying SSL library
+ * does not support it. For this reason we workaround this corner case
+ * by pretending to have no encryption enabled and by manually adding
+ * the required packet overhead to the MTU computation.
+ */
+const char* ciphername = o->ciphername;
+
+if (strcmp(o->ciphername, "BF-CBC") == 0)
+{
+/* none has no overhead, so use this to later add only --auth
+ * overhead */
+
+/* overhead of BF-CBC: 64 bit block size, 64 bit IV size */
+frame_add_to_extra_frame(_frame, 64/8 + 64/8);
+}
+
+init_key_type(_kt, ciphername, o->authname, o->keysize, true,
+ false);
+
crypto_adjust_frame_parameters(_frame, _kt, o->replay,
cipher_kt_mode_ofb_cfb(fake_kt.cipher));
frame_finalize(_frame, o->ce.link_mtu_defined, o->ce.link_mtu,
@@ -3836,18 +3856,32 @@ options_string(const struct options *o,
+ (TLS_SERVER == true)
<= 1);
-init_key_type(, o->ciphername, o->authname, o->keysize, true,
- false);
+/* Skip resolving BF-CBC to allow SSL libraries without BF-CBC
+ * to work here in the default configuration */
+const char *ciphername = o->ciphername;
+int keysize;
+
+if (strcmp(o->ciphername, "BF-CBC") == 0) {
+init_key_type(, "none", o->authname, o->keysize, true,
+ false);
+ciphername = cipher_kt_name(kt.cipher);
+keysize = 128;
+}
+else
+{
+init_key_type(, o->ciphername, o->authname, o->keysize, true,
+