mirror of https://github.com/vishvananda/netlink
add actions support for fwfilter
Signed-off-by: chengzhycn <chengzhycn@gmail.com>
This commit is contained in:
parent
8baf7b0c69
commit
d3b8a16e9b
|
@ -349,6 +349,7 @@ type FwFilter struct {
|
|||
InDev string
|
||||
Mask uint32
|
||||
Police *PoliceAction
|
||||
Actions []Action
|
||||
}
|
||||
|
||||
func (filter *FwFilter) Attrs() *FilterAttrs {
|
||||
|
|
|
@ -312,6 +312,10 @@ func (h *Handle) filterModify(filter Filter, flags int) error {
|
|||
native.PutUint32(b, filter.ClassId)
|
||||
options.AddRtAttr(nl.TCA_FW_CLASSID, b)
|
||||
}
|
||||
actionsAttr := options.AddRtAttr(nl.TCA_FW_ACT, nil)
|
||||
if err := EncodeActions(actionsAttr, filter.Actions); err != nil {
|
||||
return err
|
||||
}
|
||||
case *BpfFilter:
|
||||
var bpfFlags uint32
|
||||
if filter.ClassId != 0 {
|
||||
|
@ -861,6 +865,15 @@ func parseFwData(filter Filter, data []syscall.NetlinkRouteAttr) (bool, error) {
|
|||
parsePolice(aattr, &police)
|
||||
}
|
||||
fw.Police = &police
|
||||
case nl.TCA_FW_ACT:
|
||||
tables, err := nl.ParseRouteAttr(datum.Value)
|
||||
if err != nil {
|
||||
return detailed, err
|
||||
}
|
||||
fw.Actions, err = parseActions(tables)
|
||||
if err != nil {
|
||||
return detailed, err
|
||||
}
|
||||
}
|
||||
}
|
||||
return detailed, nil
|
||||
|
|
129
filter_test.go
129
filter_test.go
|
@ -510,6 +510,135 @@ func TestFilterFwAddDel(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestFilterFwActAddDel(t *testing.T) {
|
||||
tearDown := setUpNetlinkTest(t)
|
||||
defer tearDown()
|
||||
if err := LinkAdd(&Ifb{LinkAttrs{Name: "foo"}}); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := LinkAdd(&Ifb{LinkAttrs{Name: "bar"}}); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
link, err := LinkByName("foo")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := LinkSetUp(link); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
redir, err := LinkByName("bar")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := LinkSetUp(redir); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
qdisc := &Ingress{
|
||||
QdiscAttrs: QdiscAttrs{
|
||||
LinkIndex: link.Attrs().Index,
|
||||
Handle: MakeHandle(0xffff, 0),
|
||||
Parent: HANDLE_INGRESS,
|
||||
},
|
||||
}
|
||||
if err := QdiscAdd(qdisc); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
qdiscs, err := SafeQdiscList(link)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if len(qdiscs) != 1 {
|
||||
t.Fatal("Failed to add qdisc")
|
||||
}
|
||||
_, ok := qdiscs[0].(*Ingress)
|
||||
if !ok {
|
||||
t.Fatal("Qdisc is the wrong type")
|
||||
}
|
||||
|
||||
classId := MakeHandle(1, 1)
|
||||
filter := &FwFilter{
|
||||
FilterAttrs: FilterAttrs{
|
||||
LinkIndex: link.Attrs().Index,
|
||||
Parent: MakeHandle(0xffff, 0),
|
||||
Priority: 1,
|
||||
Protocol: unix.ETH_P_ALL,
|
||||
Handle: MakeHandle(0, 0x6),
|
||||
},
|
||||
ClassId: classId,
|
||||
Actions: []Action{
|
||||
&MirredAction{
|
||||
ActionAttrs: ActionAttrs{
|
||||
Action: TC_ACT_STOLEN,
|
||||
},
|
||||
MirredAction: TCA_EGRESS_REDIR,
|
||||
Ifindex: redir.Attrs().Index,
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
if err := FilterAdd(filter); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
filters, err := FilterList(link, MakeHandle(0xffff, 0))
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if len(filters) != 1 {
|
||||
t.Fatal("Failed to add filter")
|
||||
}
|
||||
fw, ok := filters[0].(*FwFilter)
|
||||
if !ok {
|
||||
t.Fatal("Filter is the wrong type")
|
||||
}
|
||||
|
||||
if len(fw.Actions) != 1 {
|
||||
t.Fatalf("Too few Actions in filter")
|
||||
}
|
||||
if fw.ClassId != classId {
|
||||
t.Fatalf("ClassId of the filter is the wrong value")
|
||||
}
|
||||
|
||||
mia, ok := fw.Actions[0].(*MirredAction)
|
||||
if !ok {
|
||||
t.Fatal("Unable to find mirred action")
|
||||
}
|
||||
|
||||
if mia.Attrs().Action != TC_ACT_STOLEN {
|
||||
t.Fatal("Mirred action isn't TC_ACT_STOLEN")
|
||||
}
|
||||
|
||||
if mia.MirredAction != TCA_EGRESS_REDIR {
|
||||
t.Fatal("MirredAction isn't TCA_EGRESS_REDIR")
|
||||
}
|
||||
|
||||
if mia.Ifindex != redir.Attrs().Index {
|
||||
t.Fatal("Unmatched redirect index")
|
||||
}
|
||||
|
||||
if err := FilterDel(filter); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
filters, err = FilterList(link, MakeHandle(0xffff, 0))
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if len(filters) != 0 {
|
||||
t.Fatal("Failed to remove filter")
|
||||
}
|
||||
|
||||
if err := QdiscDel(qdisc); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
qdiscs, err = SafeQdiscList(link)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if len(qdiscs) != 0 {
|
||||
t.Fatal("Failed to remove qdisc")
|
||||
}
|
||||
}
|
||||
|
||||
func TestFilterU32BpfAddDel(t *testing.T) {
|
||||
t.Skipf("Fd does not match in ci")
|
||||
tearDown := setUpNetlinkTest(t)
|
||||
|
|
Loading…
Reference in New Issue