1 /* 2 * 3 * Copyright 2018 gRPC authors. 4 * 5 * Licensed under the Apache License, Version 2.0 (the "License"); 6 * you may not use this file except in compliance with the License. 7 * You may obtain a copy of the License at 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * See the License for the specific language governing permissions and 15 * limitations under the License. 16 * 17 */ 18 19 /* This file contains constants defined in <linux/errqueue.h> and 20 * <linux/net_tstamp.h> so as to allow collecting network timestamps in the 21 * kernel. This file allows tcp_posix.cc to compile on platforms that do not 22 * have <linux/errqueue.h> and <linux/net_tstamp.h>. 23 */ 24 25 #ifndef GRPC_CORE_LIB_IOMGR_INTERNAL_ERRQUEUE_H 26 #define GRPC_CORE_LIB_IOMGR_INTERNAL_ERRQUEUE_H 27 28 #include <grpc/support/port_platform.h> 29 30 #include "src/core/lib/iomgr/port.h" 31 32 #ifdef GRPC_POSIX_SOCKET_TCP 33 34 #include <sys/types.h> 35 #include <time.h> 36 37 #ifdef GRPC_LINUX_ERRQUEUE 38 #include <linux/errqueue.h> 39 #include <linux/net_tstamp.h> 40 #include <linux/netlink.h> 41 #include <sys/socket.h> 42 #endif /* GRPC_LINUX_ERRQUEUE */ 43 44 namespace grpc_core { 45 46 #ifdef GRPC_LINUX_ERRQUEUE 47 48 /* Redefining scm_timestamping in the same way that <linux/errqueue.h> defines 49 * it, so that code compiles on systems that don't have it. */ 50 struct scm_timestamping { 51 struct timespec ts[3]; 52 }; 53 /* Also redefine timestamp types */ 54 /* The timestamp type for when the driver passed skb to NIC, or HW. */ 55 constexpr int SCM_TSTAMP_SND = 0; 56 /* The timestamp type for when data entered the packet scheduler. */ 57 constexpr int SCM_TSTAMP_SCHED = 1; 58 /* The timestamp type for when data acknowledged by peer. */ 59 constexpr int SCM_TSTAMP_ACK = 2; 60 61 /* Control message type containing OPT_STATS */ 62 #ifndef SCM_TIMESTAMPING_OPT_STATS 63 #define SCM_TIMESTAMPING_OPT_STATS 54 64 #endif 65 66 /* Redefine required constants from <linux/net_tstamp.h> */ 67 constexpr uint32_t SOF_TIMESTAMPING_TX_SOFTWARE = 1u << 1; 68 constexpr uint32_t SOF_TIMESTAMPING_SOFTWARE = 1u << 4; 69 constexpr uint32_t SOF_TIMESTAMPING_OPT_ID = 1u << 7; 70 constexpr uint32_t SOF_TIMESTAMPING_TX_SCHED = 1u << 8; 71 constexpr uint32_t SOF_TIMESTAMPING_TX_ACK = 1u << 9; 72 constexpr uint32_t SOF_TIMESTAMPING_OPT_TSONLY = 1u << 11; 73 constexpr uint32_t SOF_TIMESTAMPING_OPT_STATS = 1u << 12; 74 75 constexpr uint32_t kTimestampingSocketOptions = 76 SOF_TIMESTAMPING_SOFTWARE | SOF_TIMESTAMPING_OPT_ID | 77 SOF_TIMESTAMPING_OPT_TSONLY | SOF_TIMESTAMPING_OPT_STATS; 78 constexpr uint32_t kTimestampingRecordingOptions = 79 SOF_TIMESTAMPING_TX_SCHED | SOF_TIMESTAMPING_TX_SOFTWARE | 80 SOF_TIMESTAMPING_TX_ACK; 81 82 /* Netlink attribute types used for TCP opt stats. */ 83 enum TCPOptStats { 84 TCP_NLA_PAD, 85 TCP_NLA_BUSY, /* Time (usec) busy sending data. */ 86 TCP_NLA_RWND_LIMITED, /* Time (usec) limited by receive window. */ 87 TCP_NLA_SNDBUF_LIMITED, /* Time (usec) limited by send buffer. */ 88 TCP_NLA_DATA_SEGS_OUT, /* Data pkts sent including retransmission. */ 89 TCP_NLA_TOTAL_RETRANS, /* Data pkts retransmitted. */ 90 TCP_NLA_PACING_RATE, /* Pacing rate in Bps. */ 91 TCP_NLA_DELIVERY_RATE, /* Delivery rate in Bps. */ 92 TCP_NLA_SND_CWND, /* Sending congestion window. */ 93 TCP_NLA_REORDERING, /* Reordering metric. */ 94 TCP_NLA_MIN_RTT, /* minimum RTT. */ 95 TCP_NLA_RECUR_RETRANS, /* Recurring retransmits for the current pkt. */ 96 TCP_NLA_DELIVERY_RATE_APP_LMT, /* Delivery rate application limited? */ 97 TCP_NLA_SNDQ_SIZE, /* Data (bytes) pending in send queue */ 98 TCP_NLA_CA_STATE, /* ca_state of socket */ 99 TCP_NLA_SND_SSTHRESH, /* Slow start size threshold */ 100 TCP_NLA_DELIVERED, /* Data pkts delivered incl. out-of-order */ 101 TCP_NLA_DELIVERED_CE, /* Like above but only ones w/ CE marks */ 102 TCP_NLA_BYTES_SENT, /* Data bytes sent including retransmission */ 103 TCP_NLA_BYTES_RETRANS, /* Data bytes retransmitted */ 104 TCP_NLA_DSACK_DUPS, /* DSACK blocks received */ 105 TCP_NLA_REORD_SEEN, /* reordering events seen */ 106 TCP_NLA_SRTT, /* smoothed RTT in usecs */ 107 }; 108 109 /* tcp_info from from linux/tcp.h */ 110 struct tcp_info { 111 uint8_t tcpi_state; 112 uint8_t tcpi_ca_state; 113 uint8_t tcpi_retransmits; 114 uint8_t tcpi_probes; 115 uint8_t tcpi_backoff; 116 uint8_t tcpi_options; 117 uint8_t tcpi_snd_wscale : 4, tcpi_rcv_wscale : 4; 118 uint8_t tcpi_delivery_rate_app_limited : 1; 119 uint32_t tcpi_rto; 120 uint32_t tcpi_ato; 121 uint32_t tcpi_snd_mss; 122 uint32_t tcpi_rcv_mss; 123 uint32_t tcpi_unacked; 124 uint32_t tcpi_sacked; 125 uint32_t tcpi_lost; 126 uint32_t tcpi_retrans; 127 uint32_t tcpi_fackets; 128 /* Times. */ 129 uint32_t tcpi_last_data_sent; 130 uint32_t tcpi_last_ack_sent; /* Not remembered, sorry. */ 131 uint32_t tcpi_last_data_recv; 132 uint32_t tcpi_last_ack_recv; 133 /* Metrics. */ 134 uint32_t tcpi_pmtu; 135 uint32_t tcpi_rcv_ssthresh; 136 uint32_t tcpi_rtt; 137 uint32_t tcpi_rttvar; 138 uint32_t tcpi_snd_ssthresh; 139 uint32_t tcpi_snd_cwnd; 140 uint32_t tcpi_advmss; 141 uint32_t tcpi_reordering; 142 uint32_t tcpi_rcv_rtt; 143 uint32_t tcpi_rcv_space; 144 uint32_t tcpi_total_retrans; 145 uint64_t tcpi_pacing_rate; 146 uint64_t tcpi_max_pacing_rate; 147 uint64_t tcpi_bytes_acked; /* RFC4898 tcpEStatsAppHCThruOctetsAcked */ 148 uint64_t tcpi_bytes_received; /* RFC4898 tcpEStatsAppHCThruOctetsReceived */ 149 150 uint32_t tcpi_segs_out; /* RFC4898 tcpEStatsPerfSegsOut */ 151 uint32_t tcpi_segs_in; /* RFC4898 tcpEStatsPerfSegsIn */ 152 uint32_t tcpi_notsent_bytes; 153 uint32_t tcpi_min_rtt; 154 155 uint32_t tcpi_data_segs_in; /* RFC4898 tcpEStatsDataSegsIn */ 156 uint32_t tcpi_data_segs_out; /* RFC4898 tcpEStatsDataSegsOut */ 157 158 uint64_t tcpi_delivery_rate; 159 uint64_t tcpi_busy_time; /* Time (usec) busy sending data */ 160 uint64_t tcpi_rwnd_limited; /* Time (usec) limited by receive window */ 161 uint64_t tcpi_sndbuf_limited; /* Time (usec) limited by send buffer */ 162 163 uint32_t tcpi_delivered; 164 uint32_t tcpi_delivered_ce; 165 uint64_t tcpi_bytes_sent; /* RFC4898 tcpEStatsPerfHCDataOctetsOut */ 166 uint64_t tcpi_bytes_retrans; /* RFC4898 tcpEStatsPerfOctetsRetrans */ 167 uint32_t tcpi_dsack_dups; /* RFC4898 tcpEStatsStackDSACKDups */ 168 uint32_t tcpi_reord_seen; /* reordering events seen */ 169 socklen_t length; /* Length of struct returned by kernel */ 170 }; 171 172 #ifndef TCP_INFO 173 #define TCP_INFO 11 174 #endif 175 #endif /* GRPC_LINUX_ERRQUEUE */ 176 177 /* Returns true if kernel is capable of supporting errqueue and timestamping. 178 * Currently allowing only linux kernels above 4.0.0 179 */ 180 bool kernel_supports_errqueue(); 181 182 } /* namespace grpc_core */ 183 184 #endif /* GRPC_POSIX_SOCKET_TCP */ 185 186 namespace grpc_core { 187 /* Initializes errqueue support */ 188 void grpc_errqueue_init(); 189 } /* namespace grpc_core */ 190 191 #endif /* GRPC_CORE_LIB_IOMGR_INTERNAL_ERRQUEUE_H */ 192