github.com/sagernet/netlink@v0.0.0-20240612041022-b9a21c07ac6a/tcp_linux.go (about)

     1  package netlink
     2  
     3  import (
     4  	"bytes"
     5  	"errors"
     6  	"io"
     7  )
     8  
     9  const (
    10  	tcpBBRInfoLen = 20
    11  )
    12  
    13  func checkDeserErr(err error) error {
    14  	if err == io.EOF {
    15  		return nil
    16  	}
    17  	return err
    18  }
    19  
    20  func (t *TCPInfo) deserialize(b []byte) error {
    21  	var err error
    22  	rb := bytes.NewBuffer(b)
    23  
    24  	t.State, err = rb.ReadByte()
    25  	if err != nil {
    26  		return checkDeserErr(err)
    27  	}
    28  
    29  	t.Ca_state, err = rb.ReadByte()
    30  	if err != nil {
    31  		return checkDeserErr(err)
    32  	}
    33  
    34  	t.Retransmits, err = rb.ReadByte()
    35  	if err != nil {
    36  		return checkDeserErr(err)
    37  	}
    38  
    39  	t.Probes, err = rb.ReadByte()
    40  	if err != nil {
    41  		return checkDeserErr(err)
    42  	}
    43  
    44  	t.Backoff, err = rb.ReadByte()
    45  	if err != nil {
    46  		return checkDeserErr(err)
    47  	}
    48  	t.Options, err = rb.ReadByte()
    49  	if err != nil {
    50  		return checkDeserErr(err)
    51  	}
    52  
    53  	scales, err := rb.ReadByte()
    54  	if err != nil {
    55  		return checkDeserErr(err)
    56  	}
    57  	t.Snd_wscale = scales >> 4  // first 4 bits
    58  	t.Rcv_wscale = scales & 0xf // last 4 bits
    59  
    60  	rateLimAndFastOpen, err := rb.ReadByte()
    61  	if err != nil {
    62  		return checkDeserErr(err)
    63  	}
    64  	t.Delivery_rate_app_limited = rateLimAndFastOpen >> 7 // get first bit
    65  	t.Fastopen_client_fail = rateLimAndFastOpen >> 5 & 3  // get next two bits
    66  
    67  	next := rb.Next(4)
    68  	if len(next) == 0 {
    69  		return nil
    70  	}
    71  	t.Rto = native.Uint32(next)
    72  
    73  	next = rb.Next(4)
    74  	if len(next) == 0 {
    75  		return nil
    76  	}
    77  	t.Ato = native.Uint32(next)
    78  
    79  	next = rb.Next(4)
    80  	if len(next) == 0 {
    81  		return nil
    82  	}
    83  	t.Snd_mss = native.Uint32(next)
    84  
    85  	next = rb.Next(4)
    86  	if len(next) == 0 {
    87  		return nil
    88  	}
    89  	t.Rcv_mss = native.Uint32(next)
    90  
    91  	next = rb.Next(4)
    92  	if len(next) == 0 {
    93  		return nil
    94  	}
    95  	t.Unacked = native.Uint32(next)
    96  
    97  	next = rb.Next(4)
    98  	if len(next) == 0 {
    99  		return nil
   100  	}
   101  	t.Sacked = native.Uint32(next)
   102  
   103  	next = rb.Next(4)
   104  	if len(next) == 0 {
   105  		return nil
   106  	}
   107  	t.Lost = native.Uint32(next)
   108  
   109  	next = rb.Next(4)
   110  	if len(next) == 0 {
   111  		return nil
   112  	}
   113  	t.Retrans = native.Uint32(next)
   114  
   115  	next = rb.Next(4)
   116  	if len(next) == 0 {
   117  		return nil
   118  	}
   119  	t.Fackets = native.Uint32(next)
   120  
   121  	next = rb.Next(4)
   122  	if len(next) == 0 {
   123  		return nil
   124  	}
   125  	t.Last_data_sent = native.Uint32(next)
   126  
   127  	next = rb.Next(4)
   128  	if len(next) == 0 {
   129  		return nil
   130  	}
   131  	t.Last_ack_sent = native.Uint32(next)
   132  
   133  	next = rb.Next(4)
   134  	if len(next) == 0 {
   135  		return nil
   136  	}
   137  	t.Last_data_recv = native.Uint32(next)
   138  
   139  	next = rb.Next(4)
   140  	if len(next) == 0 {
   141  		return nil
   142  	}
   143  	t.Last_ack_recv = native.Uint32(next)
   144  
   145  	next = rb.Next(4)
   146  	if len(next) == 0 {
   147  		return nil
   148  	}
   149  	t.Pmtu = native.Uint32(next)
   150  
   151  	next = rb.Next(4)
   152  	if len(next) == 0 {
   153  		return nil
   154  	}
   155  	t.Rcv_ssthresh = native.Uint32(next)
   156  
   157  	next = rb.Next(4)
   158  	if len(next) == 0 {
   159  		return nil
   160  	}
   161  	t.Rtt = native.Uint32(next)
   162  
   163  	next = rb.Next(4)
   164  	if len(next) == 0 {
   165  		return nil
   166  	}
   167  	t.Rttvar = native.Uint32(next)
   168  
   169  	next = rb.Next(4)
   170  	if len(next) == 0 {
   171  		return nil
   172  	}
   173  	t.Snd_ssthresh = native.Uint32(next)
   174  
   175  	next = rb.Next(4)
   176  	if len(next) == 0 {
   177  		return nil
   178  	}
   179  	t.Snd_cwnd = native.Uint32(next)
   180  
   181  	next = rb.Next(4)
   182  	if len(next) == 0 {
   183  		return nil
   184  	}
   185  	t.Advmss = native.Uint32(next)
   186  
   187  	next = rb.Next(4)
   188  	if len(next) == 0 {
   189  		return nil
   190  	}
   191  	t.Reordering = native.Uint32(next)
   192  
   193  	next = rb.Next(4)
   194  	if len(next) == 0 {
   195  		return nil
   196  	}
   197  	t.Rcv_rtt = native.Uint32(next)
   198  
   199  	next = rb.Next(4)
   200  	if len(next) == 0 {
   201  		return nil
   202  	}
   203  	t.Rcv_space = native.Uint32(next)
   204  
   205  	next = rb.Next(4)
   206  	if len(next) == 0 {
   207  		return nil
   208  	}
   209  	t.Total_retrans = native.Uint32(next)
   210  
   211  	next = rb.Next(8)
   212  	if len(next) == 0 {
   213  		return nil
   214  	}
   215  	t.Pacing_rate = native.Uint64(next)
   216  
   217  	next = rb.Next(8)
   218  	if len(next) == 0 {
   219  		return nil
   220  	}
   221  	t.Max_pacing_rate = native.Uint64(next)
   222  
   223  	next = rb.Next(8)
   224  	if len(next) == 0 {
   225  		return nil
   226  	}
   227  	t.Bytes_acked = native.Uint64(next)
   228  
   229  	next = rb.Next(8)
   230  	if len(next) == 0 {
   231  		return nil
   232  	}
   233  	t.Bytes_received = native.Uint64(next)
   234  
   235  	next = rb.Next(4)
   236  	if len(next) == 0 {
   237  		return nil
   238  	}
   239  	t.Segs_out = native.Uint32(next)
   240  
   241  	next = rb.Next(4)
   242  	if len(next) == 0 {
   243  		return nil
   244  	}
   245  	t.Segs_in = native.Uint32(next)
   246  	next = rb.Next(4)
   247  	if len(next) == 0 {
   248  		return nil
   249  	}
   250  	t.Notsent_bytes = native.Uint32(next)
   251  	next = rb.Next(4)
   252  	if len(next) == 0 {
   253  		return nil
   254  	}
   255  	t.Min_rtt = native.Uint32(next)
   256  	next = rb.Next(4)
   257  	if len(next) == 0 {
   258  		return nil
   259  	}
   260  	t.Data_segs_in = native.Uint32(next)
   261  	next = rb.Next(4)
   262  	if len(next) == 0 {
   263  		return nil
   264  	}
   265  	t.Data_segs_out = native.Uint32(next)
   266  
   267  	next = rb.Next(8)
   268  	if len(next) == 0 {
   269  		return nil
   270  	}
   271  	t.Delivery_rate = native.Uint64(next)
   272  
   273  	next = rb.Next(8)
   274  	if len(next) == 0 {
   275  		return nil
   276  	}
   277  	t.Busy_time = native.Uint64(next)
   278  
   279  	next = rb.Next(8)
   280  	if len(next) == 0 {
   281  		return nil
   282  	}
   283  	t.Rwnd_limited = native.Uint64(next)
   284  
   285  	next = rb.Next(8)
   286  	if len(next) == 0 {
   287  		return nil
   288  	}
   289  	t.Sndbuf_limited = native.Uint64(next)
   290  
   291  	next = rb.Next(4)
   292  	if len(next) == 0 {
   293  		return nil
   294  	}
   295  	t.Delivered = native.Uint32(next)
   296  
   297  	next = rb.Next(4)
   298  	if len(next) == 0 {
   299  		return nil
   300  	}
   301  	t.Delivered_ce = native.Uint32(next)
   302  
   303  	next = rb.Next(8)
   304  	if len(next) == 0 {
   305  		return nil
   306  	}
   307  	t.Bytes_sent = native.Uint64(next)
   308  
   309  	next = rb.Next(8)
   310  	if len(next) == 0 {
   311  		return nil
   312  	}
   313  	t.Bytes_retrans = native.Uint64(next)
   314  
   315  	next = rb.Next(4)
   316  	if len(next) == 0 {
   317  		return nil
   318  	}
   319  	t.Dsack_dups = native.Uint32(next)
   320  
   321  	next = rb.Next(4)
   322  	if len(next) == 0 {
   323  		return nil
   324  	}
   325  	t.Reord_seen = native.Uint32(next)
   326  
   327  	next = rb.Next(4)
   328  	if len(next) == 0 {
   329  		return nil
   330  	}
   331  	t.Rcv_ooopack = native.Uint32(next)
   332  
   333  	next = rb.Next(4)
   334  	if len(next) == 0 {
   335  		return nil
   336  	}
   337  	t.Snd_wnd = native.Uint32(next)
   338  	return nil
   339  }
   340  
   341  func (t *TCPBBRInfo) deserialize(b []byte) error {
   342  	if len(b) != tcpBBRInfoLen {
   343  		return errors.New("Invalid length")
   344  	}
   345  
   346  	rb := bytes.NewBuffer(b)
   347  	t.BBRBW = native.Uint64(rb.Next(8))
   348  	t.BBRMinRTT = native.Uint32(rb.Next(4))
   349  	t.BBRPacingGain = native.Uint32(rb.Next(4))
   350  	t.BBRCwndGain = native.Uint32(rb.Next(4))
   351  
   352  	return nil
   353  }