We are happy to announce the release of strongSwan 5.9.6, which modularizes the IKEv2 key derivation, supports labeled IPsec with IKEv2, improves DoS protection and comes with several other new features and fixes.
The main two steps of the IKEv2 key derivation (PRF/prf+) have been modularized. In particular, prf+
is now provided by a plugin. This makes certification (e.g. FIPS-140) easier at it allows implementing them via an already certified third-party library.
For the most commonly used HMAC-based PRFs, the botan, openssl and wolfssl plugins implement the two steps via their respective implementations of RFC 5869's HKDF-Extract
(KDF_PRF
) and HKDF-Expand
(KDF_PRF_PLUS
). A default implementation, based on generic PRFs from other plugins, is provided by the new kdf plugin (may be disabled if one of the mentioned third-party plugins is loaded and none of the rarely used non-HMAC PRFs are used).
Support for labeled IPsec with IKEv2 (draft-ietf-ipsecme-labeled-ipsec) has been added. Two modes are currently supported:
SELinux: When building with --enable-selinux
, support for SELinux labels is enabled and the selinux plugin is built. If SELinux is usable on the system, the negotiated labels are installed on IPsec SAs and policies. The configured label is expected to be a generic context (e.g. system_u:object_r:ipsec_spd_t:s0
), which is installed on trap policies. Either from the outset via start_action=trap
, or dynamically by the selinux plugin after an IKE_SA has been established (e.g. in roadwarrior scenarios, in particular as responder). Once traffic hits such a policy and matches its context via association:polmatch
, an acquire with the actual label is triggered by the kernel, for which a CHILD_SA is negotiated with the peer. A childless IKE_SA is created if the connection is not triggered by an acquire and no specific label is available. Labels received as responder are accepted if they match the configured label via association:polmatch
.
Simple: This proprietary mode, which is the default if SELinux support is disabled or not available on the system, allows exchanging arbitrary labels to identify specific child configs on the peer. These labels are not configured on the IPsec SAs or policies but are simply used during CHILD_SA creation to aid config selection (an example can be seen in the ikev2/net2net-dscp scenario).
The secrets used for generating COOKIE payloads are now switched based on a time limit (2 minutes) and not the previous usage limit (10'000 generated cookies). This avoids switching secrets multiple times a second under a heavy attack, preventing legitimate clients from successfully sending requests with valid cookies (they are valid for 10 seconds, by default).
So far, sending and requiring COOKIE payloads was triggered only by the total number of half-open IKE_SAs. Because that global threshold is higher than the per-IP block threshold (5 half-open IKE_SAs are allowed per IP, by default), it was possible for an attacker to block a legitimate user by sending spoofed IKE_SA_INIT packets from that user's IP. To prevent this, a new per-IP threshold (3 half-open IKE_SAs, by default) has been added to trigger cookies. The default value for the global threshold has also been increased slightly (from 10 to 30).
Unprocessed but queued initial messages (IKE_SA_INIT for IKEv2) are now already counted as half-open IKE_SAs. This makes the thresholds more accurate so it isn't possible anymore for attackers to create thousands of jobs for packets from spoofed IP addresses before the daemon is able to process enough of them to create half-open IKE_SAs that would trigger the thresholds.
dpd_action=restart
). This does not prevent duplicates if they are initiated by the two peers concurrently.trap
and start
in start_action
(i.e. start_action=trap|start
) to immediately initiate an SA for which trap policies are also installed.unable to install policy ... for reqid ..., the same policy for reqid ... exists
is replaced by a simple warning should the reqid for a policy actually get updated.map_level
option for syslog loggers allows mapping log levels (0..4) to syslog levels starting at the specified number (by default, all messages are logged with LOG_INFO
).