github.com/cilium/cilium@v1.16.2/pkg/maps/act/act.go (about)

     1  // SPDX-License-Identifier: Apache-2.0
     2  // Copyright Authors of Cilium
     3  
     4  package act
     5  
     6  import (
     7  	"fmt"
     8  	"strconv"
     9  
    10  	"github.com/cilium/hive/cell"
    11  	"github.com/spf13/pflag"
    12  
    13  	"github.com/cilium/cilium/pkg/bpf"
    14  	"github.com/cilium/cilium/pkg/byteorder"
    15  	"github.com/cilium/cilium/pkg/datapath/linux/config/defines"
    16  	"github.com/cilium/cilium/pkg/ebpf"
    17  	"github.com/cilium/cilium/pkg/option"
    18  	"github.com/cilium/cilium/pkg/service"
    19  )
    20  
    21  const ActiveConnectionTrackingMapName = "cilium_lb_act"
    22  
    23  // Cell provides the ActiveConnectionTrackingMap which contains information about opened
    24  // and closed connection to each service-zone pair.
    25  var Cell = cell.Module(
    26  	"active-connection-tracking",
    27  	"eBPF map with counts of open-closed connections for each service-zone pair",
    28  
    29  	cell.Provide(newActiveConnectionTrackingMap),
    30  	cell.Config(defaultConfig),
    31  )
    32  
    33  type Config struct {
    34  	EnableActiveConnectionTracking bool
    35  }
    36  
    37  func (c Config) Flags(fs *pflag.FlagSet) {
    38  	fs.Bool("enable-active-connection-tracking", defaultConfig.EnableActiveConnectionTracking,
    39  		"Count open and active connections to services, grouped by zones defined in fixed-zone-mapping.")
    40  }
    41  
    42  var defaultConfig = Config{
    43  	EnableActiveConnectionTracking: false,
    44  }
    45  
    46  type ActiveConnectionTrackingIterateCallback func(*ActiveConnectionTrackerKey, *ActiveConnectionTrackerValue)
    47  
    48  type ActiveConnectionTrackingMap interface {
    49  	IterateWithCallback(ActiveConnectionTrackingIterateCallback) error
    50  }
    51  
    52  type actMap struct {
    53  	m *bpf.Map
    54  }
    55  
    56  func newActiveConnectionTrackingMap(in struct {
    57  	cell.In
    58  
    59  	Lifecycle cell.Lifecycle
    60  	Conf      Config
    61  }) (out struct {
    62  	cell.Out
    63  
    64  	bpf.MapOut[ActiveConnectionTrackingMap]
    65  	defines.NodeOut
    66  }) {
    67  	if !in.Conf.EnableActiveConnectionTracking {
    68  		return
    69  	}
    70  	size := option.Config.LBServiceMapEntries * len(option.Config.FixedZoneMapping)
    71  	if size == 0 {
    72  		return
    73  	}
    74  
    75  	out.NodeDefines = map[string]string{
    76  		"ENABLE_ACTIVE_CONNECTION_TRACKING": "1",
    77  		"LB_ACT_MAP":                        ActiveConnectionTrackingMapName,
    78  		"CILIUM_LB_ACT_MAP_MAX_ENTRIES":     strconv.Itoa(size),
    79  	}
    80  
    81  	out.MapOut = bpf.NewMapOut(ActiveConnectionTrackingMap(createActiveConnectionTrackingMap(in.Lifecycle, size)))
    82  	return
    83  }
    84  
    85  func createActiveConnectionTrackingMap(lc cell.Lifecycle, size int) *actMap {
    86  	m := bpf.NewMap(ActiveConnectionTrackingMapName,
    87  		ebpf.LRUHash,
    88  		&ActiveConnectionTrackerKey{},
    89  		&ActiveConnectionTrackerValue{},
    90  		size,
    91  		0,
    92  	)
    93  
    94  	lc.Append(cell.Hook{
    95  		OnStart: func(context cell.HookContext) error {
    96  			return m.OpenOrCreate()
    97  		},
    98  		OnStop: func(context cell.HookContext) error {
    99  			return m.Close()
   100  		},
   101  	})
   102  
   103  	return &actMap{m}
   104  }
   105  
   106  func (m actMap) IterateWithCallback(cb ActiveConnectionTrackingIterateCallback) error {
   107  	return m.m.DumpWithCallback(func(k bpf.MapKey, v bpf.MapValue) {
   108  		key := k.(*ActiveConnectionTrackerKey)
   109  		value := v.(*ActiveConnectionTrackerValue)
   110  
   111  		cb(key, value)
   112  	})
   113  }
   114  
   115  // ActiveConnectionTrackerKey is the key to ActiveConnectionTrackingMap.
   116  //
   117  // It must match 'struct lb_act_key' in "bpf/lib/act.h".
   118  type ActiveConnectionTrackerKey struct {
   119  	SvcID uint16 `align:"svc_id"`
   120  	Zone  uint8  `align:"zone"`
   121  	Pad   uint8  `align:"pad"`
   122  }
   123  
   124  func (s *ActiveConnectionTrackerKey) New() bpf.MapKey { return &ActiveConnectionTrackerKey{} }
   125  
   126  func (v *ActiveConnectionTrackerKey) String() string {
   127  	svcID := byteorder.HostToNetwork16(v.SvcID)
   128  	if svcAddr, err := service.GetID(uint32(svcID)); err == nil && svcAddr != nil {
   129  		return fmt.Sprintf("%s[%s]", svcAddr.String(), option.Config.GetZone(v.Zone))
   130  	}
   131  	return fmt.Sprintf("%d[%s]", svcID, option.Config.GetZone(v.Zone))
   132  }
   133  
   134  // ActiveConnectionTrackerValue is the value in ActiveConnectionTrackingMap.
   135  //
   136  // It must match 'struct lb_act_value' in "bpf/lib/act.h".
   137  type ActiveConnectionTrackerValue struct {
   138  	Opened uint32 `align:"opened"`
   139  	Closed uint32 `align:"closed"`
   140  }
   141  
   142  func (s *ActiveConnectionTrackerValue) New() bpf.MapValue { return &ActiveConnectionTrackerValue{} }
   143  
   144  func (s *ActiveConnectionTrackerValue) String() string {
   145  	return fmt.Sprintf("+%d -%d", s.Opened, s.Closed)
   146  }