diff --git a/dp-core/vr_flow.c b/dp-core/vr_flow.c index 2d690c3d2..a91bc01d7 100644 --- a/dp-core/vr_flow.c +++ b/dp-core/vr_flow.c @@ -222,6 +222,7 @@ __vr_flow_reset_entry(struct vrouter *router, struct vr_flow_entry *fe) fe->fe_flags &= (VR_FLOW_FLAG_ACTIVE | VR_FLOW_FLAG_EVICTED | VR_FLOW_FLAG_NEW_FLOW | VR_FLOW_FLAG_DELETE_MARKED); + fe->fe_ttl = 0; return; } @@ -778,6 +779,8 @@ vr_flow_action(struct vrouter *router, struct vr_flow_entry *fe, struct vr_forwarding_md *fmd) { int valid_src; + unsigned int ip_inc_diff_cksum = 0; + struct vr_ip *ip; flow_result_t result; @@ -861,6 +864,22 @@ vr_flow_action(struct vrouter *router, struct vr_flow_entry *fe, break; } + if (result == FLOW_FORWARD) { + if (pkt->vp_type == VP_TYPE_IP) { + ip = (struct vr_ip *)pkt_network_header(pkt); + if (ip) { + if (fe->fe_ttl && (fe->fe_ttl != ip->ip_ttl)) { + vr_incremental_diff(ip->ip_ttl, fe->fe_ttl, &ip_inc_diff_cksum); + ip->ip_ttl = fe->fe_ttl; + + if (ip_inc_diff_cksum) + vr_ip_incremental_csum(ip, ip_inc_diff_cksum); + } + } + } + } + + if (fe->fe_tcp_flags & VR_FLOW_TCP_DEAD) vr_flow_mark_evict(router, fe, index); @@ -1956,6 +1975,8 @@ vr_flow_set(struct vrouter *router, vr_flow_req *req) fe->fe_action = req->fr_action; } + fe->fe_ttl = req->fr_ttl; + if (fe->fe_action == VR_FLOW_ACTION_DROP) fe->fe_drop_reason = (uint8_t)req->fr_drop_reason; diff --git a/dp-core/vr_proto_ip.c b/dp-core/vr_proto_ip.c index f5ae578b2..1f6d133b1 100644 --- a/dp-core/vr_proto_ip.c +++ b/dp-core/vr_proto_ip.c @@ -97,7 +97,8 @@ vr_ip_update_csum(struct vr_packet *pkt, unsigned int ip_inc, unsigned int inc) unsigned short *csump; ip = (struct vr_ip *)pkt_network_header(pkt); - ip->ip_csum = vr_ip_csum(ip); + if (ip_inc) + vr_ip_incremental_csum(ip, ip_inc); if (ip->ip_proto == VR_IP_PROTO_TCP) { tcp = (struct vr_tcp *)((unsigned char *)ip + ip->ip_hl * 4); diff --git a/include/vr_flow.h b/include/vr_flow.h index c0c6a031a..bd8e2a666 100644 --- a/include/vr_flow.h +++ b/include/vr_flow.h @@ -301,7 +301,7 @@ struct vr_flow_queue { struct vr_dummy_flow_entry { vr_hentry_t fe_hentry; - uint8_t fe_pack_hentry; + uint8_t fe_ttl; int16_t fe_qos_id; struct vr_flow fe_key; uint8_t fe_gen_id; @@ -329,7 +329,7 @@ struct vr_dummy_flow_entry { /* do not change. any field positions as it might lead to incompatibility */ struct vr_flow_entry { vr_hentry_t fe_hentry; - uint8_t fe_pack_hentry; + uint8_t fe_ttl; int16_t fe_qos_id; struct vr_flow fe_key; uint8_t fe_gen_id; diff --git a/include/vr_packet.h b/include/vr_packet.h index 1c35f8dc7..3dbd11da7 100644 --- a/include/vr_packet.h +++ b/include/vr_packet.h @@ -412,7 +412,12 @@ vr_ip_incremental_csum(struct vr_ip *ip, unsigned int diff) { unsigned int csum; - diff &= 0xffff; + diff = (diff >> 16) + (diff & 0xffff); + if (diff >> 16) { + diff &= 0xffff; + diff += 1; + } + csum = ~(ip->ip_csum) & 0xffff; csum += diff; csum = (csum >> 16) + (csum & 0xffff); @@ -707,6 +712,7 @@ vr_ip_transport_header_valid(struct vr_ip *iph) } + #define VR_TCP_FLAG_FIN 0x0001 #define VR_TCP_FLAG_SYN 0x0002 #define VR_TCP_FLAG_RST 0x0004 diff --git a/sandesh/vr.sandesh b/sandesh/vr.sandesh index 1862b7055..76c46992b 100644 --- a/sandesh/vr.sandesh +++ b/sandesh/vr.sandesh @@ -191,6 +191,7 @@ buffer sandesh vr_flow_req { 36: i32 fr_oflow_entries; 37: byte fr_gen_id; 38: i16 fr_qos_id; + 39: byte fr_ttl; } buffer sandesh vr_vrf_assign_req { diff --git a/utils/flow.c b/utils/flow.c index 4cc4367b4..069bea332 100644 --- a/utils/flow.c +++ b/utils/flow.c @@ -1401,6 +1401,7 @@ flow_dump_table(struct flow_table *ft) printf(", %d, ", fe->fe_sec_mirror_id); } printf(" SPort %d", fe->fe_udp_src_port); + printf(" TTL %d", fe->fe_ttl); printf(")"); }