Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions fake_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -667,6 +667,8 @@ func TestFakeParseDump(t *testing.T) {
dump: `
add table ip test
add flowtable ip test myflowtable { hook ingress priority filter ; devices = { eth0, eth1 } ; }
add flowtable ip test countedflowtable { hook ingress priority filter ; devices = { eth2 } ; counter ; }
add flowtable ip test nodevflowtable { hook ingress priority filter ; counter ; }
add chain ip test anotherchain
add chain ip test chain { comment "foo" ; }
add map ip test map1 { type ipv4_addr . inet_proto . inet_service ; }
Expand Down
12 changes: 10 additions & 2 deletions objects.go
Original file line number Diff line number Diff line change
Expand Up @@ -730,15 +730,20 @@ func (flowtable *Flowtable) writeOperation(verb verb, ctx *nftContext, writer io
fmt.Fprintf(writer, " devices = { %s } ;", strings.Join(flowtable.Devices, ", "))
}

if flowtable.Counter != nil && *flowtable.Counter {
fmt.Fprintf(writer, " counter ;")
}

fmt.Fprintf(writer, " }")
}

fmt.Fprintf(writer, "\n")
}

// nft add flowtable inet example_table example_flowtable { hook ingress priority filter ; devices = { eth0 }; }
// nft add flowtable inet example_table example_flowtable { hook ingress priority filter ; devices = { eth0 } ; counter ; }
// Every property is optional, so a flowtable may have a counter and no devices.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is that true? The man page claims devices is required.

Though, I guess, my nft man page doesn't mention flowtable counters...

@caseydavenport caseydavenport Sep 1, 2026 •

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yep! At least in my local verification, I was able to create tables without devices but with counter set. Not sure why that would be useful, though.

var flowtableRegexp = regexp.MustCompile(fmt.Sprintf(
`%s(?: {(?: hook ingress priority %s ;)(?: devices = {(.*)} ;) })?`,
`%s(?: {(?: hook ingress priority %s ;)?(?: devices = {(.*)} ;)?( counter ;)? })?`,
noSpaceGroup, noSpaceGroup))

func (flowtable *Flowtable) parse(family Family, table, line string) error {
Expand All @@ -764,6 +769,9 @@ func (flowtable *Flowtable) parse(family Family, table, line string) error {
flowtable.Devices = devices
}
}
if match[4] != "" {
flowtable.Counter = PtrTo(true)
}
return nil
}

Expand Down
21 changes: 21 additions & 0 deletions objects_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -167,6 +167,27 @@ func TestObjects(t *testing.T) {
},
out: `create flowtable ip mytable myflowtable { hook ingress priority filter ; devices = { eth0, eth1 } ; }`,
},
{
name: "create flowtable with counter",
verb: createVerb,
object: &Flowtable{
Name: "myflowtable",
Priority: PtrTo(FilterIngressPriority),
Devices: []string{"eth0", "eth1"},
Counter: PtrTo(true),
},
out: `create flowtable ip mytable myflowtable { hook ingress priority filter ; devices = { eth0, eth1 } ; counter ; }`,
},
{
name: "create flowtable with counter and no devices",
verb: createVerb,
object: &Flowtable{
Name: "myflowtable",
Priority: PtrTo(FilterIngressPriority),
Counter: PtrTo(true),
},
out: `create flowtable ip mytable myflowtable { hook ingress priority filter ; counter ; }`,
},
{
name: "flush flowtable",
verb: flushVerb,
Expand Down
4 changes: 4 additions & 0 deletions types.go
Original file line number Diff line number Diff line change
Expand Up @@ -496,6 +496,10 @@ type Flowtable struct {
// that should be offloaded.
Devices []string

// Counter enables packet and byte accounting for offloaded flows.
// (Optional; requires kernel 5.13 or later)
Counter *bool

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How do you read the counter?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The flowtable counter just indicates that conntrack metrics should continue to be updated based on the offloaded flows (whereas normally they are not) - so we read them from there.


// Handle is an identifier that can be used to uniquely identify an object when
// deleting it. When adding a new object, this must be nil
Handle *int
Expand Down
Loading