@@ -19,40 +19,31 @@ static LIST_HEAD(flowtables);
1919
2020static void
2121flow_offload_fill_dir (struct flow_offload * flow , struct nf_conn * ct ,
22- struct nf_flow_route * route ,
2322 enum flow_offload_tuple_dir dir )
2423{
2524 struct flow_offload_tuple * ft = & flow -> tuplehash [dir ].tuple ;
2625 struct nf_conntrack_tuple * ctt = & ct -> tuplehash [dir ].tuple ;
27- struct dst_entry * other_dst = route -> tuple [!dir ].dst ;
28- struct dst_entry * dst = route -> tuple [dir ].dst ;
2926
3027 ft -> dir = dir ;
3128
3229 switch (ctt -> src .l3num ) {
3330 case NFPROTO_IPV4 :
3431 ft -> src_v4 = ctt -> src .u3 .in ;
3532 ft -> dst_v4 = ctt -> dst .u3 .in ;
36- ft -> mtu = ip_dst_mtu_maybe_forward (dst , true);
3733 break ;
3834 case NFPROTO_IPV6 :
3935 ft -> src_v6 = ctt -> src .u3 .in6 ;
4036 ft -> dst_v6 = ctt -> dst .u3 .in6 ;
41- ft -> mtu = ip6_dst_mtu_forward (dst );
4237 break ;
4338 }
4439
4540 ft -> l3proto = ctt -> src .l3num ;
4641 ft -> l4proto = ctt -> dst .protonum ;
4742 ft -> src_port = ctt -> src .u .tcp .port ;
4843 ft -> dst_port = ctt -> dst .u .tcp .port ;
49-
50- ft -> iifidx = other_dst -> dev -> ifindex ;
51- ft -> dst_cache = dst ;
5244}
5345
54- struct flow_offload *
55- flow_offload_alloc (struct nf_conn * ct , struct nf_flow_route * route )
46+ struct flow_offload * flow_offload_alloc (struct nf_conn * ct )
5647{
5748 struct flow_offload * flow ;
5849
@@ -64,16 +55,10 @@ flow_offload_alloc(struct nf_conn *ct, struct nf_flow_route *route)
6455 if (!flow )
6556 goto err_ct_refcnt ;
6657
67- if (!dst_hold_safe (route -> tuple [FLOW_OFFLOAD_DIR_ORIGINAL ].dst ))
68- goto err_dst_cache_original ;
69-
70- if (!dst_hold_safe (route -> tuple [FLOW_OFFLOAD_DIR_REPLY ].dst ))
71- goto err_dst_cache_reply ;
72-
7358 flow -> ct = ct ;
7459
75- flow_offload_fill_dir (flow , ct , route , FLOW_OFFLOAD_DIR_ORIGINAL );
76- flow_offload_fill_dir (flow , ct , route , FLOW_OFFLOAD_DIR_REPLY );
60+ flow_offload_fill_dir (flow , ct , FLOW_OFFLOAD_DIR_ORIGINAL );
61+ flow_offload_fill_dir (flow , ct , FLOW_OFFLOAD_DIR_REPLY );
7762
7863 if (ct -> status & IPS_SRC_NAT )
7964 flow -> flags |= FLOW_OFFLOAD_SNAT ;
@@ -82,17 +67,63 @@ flow_offload_alloc(struct nf_conn *ct, struct nf_flow_route *route)
8267
8368 return flow ;
8469
85- err_dst_cache_reply :
86- dst_release (route -> tuple [FLOW_OFFLOAD_DIR_ORIGINAL ].dst );
87- err_dst_cache_original :
88- kfree (flow );
8970err_ct_refcnt :
9071 nf_ct_put (ct );
9172
9273 return NULL ;
9374}
9475EXPORT_SYMBOL_GPL (flow_offload_alloc );
9576
77+ static int flow_offload_fill_route (struct flow_offload * flow ,
78+ const struct nf_flow_route * route ,
79+ enum flow_offload_tuple_dir dir )
80+ {
81+ struct flow_offload_tuple * flow_tuple = & flow -> tuplehash [dir ].tuple ;
82+ struct dst_entry * other_dst = route -> tuple [!dir ].dst ;
83+ struct dst_entry * dst = route -> tuple [dir ].dst ;
84+
85+ if (!dst_hold_safe (route -> tuple [dir ].dst ))
86+ return -1 ;
87+
88+ switch (flow_tuple -> l3proto ) {
89+ case NFPROTO_IPV4 :
90+ flow_tuple -> mtu = ip_dst_mtu_maybe_forward (dst , true);
91+ break ;
92+ case NFPROTO_IPV6 :
93+ flow_tuple -> mtu = ip6_dst_mtu_forward (dst );
94+ break ;
95+ }
96+
97+ flow_tuple -> iifidx = other_dst -> dev -> ifindex ;
98+ flow_tuple -> dst_cache = dst ;
99+
100+ return 0 ;
101+ }
102+
103+ int flow_offload_route_init (struct flow_offload * flow ,
104+ const struct nf_flow_route * route )
105+ {
106+ int err ;
107+
108+ err = flow_offload_fill_route (flow , route , FLOW_OFFLOAD_DIR_ORIGINAL );
109+ if (err < 0 )
110+ return err ;
111+
112+ err = flow_offload_fill_route (flow , route , FLOW_OFFLOAD_DIR_REPLY );
113+ if (err < 0 )
114+ goto err_route_reply ;
115+
116+ flow -> type = NF_FLOW_OFFLOAD_ROUTE ;
117+
118+ return 0 ;
119+
120+ err_route_reply :
121+ dst_release (route -> tuple [FLOW_OFFLOAD_DIR_ORIGINAL ].dst );
122+
123+ return err ;
124+ }
125+ EXPORT_SYMBOL_GPL (flow_offload_route_init );
126+
96127static void flow_offload_fixup_tcp (struct ip_ct_tcp * tcp )
97128{
98129 tcp -> state = TCP_CONNTRACK_ESTABLISHED ;
@@ -141,10 +172,21 @@ static void flow_offload_fixup_ct(struct nf_conn *ct)
141172 flow_offload_fixup_ct_timeout (ct );
142173}
143174
144- void flow_offload_free (struct flow_offload * flow )
175+ static void flow_offload_route_release (struct flow_offload * flow )
145176{
146177 dst_release (flow -> tuplehash [FLOW_OFFLOAD_DIR_ORIGINAL ].tuple .dst_cache );
147178 dst_release (flow -> tuplehash [FLOW_OFFLOAD_DIR_REPLY ].tuple .dst_cache );
179+ }
180+
181+ void flow_offload_free (struct flow_offload * flow )
182+ {
183+ switch (flow -> type ) {
184+ case NF_FLOW_OFFLOAD_ROUTE :
185+ flow_offload_route_release (flow );
186+ break ;
187+ default :
188+ break ;
189+ }
148190 if (flow -> flags & FLOW_OFFLOAD_DYING )
149191 nf_ct_delete (flow -> ct , 0 , 0 );
150192 nf_ct_put (flow -> ct );
0 commit comments