segment_bench_test.go 1.7 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465
  1. //go:build linux && !android && !e2e_testing
  2. package tio
  3. import "testing"
  4. // fakeBatch stands in for batch.TxBatcher inside the bench — same shape
  5. // of pointer-capturing closure that sendInsideMessage builds.
  6. type fakeBatch struct{ buf [65536]byte }
  7. func (b *fakeBatch) Reserve(sz int) []byte { return b.buf[:sz] }
  8. func (b *fakeBatch) Commit([]byte) {}
  9. type fakeHostInfo struct {
  10. remoteIndexId uint32
  11. counter uint64
  12. }
  13. type fakeIface struct {
  14. rebindCount uint8
  15. hi *fakeHostInfo
  16. }
  17. // BenchmarkSegmentSuperpacketAllocsTSO measures allocation per
  18. // SegmentSuperpacket call when a closure captures pointer-bearing
  19. // receivers — the realistic shape of sendInsideMessage's closure.
  20. func BenchmarkSegmentSuperpacketAllocsTSO(b *testing.B) {
  21. const mss = 1400
  22. const numSeg = 32
  23. pkt := buildTSOv6(mss*numSeg, mss)
  24. gso := GSOInfo{
  25. Size: mss,
  26. HdrLen: 60, // 40 (IPv6) + 20 (TCP)
  27. CsumStart: 40,
  28. Proto: GSOProtoTCP,
  29. }
  30. p := Packet{Bytes: pkt, GSO: gso}
  31. hi := &fakeHostInfo{remoteIndexId: 0xdeadbeef}
  32. f := &fakeIface{rebindCount: 7, hi: hi}
  33. fb := &fakeBatch{}
  34. // SegmentSuperpacket consumes pkt destructively; refresh from a master
  35. // copy each iter (matches the production pattern where every TUN read
  36. // hands the segmenter a fresh kernel-supplied buffer).
  37. master := append([]byte(nil), pkt...)
  38. work := make([]byte, len(pkt))
  39. p.Bytes = work
  40. b.ReportAllocs()
  41. b.ResetTimer()
  42. for i := 0; i < b.N; i++ {
  43. copy(work, master)
  44. err := SegmentSuperpacket(p, func(seg []byte) error {
  45. out := fb.Reserve(16 + len(seg) + 16)
  46. out[0] = byte(f.rebindCount)
  47. out[1] = byte(hi.counter)
  48. hi.counter++
  49. fb.Commit(out)
  50. return nil
  51. })
  52. if err != nil {
  53. b.Fatalf("SegmentSuperpacket: %v", err)
  54. }
  55. }
  56. }