2222#include <vnet/ipsec/ipsec.h>
2323#include <vnet/ipsec/esp.h>
2424#include <vnet/ipsec/ah.h>
25+ #include <vnet/tunnel/tunnel_dp.h>
2526
2627#define foreach_ah_encrypt_next \
2728 _ (DROP, "error-drop") \
@@ -111,12 +112,13 @@ typedef struct
111112{
112113 union
113114 {
115+ /* Variable fields in the IP header not covered by the AH
116+ * integrity check */
114117 struct
115118 {
116119 u8 hop_limit ;
117120 u32 ip_version_traffic_class_and_flow_label ;
118121 };
119-
120122 struct
121123 {
122124 u8 ttl ;
@@ -209,8 +211,6 @@ ah_encrypt_inline (vlib_main_t * vm,
209211
210212 ssize_t adv ;
211213 ih0 = vlib_buffer_get_current (b [0 ]);
212- pd -> ttl = ih0 -> ip4 .ttl ;
213- pd -> tos = ih0 -> ip4 .tos ;
214214
215215 if (PREDICT_TRUE (ipsec_sa_is_set_IS_TUNNEL (sa0 )))
216216 {
@@ -246,10 +246,20 @@ ah_encrypt_inline (vlib_main_t * vm,
246246 ip_hdr_size = sizeof (ip6_header_t );
247247 oh6_0 = vlib_buffer_get_current (b [0 ]);
248248 pd -> current_data = b [0 ]-> current_data ;
249-
250249 pd -> hop_limit = ih6_0 -> ip6 .hop_limit ;
251- pd -> ip_version_traffic_class_and_flow_label =
250+
251+ oh6_0 -> ip6 .ip_version_traffic_class_and_flow_label =
252252 ih6_0 -> ip6 .ip_version_traffic_class_and_flow_label ;
253+
254+ ip6_set_dscp_network_order (& oh6_0 -> ip6 , sa0 -> dscp );
255+
256+ tunnel_encap_fixup_6o6 (sa0 -> tunnel_flags ,
257+ & ih6_0 -> ip6 , & oh6_0 -> ip6 );
258+
259+ pd -> ip_version_traffic_class_and_flow_label =
260+ oh6_0 -> ip6 .ip_version_traffic_class_and_flow_label ;
261+ oh6_0 -> ip6 .ip_version_traffic_class_and_flow_label = 0 ;
262+
253263 if (PREDICT_TRUE (ipsec_sa_is_set_IS_TUNNEL (sa0 )))
254264 {
255265 next_hdr_type = IP_PROTOCOL_IPV6 ;
@@ -275,8 +285,24 @@ ah_encrypt_inline (vlib_main_t * vm,
275285 {
276286 ip_hdr_size = sizeof (ip4_header_t );
277287 oh0 = vlib_buffer_get_current (b [0 ]);
278- clib_memset (oh0 , 0 , sizeof (ip4_and_ah_header_t ));
288+ pd -> ttl = ih0 -> ip4 .ttl ;
289+
290+ if (sa0 -> dscp )
291+ pd -> tos = sa0 -> dscp << 2 ;
292+ else
293+ {
294+ pd -> tos = ih0 -> ip4 .tos ;
295+ if (!
296+ (sa0 -> tunnel_flags &
297+ TUNNEL_ENCAP_DECAP_FLAG_ENCAP_COPY_DSCP ))
298+ pd -> tos &= 0x3 ;
299+ if (!
300+ (sa0 -> tunnel_flags &
301+ TUNNEL_ENCAP_DECAP_FLAG_ENCAP_COPY_ECN ))
302+ pd -> tos &= 0xfc ;
303+ }
279304 pd -> current_data = b [0 ]-> current_data ;
305+ clib_memset (oh0 , 0 , sizeof (ip4_and_ah_header_t ));
280306
281307 if (PREDICT_TRUE (ipsec_sa_is_set_IS_TUNNEL (sa0 )))
282308 {
0 commit comments