1717#include "homa_stub.h"
1818#endif /* See strip.py */
1919
20+ #ifndef __STRIP__ /* See strip.py */
21+ /**
22+ * homa_set_hijack() - Set fields in an outgoing Homa packet that are needed
23+ * for TCP hijacking to work properly. This function doesn't actually cause
24+ * the packet to be sent via TCP (that is determined by hsk->sock.sk_protocol,
25+ * which is set elsewhere). The modifications made here are safe even if the
26+ * packet isn't actually sent via TCP.
27+ * @skb: Packet buffer in which to set fields.
28+ * @peer: Peer that contains source and destination addresses for the packet.
29+ * @ipv6: True means the packet is going to be sent via IPv6; false means
30+ * IPv4.
31+ */
32+ static inline void homa_set_hijack (struct sk_buff * skb , struct homa_peer * peer ,
33+ bool ipv6 )
34+ {
35+ struct homa_common_hdr * h ;
36+
37+ h = (struct homa_common_hdr * )skb_transport_header (skb );
38+ h -> flags = HOMA_TCP_FLAGS ;
39+ h -> urgent = htons (HOMA_TCP_URGENT );
40+ /* Arrange for proper TCP checksumming. */
41+ skb -> ip_summed = CHECKSUM_PARTIAL ;
42+ skb -> csum_start = skb_transport_header (skb ) - skb -> head ;
43+ skb -> csum_offset = offsetof(struct homa_common_hdr , checksum );
44+ if (ipv6 )
45+ h -> checksum = ~tcp_v6_check (skb -> len , & peer -> flow .u .ip6 .saddr ,
46+ & peer -> flow .u .ip6 .daddr , 0 );
47+ else
48+ h -> checksum = ~tcp_v4_check (skb -> len , peer -> flow .u .ip4 .saddr ,
49+ peer -> flow .u .ip4 .daddr , 0 );
50+ }
51+ #endif /* See strip.py */
52+
2053/**
2154 * homa_message_out_init() - Initialize rpc->msgout.
2255 * @rpc: RPC whose output message should be initialized. Must be
@@ -160,8 +193,7 @@ struct sk_buff *homa_tx_data_pkt_alloc(struct homa_rpc *rpc,
160193 h -> common .dport = htons (rpc -> dport );
161194 h -> common .sequence = htonl (offset );
162195 h -> common .type = DATA ;
163- IF_NO_STRIP (homa_set_hijack (& h -> common ));
164- homa_set_doff (h , sizeof (struct homa_data_hdr ));
196+ homa_set_doff (skb , sizeof (struct homa_data_hdr ));
165197 h -> common .checksum = 0 ;
166198 h -> common .sender_id = cpu_to_be64 (rpc -> id );
167199 h -> message_length = htonl (rpc -> msgout .length );
@@ -190,7 +222,7 @@ struct sk_buff *homa_tx_data_pkt_alloc(struct homa_rpc *rpc,
190222#else /* See strip.py */
191223 if (segs > 1 ) {
192224#endif /* See strip.py */
193- homa_set_doff (h , sizeof (struct homa_data_hdr ) -
225+ homa_set_doff (skb , sizeof (struct homa_data_hdr ) -
194226 sizeof (struct homa_seg_hdr ));
195227#ifndef __STRIP__ /* See strip.py */
196228 h -> seg .offset = htonl (offset );
@@ -429,7 +461,6 @@ int homa_xmit_control(enum homa_packet_type type, void *contents,
429461 h -> type = type ;
430462 h -> sport = htons (rpc -> hsk -> port );
431463 h -> dport = htons (rpc -> dport );
432- IF_NO_STRIP (homa_set_hijack (h ));
433464 h -> sender_id = cpu_to_be64 (rpc -> id );
434465 return __homa_xmit_control (contents , length , rpc -> peer , rpc -> hsk );
435466}
@@ -474,12 +505,16 @@ int __homa_xmit_control(void *contents, size_t length, struct homa_peer *peer,
474505 priority = hsk -> homa -> num_priorities - 1 ;
475506#endif /* See strip.py */
476507 skb -> ooo_okay = 1 ;
508+ homa_set_doff (skb , length );
477509#ifndef __STRIP__ /* See strip.py */
478510 if (hsk -> inet .sk .sk_family == AF_INET6 ) {
511+ homa_set_hijack (skb , peer , true);
479512 result = ip6_xmit (& hsk -> inet .sk , skb , & peer -> flow .u .ip6 , 0 ,
480513 NULL , hsk -> homa -> priority_map [priority ] << 5 ,
481514 0 );
482515 } else {
516+ homa_set_hijack (skb , peer , false);
517+
483518 /* This will find its way to the DSCP field in the IPv4 hdr. */
484519 hsk -> inet .tos = hsk -> homa -> priority_map [priority ] << 5 ;
485520 result = ip_queue_xmit (& hsk -> inet .sk , skb , & peer -> flow );
@@ -535,7 +570,6 @@ void homa_xmit_unknown(struct sk_buff *skb, struct homa_sock *hsk)
535570 unknown .common .sport = h -> dport ;
536571 unknown .common .dport = h -> sport ;
537572 unknown .common .type = RPC_UNKNOWN ;
538- IF_NO_STRIP (homa_set_hijack (& unknown .common ));
539573 unknown .common .sender_id = cpu_to_be64 (homa_local_id (h -> sender_id ));
540574 peer = homa_peer_get (hsk , & saddr );
541575 if (!IS_ERR (peer )) {
@@ -680,15 +714,13 @@ void __homa_xmit_data(struct sk_buff *skb, struct homa_rpc *rpc)
680714 skb_dst_set (skb , homa_get_dst (rpc -> peer , rpc -> hsk ));
681715
682716 skb -> ooo_okay = 1 ;
683- skb -> ip_summed = CHECKSUM_PARTIAL ;
684- skb -> csum_start = skb_transport_header (skb ) - skb -> head ;
685- skb -> csum_offset = offsetof(struct homa_common_hdr , checksum );
686717 if (rpc -> hsk -> inet .sk .sk_family == AF_INET6 ) {
687718 tt_record4 ("calling ip6_xmit: wire_bytes %d, peer 0x%x, id %d, offset %d" ,
688719 homa_get_skb_info (skb )-> wire_bytes ,
689720 tt_addr (rpc -> peer -> addr ), rpc -> id ,
690721 homa_get_skb_info (skb )-> offset );
691722#ifndef __STRIP__ /* See strip.py */
723+ homa_set_hijack (skb , rpc -> peer , true);
692724 err = ip6_xmit (& rpc -> hsk -> inet .sk , skb , & rpc -> peer -> flow .u .ip6 ,
693725 0 , NULL ,
694726 rpc -> hsk -> homa -> priority_map [priority ] << 5 , 0 );
@@ -703,6 +735,7 @@ void __homa_xmit_data(struct sk_buff *skb, struct homa_rpc *rpc)
703735 homa_get_skb_info (skb )-> offset );
704736
705737#ifndef __STRIP__ /* See strip.py */
738+ homa_set_hijack (skb , rpc -> peer , false);
706739 rpc -> hsk -> inet .tos =
707740 rpc -> hsk -> homa -> priority_map [priority ] << 5 ;
708741 err = ip_queue_xmit (& rpc -> hsk -> inet .sk , skb , & rpc -> peer -> flow );
0 commit comments