aboutsummaryrefslogtreecommitdiffstats
path: root/sys/linux/init_iptables.go
diff options
context:
space:
mode:
authorDmitry Vyukov <dvyukov@google.com>2018-02-10 13:23:03 +0100
committerDmitry Vyukov <dvyukov@google.com>2018-02-17 19:02:12 +0100
commit9df1a36a98aaf167993501c32ff7a10a38913f50 (patch)
tree3147f56e0462b9ac2b6c2b1bfeda4332f9c097c5 /sys/linux/init_iptables.go
parent1f693e021993b9ce686952f9f28475684767c458 (diff)
sys/linux: add bridge netfilter support
Diffstat (limited to 'sys/linux/init_iptables.go')
-rw-r--r--sys/linux/init_iptables.go61
1 files changed, 61 insertions, 0 deletions
diff --git a/sys/linux/init_iptables.go b/sys/linux/init_iptables.go
index c33204496..89604e0b1 100644
--- a/sys/linux/init_iptables.go
+++ b/sys/linux/init_iptables.go
@@ -106,3 +106,64 @@ func (arch *arch) generateNetfilterTable(g *prog.Gen, typ prog.Type, old prog.Ar
})
return
}
+
+func (arch *arch) generateEbtables(g *prog.Gen, typ prog.Type, old prog.Arg) (
+ arg prog.Arg, calls []*prog.Call) {
+ if old == nil {
+ arg = g.GenerateSpecialArg(typ, &calls)
+ } else {
+ // TODO(dvyukov): try to restore original hook order after mutation
+ // instead of assigning brand new offsets.
+ arg = old
+ calls = g.MutateArg(arg)
+ }
+ hooksField, entriesField := 4, 7
+ if g.Target().PtrSize == 8 {
+ // Account for paddings.
+ hooksField, entriesField = 5, 9
+ }
+ tableArg := arg.(*prog.UnionArg).Option.(*prog.GroupArg)
+ entriesPtr := tableArg.Inner[entriesField].(*prog.PointerArg)
+ entriesArray := entriesPtr.Res.(*prog.GroupArg)
+ offsets := make([]uint64, len(entriesArray.Inner))
+ var pos, totalEntries uint64
+ for i, entriesArg0 := range entriesArray.Inner {
+ entriesArg := entriesArg0.(*prog.GroupArg)
+ arrayArg := entriesArg.Inner[len(entriesArg.Inner)-1].(*prog.GroupArg)
+ entriesArg.Inner[2].(*prog.ConstArg).Val = totalEntries
+ totalEntries += uint64(len(arrayArg.Inner))
+ offsets[i] = pos
+ pos += entriesArg.Size()
+ }
+ tableArg.Inner[2].(*prog.ConstArg).Val = totalEntries
+ if pos != entriesArray.Size() {
+ panic("netfilter offsets are broken")
+ }
+ // Assign offsets to used hooks.
+ validHooks := tableArg.Inner[1].(*prog.ConstArg).Val
+ hooksArg := tableArg.Inner[hooksField].(*prog.GroupArg)
+ for i, hookArg0 := range hooksArg.Inner {
+ hookArg := hookArg0.(*prog.ConstArg)
+ if validHooks&(1<<uint(i)) == 0 {
+ hookArg.Val = 0
+ continue
+ }
+ addr := g.Target().PhysicalAddr(entriesPtr)
+ if len(offsets) != 0 {
+ addr += offsets[0]
+ offsets = offsets[1:]
+ }
+ hookArg.Val = addr
+ }
+ return
+}
+
+func (arch *arch) sanitizeEbtables(c *prog.Call) {
+ // This is very hacky... just as netfilter interfaces.
+ // setsockopt's len argument must be equal to size of ebt_replace + entries size.
+ lenArg := c.Args[4].(*prog.ConstArg)
+ tableArg := c.Args[3].(*prog.PointerArg).Res.(*prog.UnionArg).Option.(*prog.GroupArg)
+ entriesField := len(tableArg.Inner) - 1
+ entriesArg := tableArg.Inner[entriesField].(*prog.PointerArg).Res
+ lenArg.Val = tableArg.Size() + entriesArg.Size()
+}