From 3f8dec4d6ed5b3750d63e0f9e3b9f7fca3643108 Mon Sep 17 00:00:00 2001 From: Rafael Campos Date: Mon, 8 Aug 2022 14:48:53 +0200 Subject: [PATCH] Fix Meta unmarshal when is Source Register The Meta nftables expression was not filling the Register and SourceRegister fields when unmarshalling. Add a check for NFTA_META_SREG message when unmarshalling to fill the Meta fields. Add Unit Test for source and destination unmarshall. Signed-off-by: Rafael Campos --- expr/expr.go | 3 +++ expr/meta_test.go | 62 +++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 65 insertions(+) create mode 100644 expr/meta_test.go diff --git a/expr/expr.go b/expr/expr.go index 746d45b..2f342be 100644 --- a/expr/expr.go +++ b/expr/expr.go @@ -243,6 +243,9 @@ func (e *Meta) unmarshal(fam byte, data []byte) error { ad.ByteOrder = binary.BigEndian for ad.Next() { switch ad.Type() { + case unix.NFTA_META_SREG: + e.Register = ad.Uint32() + e.SourceRegister = true case unix.NFTA_META_DREG: e.Register = ad.Uint32() case unix.NFTA_META_KEY: diff --git a/expr/meta_test.go b/expr/meta_test.go new file mode 100644 index 0000000..b309f9f --- /dev/null +++ b/expr/meta_test.go @@ -0,0 +1,62 @@ +package expr + +import ( + "encoding/binary" + "reflect" + "testing" + + "github.com/mdlayher/netlink" + "golang.org/x/sys/unix" +) + +func TestMeta(t *testing.T) { + t.Parallel() + tests := []struct { + name string + meta Meta + }{ + { + name: "Unmarshal Meta DestRegister case", + meta: Meta{ + Key: 1, + SourceRegister: false, + Register: 1, + }, + }, + { + name: "Unmarshal Meta SourceRegister case", + meta: Meta{ + Key: 1, + SourceRegister: true, + Register: 1, + }, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + nMeta := Meta{} + data, err := tt.meta.marshal(0 /* don't care in this test */) + if err != nil { + t.Fatalf("marshal error: %+v", err) + + } + ad, err := netlink.NewAttributeDecoder(data) + if err != nil { + t.Fatalf("NewAttributeDecoder() error: %+v", err) + } + ad.ByteOrder = binary.BigEndian + for ad.Next() { + if ad.Type() == unix.NFTA_EXPR_DATA { + if err := nMeta.unmarshal(0, ad.Bytes()); err != nil { + t.Errorf("unmarshal error: %+v", err) + break + } + } + } + if !reflect.DeepEqual(tt.meta, nMeta) { + t.Fatalf("original %+v and recovered %+v Exthdr structs are different", tt.meta, nMeta) + } + }) + } +}