Index: share/man/man4/carp.4 =================================================================== --- share/man/man4/carp.4 +++ share/man/man4/carp.4 @@ -26,7 +26,7 @@ .\" .\" $FreeBSD$ .\" -.Dd February 21, 2013 +.Dd February 23, 2018 .Dt CARP 4 .Os .Sh NAME @@ -102,6 +102,13 @@ When enabled, a vhid in a backup state would preempt a master that is announcing itself with a lower advskew. Disabled by default. +.It Va net.inet.carp.dscp +Set DSCP value in carp packet +When enabled, set Class of Service to CS7 (network control) in outgoing +carp packets. +When disabled, Class of Service is set to TOS LOW_DELAY. +TOS values were deprecated and replaced by DSCP in 1998. +Disabled by default. .It Va net.inet.carp.log Determines what events relating to .Nm Index: sys/netinet/ip6.h =================================================================== --- sys/netinet/ip6.h +++ sys/netinet/ip6.h @@ -102,6 +102,7 @@ #define IPV6_FLOWLABEL_MASK 0xffff0f00 /* flow label (20 bits) */ #endif /* LITTLE_ENDIAN */ #endif +#define IPV6_FLOWLABEL_LEN 20 #if 1 /* ECN bits proposed by Sally Floyd */ #define IP6TOS_CE 0x01 /* congestion experienced */ Index: sys/netinet/ip_carp.c =================================================================== --- sys/netinet/ip_carp.c +++ sys/netinet/ip_carp.c @@ -190,6 +190,10 @@ static VNET_DEFINE(int, carp_allow) = 1; #define V_carp_allow VNET(carp_allow) +/* Set DSCP in outgoing CARP packets. */ +static VNET_DEFINE(int, carp_dscp) = 1; +#define V_carp_dscp VNET(carp_dscp) + /* Preempt slower nodes. */ static VNET_DEFINE(int, carp_preempt) = 0; #define V_carp_preempt VNET(carp_preempt) @@ -215,6 +219,8 @@ SYSCTL_NODE(_net_inet, IPPROTO_CARP, carp, CTLFLAG_RW, 0, "CARP"); SYSCTL_INT(_net_inet_carp, OID_AUTO, allow, CTLFLAG_VNET | CTLFLAG_RW, &VNET_NAME(carp_allow), 0, "Accept incoming CARP packets"); +SYSCTL_INT(_net_inet_carp, OID_AUTO, dscp, CTLFLAG_VNET | CTLFLAG_RW, + &VNET_NAME(carp_dscp), 0, "Use DSCP CS7 for carp packets"); SYSCTL_INT(_net_inet_carp, OID_AUTO, preempt, CTLFLAG_VNET | CTLFLAG_RW, &VNET_NAME(carp_preempt), 0, "High-priority backup preemption mode"); SYSCTL_INT(_net_inet_carp, OID_AUTO, log, CTLFLAG_VNET | CTLFLAG_RW, @@ -931,7 +937,11 @@ ip = mtod(m, struct ip *); ip->ip_v = IPVERSION; ip->ip_hl = sizeof(*ip) >> 2; - ip->ip_tos = IPTOS_LOWDELAY; + if (V_carp_dscp) { + ip->ip_tos = IPTOS_DSCP_CS7; + } else { + ip->ip_tos = IPTOS_LOWDELAY; + } ip->ip_len = htons(len); ip->ip_off = htons(IP_DF); ip->ip_ttl = CARP_DFLTTL; @@ -981,6 +991,11 @@ ip6 = mtod(m, struct ip6_hdr *); bzero(ip6, sizeof(*ip6)); ip6->ip6_vfc |= IPV6_VERSION; + if (V_carp_dscp) { + /* Traffic class isn't defined in ip6 struct instead + * it gets offset into flowlabel field */ + ip6->ip6_flow |= htonl(IPTOS_DSCP_CS7 << IPV6_FLOWLABEL_LEN); + } ip6->ip6_hlim = CARP_DFLTTL; ip6->ip6_nxt = IPPROTO_CARP;