Merge ~j-latten/ubuntu/+source/openvpn:disco-openvpn-fips-crash-1807439 into ubuntu/+source/openvpn:ubuntu/devel

Proposed by Joy Latten
Status: Merged
Approved by: Andreas Hasenack
Approved revision: b2baff9479374293e4f6a4e138d15da60137dec7
Merged at revision: b2baff9479374293e4f6a4e138d15da60137dec7
Proposed branch: ~j-latten/ubuntu/+source/openvpn:disco-openvpn-fips-crash-1807439
Merge into: ubuntu/+source/openvpn:ubuntu/devel
Diff against target: 132 lines (+110/-0)
3 files modified
debian/changelog (+7/-0)
debian/patches/openvpn-fips-2.4.patch (+102/-0)
debian/patches/series (+1/-0)
Reviewer Review Type Date Requested Status
Andreas Hasenack Approve
Seth Arnold (community) Approve
Canonical Server Pending
Review via email: mp+361583@code.launchpad.net

Description of the change

LP #1807439
openvpn when establishing a tls connection will segfault when used with Ubuntu's FIPS 140-2 libcrypto.so (openssl).

openvpn tls connection does TLS PRF(pseudorandom function) to produce securely generated pseudo random output that is used to generate keys.
MD5 is used as the hash in this computation.

FIPS 140-2 does not permit MD5 use except when used for pseudorandom function (PRF). When openvpn requests MD5 operation to FIPS-mode libcrypto.so, since it is not allowed in general, FIPS-mode libcrypto.so goes into an error state.

openvpn needs to set and pass a flag that FIPS-mode libcrypto.so recognizes and that indicates it is using MD5 for PRF, thereby FIPS-mode libcrypto.so will grant the request instead of entering an error state. In non-FIPS libcrypto.so the flag has no meaning.

To post a comment you must log in.
Revision history for this message
Andreas Hasenack (ahasenack) wrote :

Thanks for this! First pass, comments inline.

review: Needs Fixing
Revision history for this message
Andreas Hasenack (ahasenack) wrote :

Requesting a review from the security team, given that this patch has not yet made it into openvpn upstream.

Revision history for this message
Seth Arnold (seth-arnold) wrote :

The general outline of it looks good to me.

Thanks

review: Approve
Revision history for this message
Joy Latten (j-latten) wrote :
Revision history for this message
Andreas Hasenack (ahasenack) wrote :

Looks good, thanks. +1

review: Approve
Revision history for this message
Andreas Hasenack (ahasenack) wrote :

I'll sponsor this.

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
diff --git a/debian/changelog b/debian/changelog
index 1b1e956..027ec52 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -1,3 +1,10 @@
1openvpn (2.4.6-1ubuntu3) disco; urgency=medium
2
3 * d/p/openvpn-fips-2.4.patch: Allow MD5 in FIPS mode (openssl) for PRF.
4 (LP: #1807439)
5
6 -- Joy Latten <joy.latten@canonical.com> Wed, 09 Jan 2019 12:25:59 -0600
7
1openvpn (2.4.6-1ubuntu2) cosmic; urgency=medium8openvpn (2.4.6-1ubuntu2) cosmic; urgency=medium
29
3 * d/openvpn@.service: Add CAP_AUDIT_WRITE to avoid issues with callout10 * d/openvpn@.service: Add CAP_AUDIT_WRITE to avoid issues with callout
diff --git a/debian/patches/openvpn-fips-2.4.patch b/debian/patches/openvpn-fips-2.4.patch
4new file mode 10064411new file mode 100644
index 0000000..4d2221d
--- /dev/null
+++ b/debian/patches/openvpn-fips-2.4.patch
@@ -0,0 +1,102 @@
1Description: Use openssl FIPS flag to indicate MD5 use for PRF.
2 MD5 is not allowed in FIPS 140-2 except for PRF. OpenVPN needs
3 to send EVP_MD_CTX_FLAG_NON_FIPS_ALLOW flag to FIPS mode openssl
4 for PRF to indicate the exception.
5Bug: https://community.openvpn.net/openvpn/ticket/725
6Bug-Ubuntu: https://bugs.launchpad.net/bugs/1807439
7Author: Stephan Mueller <stephan.mueller@atsec.com>
8
9diff --git a/src/openvpn/crypto.c b/src/openvpn/crypto.c
10index 03e880e..25e8fc4 100644
11--- a/src/openvpn/crypto.c
12+++ b/src/openvpn/crypto.c
13@@ -876,7 +876,7 @@ init_key_ctx(struct key_ctx *ctx, struct key *key,
14 if (kt->digest && kt->hmac_length > 0)
15 {
16 ctx->hmac = hmac_ctx_new();
17- hmac_ctx_init(ctx->hmac, key->hmac, kt->hmac_length, kt->digest);
18+ hmac_ctx_init(ctx->hmac, key->hmac, kt->hmac_length, kt->digest, 0);
19
20 msg(D_HANDSHAKE,
21 "%s: Using %d bit message hash '%s' for HMAC authentication",
22diff --git a/src/openvpn/crypto_backend.h b/src/openvpn/crypto_backend.h
23index b7f519b..8662600 100644
24--- a/src/openvpn/crypto_backend.h
25+++ b/src/openvpn/crypto_backend.h
26@@ -604,10 +604,11 @@ void hmac_ctx_free(hmac_ctx_t *ctx);
27 * @param key The key to use for the HMAC
28 * @param key_len The key length to use
29 * @param kt Static message digest parameters
30+ * @param prf_use Intended use for PRF in TLS protocol
31 *
32 */
33 void hmac_ctx_init(hmac_ctx_t *ctx, const uint8_t *key, int key_length,
34- const md_kt_t *kt);
35+ const md_kt_t *kt, bool prf_use);
36
37 /*
38 * Free the given HMAC context.
39diff --git a/src/openvpn/crypto_mbedtls.c b/src/openvpn/crypto_mbedtls.c
40index 0cb7f81..d7f931d 100644
41--- a/src/openvpn/crypto_mbedtls.c
42+++ b/src/openvpn/crypto_mbedtls.c
43@@ -857,7 +857,7 @@ hmac_ctx_free(mbedtls_md_context_t *ctx)
44
45 void
46 hmac_ctx_init(mbedtls_md_context_t *ctx, const uint8_t *key, int key_len,
47- const mbedtls_md_info_t *kt)
48+ const mbedtls_md_info_t *kt, bool prf_use)
49 {
50 ASSERT(NULL != kt && NULL != ctx);
51
52diff --git a/src/openvpn/crypto_openssl.c b/src/openvpn/crypto_openssl.c
53index 9e8d3f3..d5302ae 100644
54--- a/src/openvpn/crypto_openssl.c
55+++ b/src/openvpn/crypto_openssl.c
56@@ -926,11 +926,17 @@ hmac_ctx_free(HMAC_CTX *ctx)
57
58 void
59 hmac_ctx_init(HMAC_CTX *ctx, const uint8_t *key, int key_len,
60- const EVP_MD *kt)
61+ const EVP_MD *kt, bool prf_use)
62 {
63 ASSERT(NULL != kt && NULL != ctx);
64
65 HMAC_CTX_reset(ctx);
66+
67+ /* FIPS 140-2 explicitly allows MD5 for the use in PRF although it is not
68+ * to be used anywhere else */
69+ if(kt == EVP_md5() && prf_use)
70+ HMAC_CTX_set_flags(ctx, EVP_MD_CTX_FLAG_NON_FIPS_ALLOW);
71+
72 HMAC_Init_ex(ctx, key, key_len, kt, NULL);
73
74 /* make sure we used a big enough key */
75diff --git a/src/openvpn/ntlm.c b/src/openvpn/ntlm.c
76index 077fa3e..83585e2 100644
77--- a/src/openvpn/ntlm.c
78+++ b/src/openvpn/ntlm.c
79@@ -88,7 +88,7 @@ gen_hmac_md5(const uint8_t *data, int data_len, const uint8_t *key, int key_len,
80 const md_kt_t *md5_kt = md_kt_get("MD5");
81 hmac_ctx_t *hmac_ctx = hmac_ctx_new();
82
83- hmac_ctx_init(hmac_ctx, key, key_len, md5_kt);
84+ hmac_ctx_init(hmac_ctx, key, key_len, md5_kt, 0);
85 hmac_ctx_update(hmac_ctx, data, data_len);
86 hmac_ctx_final(hmac_ctx, result);
87 hmac_ctx_cleanup(hmac_ctx);
88diff --git a/src/openvpn/ssl.c b/src/openvpn/ssl.c
89index c0e1dd6..f929237 100644
90--- a/src/openvpn/ssl.c
91+++ b/src/openvpn/ssl.c
92@@ -1637,8 +1637,8 @@ tls1_P_hash(const md_kt_t *md_kt,
93 chunk = md_kt_size(md_kt);
94 A1_len = md_kt_size(md_kt);
95
96- hmac_ctx_init(ctx, sec, sec_len, md_kt);
97- hmac_ctx_init(ctx_tmp, sec, sec_len, md_kt);
98+ hmac_ctx_init(ctx, sec, sec_len, md_kt, 1);
99+ hmac_ctx_init(ctx_tmp, sec, sec_len, md_kt, 1);
100
101 hmac_ctx_update(ctx,seed,seed_len);
102 hmac_ctx_final(ctx, A1);
diff --git a/debian/patches/series b/debian/patches/series
index a903d3d..cc99ac9 100644
--- a/debian/patches/series
+++ b/debian/patches/series
@@ -6,3 +6,4 @@ kfreebsd_support.patch
6match-manpage-and-command-help.patch6match-manpage-and-command-help.patch
7spelling_errors.patch7spelling_errors.patch
8systemd.patch8systemd.patch
9openvpn-fips-2.4.patch

Subscribers

People subscribed via source and target branches