mirror of
https://github.com/netbirdio/gvisor.git
synced 2026-05-22 17:12:49 -07:00
Cleanup iptables bug TODOs
There are many references to unimplemented iptables features that link to #170, but that bug is about Istio support specifically. Istio is supported, so the references should change. Some TODOs are addressed, some removed because they are not features requested by users, and some are left as implementation notes. Fixes #170. PiperOrigin-RevId: 379328488
This commit is contained in:
committed by
gVisor bot
parent
b720bcb6f6
commit
9c7ff24fe6
@@ -852,15 +852,13 @@ func (t *Task) SetOOMScoreAdj(adj int32) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
// UID returns t's uid.
|
||||
// TODO(gvisor.dev/issue/170): This method is not namespaced yet.
|
||||
func (t *Task) UID() uint32 {
|
||||
// KUID returns t's kuid.
|
||||
func (t *Task) KUID() uint32 {
|
||||
return uint32(t.Credentials().EffectiveKUID)
|
||||
}
|
||||
|
||||
// GID returns t's gid.
|
||||
// TODO(gvisor.dev/issue/170): This method is not namespaced yet.
|
||||
func (t *Task) GID() uint32 {
|
||||
// KGID returns t's kgid.
|
||||
func (t *Task) KGID() uint32 {
|
||||
return uint32(t.Credentials().EffectiveKGID)
|
||||
}
|
||||
|
||||
|
||||
@@ -25,6 +25,7 @@ go_library(
|
||||
"//pkg/log",
|
||||
"//pkg/marshal",
|
||||
"//pkg/sentry/kernel",
|
||||
"//pkg/sentry/kernel/auth",
|
||||
"//pkg/syserr",
|
||||
"//pkg/tcpip",
|
||||
"//pkg/tcpip/header",
|
||||
|
||||
@@ -19,20 +19,12 @@ import (
|
||||
|
||||
"gvisor.dev/gvisor/pkg/abi/linux"
|
||||
"gvisor.dev/gvisor/pkg/bits"
|
||||
"gvisor.dev/gvisor/pkg/sentry/kernel"
|
||||
"gvisor.dev/gvisor/pkg/syserr"
|
||||
"gvisor.dev/gvisor/pkg/tcpip"
|
||||
"gvisor.dev/gvisor/pkg/tcpip/stack"
|
||||
)
|
||||
|
||||
// TODO(gvisor.dev/issue/170): The following per-matcher params should be
|
||||
// supported:
|
||||
// - Table name
|
||||
// - Match size
|
||||
// - User size
|
||||
// - Hooks
|
||||
// - Proto
|
||||
// - Family
|
||||
|
||||
// matchMaker knows how to (un)marshal the matcher named name().
|
||||
type matchMaker interface {
|
||||
// name is the matcher name as stored in the xt_entry_match struct.
|
||||
@@ -43,7 +35,7 @@ type matchMaker interface {
|
||||
|
||||
// unmarshal converts from the ABI matcher struct to an
|
||||
// stack.Matcher.
|
||||
unmarshal(buf []byte, filter stack.IPHeaderFilter) (stack.Matcher, error)
|
||||
unmarshal(task *kernel.Task, buf []byte, filter stack.IPHeaderFilter) (stack.Matcher, error)
|
||||
}
|
||||
|
||||
type matcher interface {
|
||||
@@ -94,12 +86,12 @@ func marshalEntryMatch(name string, data []byte) []byte {
|
||||
return buf
|
||||
}
|
||||
|
||||
func unmarshalMatcher(match linux.XTEntryMatch, filter stack.IPHeaderFilter, buf []byte) (stack.Matcher, error) {
|
||||
func unmarshalMatcher(task *kernel.Task, match linux.XTEntryMatch, filter stack.IPHeaderFilter, buf []byte) (stack.Matcher, error) {
|
||||
matchMaker, ok := matchMakers[match.Name.String()]
|
||||
if !ok {
|
||||
return nil, fmt.Errorf("unsupported matcher with name %q", match.Name.String())
|
||||
}
|
||||
return matchMaker.unmarshal(buf, filter)
|
||||
return matchMaker.unmarshal(task, buf, filter)
|
||||
}
|
||||
|
||||
// targetMaker knows how to (un)marshal a target. Once registered,
|
||||
|
||||
@@ -18,6 +18,7 @@ import (
|
||||
"fmt"
|
||||
|
||||
"gvisor.dev/gvisor/pkg/abi/linux"
|
||||
"gvisor.dev/gvisor/pkg/sentry/kernel"
|
||||
"gvisor.dev/gvisor/pkg/syserr"
|
||||
"gvisor.dev/gvisor/pkg/tcpip"
|
||||
"gvisor.dev/gvisor/pkg/tcpip/header"
|
||||
@@ -123,7 +124,7 @@ func getEntries4(table stack.Table, tablename linux.TableName) (linux.KernelIPTG
|
||||
return entries, info
|
||||
}
|
||||
|
||||
func modifyEntries4(stk *stack.Stack, optVal []byte, replace *linux.IPTReplace, table *stack.Table) (map[uint32]int, *syserr.Error) {
|
||||
func modifyEntries4(task *kernel.Task, stk *stack.Stack, optVal []byte, replace *linux.IPTReplace, table *stack.Table) (map[uint32]int, *syserr.Error) {
|
||||
nflog("set entries: setting entries in table %q", replace.Name.String())
|
||||
|
||||
// Convert input into a list of rules and their offsets.
|
||||
@@ -148,23 +149,19 @@ func modifyEntries4(stk *stack.Stack, optVal []byte, replace *linux.IPTReplace,
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
}
|
||||
|
||||
// TODO(gvisor.dev/issue/170): We should support more IPTIP
|
||||
// filtering fields.
|
||||
filter, err := filterFromIPTIP(entry.IP)
|
||||
if err != nil {
|
||||
nflog("bad iptip: %v", err)
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
}
|
||||
|
||||
// TODO(gvisor.dev/issue/170): Matchers and targets can specify
|
||||
// that they only work for certain protocols, hooks, tables.
|
||||
// Get matchers.
|
||||
matchersSize := entry.TargetOffset - linux.SizeOfIPTEntry
|
||||
if len(optVal) < int(matchersSize) {
|
||||
nflog("entry doesn't have enough room for its matchers (only %d bytes remain)", len(optVal))
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
}
|
||||
matchers, err := parseMatchers(filter, optVal[:matchersSize])
|
||||
matchers, err := parseMatchers(task, filter, optVal[:matchersSize])
|
||||
if err != nil {
|
||||
nflog("failed to parse matchers: %v", err)
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
|
||||
@@ -18,6 +18,7 @@ import (
|
||||
"fmt"
|
||||
|
||||
"gvisor.dev/gvisor/pkg/abi/linux"
|
||||
"gvisor.dev/gvisor/pkg/sentry/kernel"
|
||||
"gvisor.dev/gvisor/pkg/syserr"
|
||||
"gvisor.dev/gvisor/pkg/tcpip"
|
||||
"gvisor.dev/gvisor/pkg/tcpip/header"
|
||||
@@ -126,7 +127,7 @@ func getEntries6(table stack.Table, tablename linux.TableName) (linux.KernelIP6T
|
||||
return entries, info
|
||||
}
|
||||
|
||||
func modifyEntries6(stk *stack.Stack, optVal []byte, replace *linux.IPTReplace, table *stack.Table) (map[uint32]int, *syserr.Error) {
|
||||
func modifyEntries6(task *kernel.Task, stk *stack.Stack, optVal []byte, replace *linux.IPTReplace, table *stack.Table) (map[uint32]int, *syserr.Error) {
|
||||
nflog("set entries: setting entries in table %q", replace.Name.String())
|
||||
|
||||
// Convert input into a list of rules and their offsets.
|
||||
@@ -151,23 +152,19 @@ func modifyEntries6(stk *stack.Stack, optVal []byte, replace *linux.IPTReplace,
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
}
|
||||
|
||||
// TODO(gvisor.dev/issue/170): We should support more IPTIP
|
||||
// filtering fields.
|
||||
filter, err := filterFromIP6TIP(entry.IPv6)
|
||||
if err != nil {
|
||||
nflog("bad iptip: %v", err)
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
}
|
||||
|
||||
// TODO(gvisor.dev/issue/170): Matchers and targets can specify
|
||||
// that they only work for certain protocols, hooks, tables.
|
||||
// Get matchers.
|
||||
matchersSize := entry.TargetOffset - linux.SizeOfIP6TEntry
|
||||
if len(optVal) < int(matchersSize) {
|
||||
nflog("entry doesn't have enough room for its matchers (only %d bytes remain)", len(optVal))
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
}
|
||||
matchers, err := parseMatchers(filter, optVal[:matchersSize])
|
||||
matchers, err := parseMatchers(task, filter, optVal[:matchersSize])
|
||||
if err != nil {
|
||||
nflog("failed to parse matchers: %v", err)
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
|
||||
@@ -174,13 +174,12 @@ func setHooksAndUnderflow(info *linux.IPTGetinfo, table stack.Table, offset uint
|
||||
|
||||
// SetEntries sets iptables rules for a single table. See
|
||||
// net/ipv4/netfilter/ip_tables.c:translate_table for reference.
|
||||
func SetEntries(stk *stack.Stack, optVal []byte, ipv6 bool) *syserr.Error {
|
||||
func SetEntries(task *kernel.Task, stk *stack.Stack, optVal []byte, ipv6 bool) *syserr.Error {
|
||||
var replace linux.IPTReplace
|
||||
replaceBuf := optVal[:linux.SizeOfIPTReplace]
|
||||
optVal = optVal[linux.SizeOfIPTReplace:]
|
||||
replace.UnmarshalBytes(replaceBuf)
|
||||
|
||||
// TODO(gvisor.dev/issue/170): Support other tables.
|
||||
var table stack.Table
|
||||
switch replace.Name.String() {
|
||||
case filterTable:
|
||||
@@ -188,16 +187,16 @@ func SetEntries(stk *stack.Stack, optVal []byte, ipv6 bool) *syserr.Error {
|
||||
case natTable:
|
||||
table = stack.EmptyNATTable()
|
||||
default:
|
||||
nflog("we don't yet support writing to the %q table (gvisor.dev/issue/170)", replace.Name.String())
|
||||
nflog("unknown iptables table %q", replace.Name.String())
|
||||
return syserr.ErrInvalidArgument
|
||||
}
|
||||
|
||||
var err *syserr.Error
|
||||
var offsets map[uint32]int
|
||||
if ipv6 {
|
||||
offsets, err = modifyEntries6(stk, optVal, &replace, &table)
|
||||
offsets, err = modifyEntries6(task, stk, optVal, &replace, &table)
|
||||
} else {
|
||||
offsets, err = modifyEntries4(stk, optVal, &replace, &table)
|
||||
offsets, err = modifyEntries4(task, stk, optVal, &replace, &table)
|
||||
}
|
||||
if err != nil {
|
||||
return err
|
||||
@@ -272,7 +271,6 @@ func SetEntries(stk *stack.Stack, optVal []byte, ipv6 bool) *syserr.Error {
|
||||
table.Rules[ruleIdx] = rule
|
||||
}
|
||||
|
||||
// TODO(gvisor.dev/issue/170): Support other chains.
|
||||
// Since we don't support FORWARD, yet, make sure all other chains point to
|
||||
// ACCEPT rules.
|
||||
for hook, ruleIdx := range table.BuiltinChains {
|
||||
@@ -287,7 +285,7 @@ func SetEntries(stk *stack.Stack, optVal []byte, ipv6 bool) *syserr.Error {
|
||||
}
|
||||
}
|
||||
|
||||
// TODO(gvisor.dev/issue/170): Check the following conditions:
|
||||
// TODO(gvisor.dev/issue/6167): Check the following conditions:
|
||||
// - There are no loops.
|
||||
// - There are no chains without an unconditional final rule.
|
||||
// - There are no chains without an unconditional underflow rule.
|
||||
@@ -297,7 +295,7 @@ func SetEntries(stk *stack.Stack, optVal []byte, ipv6 bool) *syserr.Error {
|
||||
|
||||
// parseMatchers parses 0 or more matchers from optVal. optVal should contain
|
||||
// only the matchers.
|
||||
func parseMatchers(filter stack.IPHeaderFilter, optVal []byte) ([]stack.Matcher, error) {
|
||||
func parseMatchers(task *kernel.Task, filter stack.IPHeaderFilter, optVal []byte) ([]stack.Matcher, error) {
|
||||
nflog("set entries: parsing matchers of size %d", len(optVal))
|
||||
var matchers []stack.Matcher
|
||||
for len(optVal) > 0 {
|
||||
@@ -321,13 +319,13 @@ func parseMatchers(filter stack.IPHeaderFilter, optVal []byte) ([]stack.Matcher,
|
||||
}
|
||||
|
||||
// Parse the specific matcher.
|
||||
matcher, err := unmarshalMatcher(match, filter, optVal[linux.SizeOfXTEntryMatch:match.MatchSize])
|
||||
matcher, err := unmarshalMatcher(task, match, filter, optVal[linux.SizeOfXTEntryMatch:match.MatchSize])
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed to create matcher: %v", err)
|
||||
}
|
||||
matchers = append(matchers, matcher)
|
||||
|
||||
// TODO(gvisor.dev/issue/170): Check the revision field.
|
||||
// TODO(gvisor.dev/issue/6167): Check the revision field.
|
||||
optVal = optVal[match.MatchSize:]
|
||||
}
|
||||
|
||||
|
||||
@@ -19,6 +19,8 @@ import (
|
||||
|
||||
"gvisor.dev/gvisor/pkg/abi/linux"
|
||||
"gvisor.dev/gvisor/pkg/marshal"
|
||||
"gvisor.dev/gvisor/pkg/sentry/kernel"
|
||||
"gvisor.dev/gvisor/pkg/sentry/kernel/auth"
|
||||
"gvisor.dev/gvisor/pkg/tcpip/stack"
|
||||
)
|
||||
|
||||
@@ -40,8 +42,8 @@ func (ownerMarshaler) name() string {
|
||||
func (ownerMarshaler) marshal(mr matcher) []byte {
|
||||
matcher := mr.(*OwnerMatcher)
|
||||
iptOwnerInfo := linux.IPTOwnerInfo{
|
||||
UID: matcher.uid,
|
||||
GID: matcher.gid,
|
||||
UID: uint32(matcher.uid),
|
||||
GID: uint32(matcher.gid),
|
||||
}
|
||||
|
||||
// Support for UID and GID match.
|
||||
@@ -63,7 +65,7 @@ func (ownerMarshaler) marshal(mr matcher) []byte {
|
||||
}
|
||||
|
||||
// unmarshal implements matchMaker.unmarshal.
|
||||
func (ownerMarshaler) unmarshal(buf []byte, filter stack.IPHeaderFilter) (stack.Matcher, error) {
|
||||
func (ownerMarshaler) unmarshal(task *kernel.Task, buf []byte, filter stack.IPHeaderFilter) (stack.Matcher, error) {
|
||||
if len(buf) < linux.SizeOfIPTOwnerInfo {
|
||||
return nil, fmt.Errorf("buf has insufficient size for owner match: %d", len(buf))
|
||||
}
|
||||
@@ -72,11 +74,12 @@ func (ownerMarshaler) unmarshal(buf []byte, filter stack.IPHeaderFilter) (stack.
|
||||
// exceed what's strictly necessary to hold matchData.
|
||||
var matchData linux.IPTOwnerInfo
|
||||
matchData.UnmarshalUnsafe(buf[:linux.SizeOfIPTOwnerInfo])
|
||||
nflog("parseMatchers: parsed IPTOwnerInfo: %+v", matchData)
|
||||
nflog("parsed IPTOwnerInfo: %+v", matchData)
|
||||
|
||||
var owner OwnerMatcher
|
||||
owner.uid = matchData.UID
|
||||
owner.gid = matchData.GID
|
||||
creds := task.Credentials()
|
||||
owner.uid = creds.UserNamespace.MapToKUID(auth.UID(matchData.UID))
|
||||
owner.gid = creds.UserNamespace.MapToKGID(auth.GID(matchData.GID))
|
||||
|
||||
// Check flags.
|
||||
if matchData.Match&linux.XT_OWNER_UID != 0 {
|
||||
@@ -97,8 +100,8 @@ func (ownerMarshaler) unmarshal(buf []byte, filter stack.IPHeaderFilter) (stack.
|
||||
|
||||
// OwnerMatcher matches against a UID and/or GID.
|
||||
type OwnerMatcher struct {
|
||||
uid uint32
|
||||
gid uint32
|
||||
uid auth.KUID
|
||||
gid auth.KGID
|
||||
matchUID bool
|
||||
matchGID bool
|
||||
invertUID bool
|
||||
@@ -113,7 +116,6 @@ func (*OwnerMatcher) name() string {
|
||||
// Match implements Matcher.Match.
|
||||
func (om *OwnerMatcher) Match(hook stack.Hook, pkt *stack.PacketBuffer, _, _ string) (bool, bool) {
|
||||
// Support only for OUTPUT chain.
|
||||
// TODO(gvisor.dev/issue/170): Need to support for POSTROUTING chain also.
|
||||
if hook != stack.Output {
|
||||
return false, true
|
||||
}
|
||||
@@ -126,7 +128,7 @@ func (om *OwnerMatcher) Match(hook stack.Hook, pkt *stack.PacketBuffer, _, _ str
|
||||
var matches bool
|
||||
// Check for UID match.
|
||||
if om.matchUID {
|
||||
if pkt.Owner.UID() == om.uid {
|
||||
if auth.KUID(pkt.Owner.KUID()) == om.uid {
|
||||
matches = true
|
||||
}
|
||||
if matches == om.invertUID {
|
||||
@@ -137,7 +139,7 @@ func (om *OwnerMatcher) Match(hook stack.Hook, pkt *stack.PacketBuffer, _, _ str
|
||||
// Check for GID match.
|
||||
if om.matchGID {
|
||||
matches = false
|
||||
if pkt.Owner.GID() == om.gid {
|
||||
if auth.KGID(pkt.Owner.KGID()) == om.gid {
|
||||
matches = true
|
||||
}
|
||||
if matches == om.invertGID {
|
||||
|
||||
@@ -331,7 +331,6 @@ func (*redirectTargetMaker) unmarshal(buf []byte, filter stack.IPHeaderFilter) (
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
}
|
||||
|
||||
// TODO(gvisor.dev/issue/170): Check if the flags are valid.
|
||||
// Also check if we need to map ports or IP.
|
||||
// For now, redirect target only supports destination port change.
|
||||
// Port range and IP range are not supported yet.
|
||||
@@ -340,7 +339,6 @@ func (*redirectTargetMaker) unmarshal(buf []byte, filter stack.IPHeaderFilter) (
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
}
|
||||
|
||||
// TODO(gvisor.dev/issue/170): Port range is not supported yet.
|
||||
if nfRange.RangeIPV4.MinPort != nfRange.RangeIPV4.MaxPort {
|
||||
nflog("redirectTargetMaker: MinPort != MaxPort (%d, %d)", nfRange.RangeIPV4.MinPort, nfRange.RangeIPV4.MaxPort)
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
@@ -502,7 +500,6 @@ func (*snatTargetMakerV4) unmarshal(buf []byte, filter stack.IPHeaderFilter) (ta
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
}
|
||||
|
||||
// TODO(gvisor.dev/issue/170): Port range is not supported yet.
|
||||
if nfRange.RangeIPV4.MinPort != nfRange.RangeIPV4.MaxPort {
|
||||
nflog("snatTargetMakerV4: MinPort != MaxPort (%d, %d)", nfRange.RangeIPV4.MinPort, nfRange.RangeIPV4.MaxPort)
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
@@ -594,7 +591,6 @@ func (*snatTargetMakerV6) unmarshal(buf []byte, filter stack.IPHeaderFilter) (ta
|
||||
// translateToStandardTarget translates from the value in a
|
||||
// linux.XTStandardTarget to an stack.Verdict.
|
||||
func translateToStandardTarget(val int32, netProto tcpip.NetworkProtocolNumber) (target, *syserr.Error) {
|
||||
// TODO(gvisor.dev/issue/170): Support other verdicts.
|
||||
switch val {
|
||||
case -linux.NF_ACCEPT - 1:
|
||||
return &acceptTarget{stack.AcceptTarget{
|
||||
|
||||
@@ -19,6 +19,7 @@ import (
|
||||
|
||||
"gvisor.dev/gvisor/pkg/abi/linux"
|
||||
"gvisor.dev/gvisor/pkg/marshal"
|
||||
"gvisor.dev/gvisor/pkg/sentry/kernel"
|
||||
"gvisor.dev/gvisor/pkg/tcpip/header"
|
||||
"gvisor.dev/gvisor/pkg/tcpip/stack"
|
||||
)
|
||||
@@ -50,7 +51,7 @@ func (tcpMarshaler) marshal(mr matcher) []byte {
|
||||
}
|
||||
|
||||
// unmarshal implements matchMaker.unmarshal.
|
||||
func (tcpMarshaler) unmarshal(buf []byte, filter stack.IPHeaderFilter) (stack.Matcher, error) {
|
||||
func (tcpMarshaler) unmarshal(_ *kernel.Task, buf []byte, filter stack.IPHeaderFilter) (stack.Matcher, error) {
|
||||
if len(buf) < linux.SizeOfXTTCP {
|
||||
return nil, fmt.Errorf("buf has insufficient size for TCP match: %d", len(buf))
|
||||
}
|
||||
@@ -95,8 +96,6 @@ func (*TCPMatcher) name() string {
|
||||
|
||||
// Match implements Matcher.Match.
|
||||
func (tm *TCPMatcher) Match(hook stack.Hook, pkt *stack.PacketBuffer, _, _ string) (bool, bool) {
|
||||
// TODO(gvisor.dev/issue/170): Proto checks should ultimately be moved
|
||||
// into the stack.Check codepath as matchers are added.
|
||||
switch pkt.NetworkProtocolNumber {
|
||||
case header.IPv4ProtocolNumber:
|
||||
netHeader := header.IPv4(pkt.NetworkHeader().View())
|
||||
|
||||
@@ -19,6 +19,7 @@ import (
|
||||
|
||||
"gvisor.dev/gvisor/pkg/abi/linux"
|
||||
"gvisor.dev/gvisor/pkg/marshal"
|
||||
"gvisor.dev/gvisor/pkg/sentry/kernel"
|
||||
"gvisor.dev/gvisor/pkg/tcpip/header"
|
||||
"gvisor.dev/gvisor/pkg/tcpip/stack"
|
||||
)
|
||||
@@ -50,7 +51,7 @@ func (udpMarshaler) marshal(mr matcher) []byte {
|
||||
}
|
||||
|
||||
// unmarshal implements matchMaker.unmarshal.
|
||||
func (udpMarshaler) unmarshal(buf []byte, filter stack.IPHeaderFilter) (stack.Matcher, error) {
|
||||
func (udpMarshaler) unmarshal(_ *kernel.Task, buf []byte, filter stack.IPHeaderFilter) (stack.Matcher, error) {
|
||||
if len(buf) < linux.SizeOfXTUDP {
|
||||
return nil, fmt.Errorf("buf has insufficient size for UDP match: %d", len(buf))
|
||||
}
|
||||
@@ -92,8 +93,6 @@ func (*UDPMatcher) name() string {
|
||||
|
||||
// Match implements Matcher.Match.
|
||||
func (um *UDPMatcher) Match(hook stack.Hook, pkt *stack.PacketBuffer, _, _ string) (bool, bool) {
|
||||
// TODO(gvisor.dev/issue/170): Proto checks should ultimately be moved
|
||||
// into the stack.Check codepath as matchers are added.
|
||||
switch pkt.NetworkProtocolNumber {
|
||||
case header.IPv4ProtocolNumber:
|
||||
netHeader := header.IPv4(pkt.NetworkHeader().View())
|
||||
|
||||
@@ -2105,10 +2105,10 @@ func setSockOptIPv6(t *kernel.Task, s socket.SocketOps, ep commonEndpoint, name
|
||||
return syserr.ErrNoDevice
|
||||
}
|
||||
// Stack must be a netstack stack.
|
||||
return netfilter.SetEntries(stack.(*Stack).Stack, optVal, true)
|
||||
return netfilter.SetEntries(t, stack.(*Stack).Stack, optVal, true)
|
||||
|
||||
case linux.IP6T_SO_SET_ADD_COUNTERS:
|
||||
// TODO(gvisor.dev/issue/170): Counter support.
|
||||
log.Infof("IP6T_SO_SET_ADD_COUNTERS is not supported")
|
||||
return nil
|
||||
|
||||
default:
|
||||
@@ -2348,10 +2348,10 @@ func setSockOptIP(t *kernel.Task, s socket.SocketOps, ep commonEndpoint, name in
|
||||
return syserr.ErrNoDevice
|
||||
}
|
||||
// Stack must be a netstack stack.
|
||||
return netfilter.SetEntries(stack.(*Stack).Stack, optVal, false)
|
||||
return netfilter.SetEntries(t, stack.(*Stack).Stack, optVal, false)
|
||||
|
||||
case linux.IPT_SO_SET_ADD_COUNTERS:
|
||||
// TODO(gvisor.dev/issue/170): Counter support.
|
||||
log.Infof("IPT_SO_SET_ADD_COUNTERS is not supported")
|
||||
return nil
|
||||
|
||||
case linux.IP_ADD_SOURCE_MEMBERSHIP,
|
||||
|
||||
@@ -173,9 +173,8 @@ func (e *endpoint) handleControl(errInfo stack.TransportError, pkt *stack.Packet
|
||||
|
||||
func (e *endpoint) handleICMP(pkt *stack.PacketBuffer) {
|
||||
received := e.stats.icmp.packetsReceived
|
||||
// TODO(gvisor.dev/issue/170): ICMP packets don't have their
|
||||
// TransportHeader fields set. See icmp/protocol.go:protocol.Parse for a
|
||||
// full explanation.
|
||||
// ICMP packets don't have their TransportHeader fields set. See
|
||||
// icmp/protocol.go:protocol.Parse for a full explanation.
|
||||
v, ok := pkt.Data().PullUp(header.ICMPv4MinimumSize)
|
||||
if !ok {
|
||||
received.invalid.Increment()
|
||||
|
||||
@@ -429,9 +429,9 @@ func (e *endpoint) WritePacket(r *stack.Route, params stack.NetworkHeaderParams,
|
||||
// based on destination address and do not send the packet to link
|
||||
// layer.
|
||||
//
|
||||
// TODO(gvisor.dev/issue/170): We should do this for every
|
||||
// packet, rather than only NATted packets, but removing this check
|
||||
// short circuits broadcasts before they are sent out to other hosts.
|
||||
// We should do this for every packet, rather than only NATted packets, but
|
||||
// removing this check short circuits broadcasts before they are sent out to
|
||||
// other hosts.
|
||||
if pkt.NatDone {
|
||||
netHeader := header.IPv4(pkt.NetworkHeader().View())
|
||||
if ep := e.protocol.findEndpointWithAddress(netHeader.DestinationAddress()); ep != nil {
|
||||
|
||||
@@ -285,8 +285,8 @@ func isMLDValid(pkt *stack.PacketBuffer, iph header.IPv6, routerAlert *header.IP
|
||||
func (e *endpoint) handleICMP(pkt *stack.PacketBuffer, hasFragmentHeader bool, routerAlert *header.IPv6RouterAlertOption) {
|
||||
sent := e.stats.icmp.packetsSent
|
||||
received := e.stats.icmp.packetsReceived
|
||||
// TODO(gvisor.dev/issue/170): ICMP packets don't have their TransportHeader
|
||||
// fields set. See icmp/protocol.go:protocol.Parse for a full explanation.
|
||||
// ICMP packets don't have their TransportHeader fields set. See
|
||||
// icmp/protocol.go:protocol.Parse for a full explanation.
|
||||
v, ok := pkt.Data().PullUp(header.ICMPv6HeaderSize)
|
||||
if !ok {
|
||||
received.invalid.Increment()
|
||||
|
||||
@@ -755,9 +755,9 @@ func (e *endpoint) WritePacket(r *stack.Route, params stack.NetworkHeaderParams,
|
||||
// based on destination address and do not send the packet to link
|
||||
// layer.
|
||||
//
|
||||
// TODO(gvisor.dev/issue/170): We should do this for every
|
||||
// packet, rather than only NATted packets, but removing this check
|
||||
// short circuits broadcasts before they are sent out to other hosts.
|
||||
// We should do this for every packet, rather than only NATted packets, but
|
||||
// removing this check short circuits broadcasts before they are sent out to
|
||||
// other hosts.
|
||||
if pkt.NatDone {
|
||||
netHeader := header.IPv6(pkt.NetworkHeader().View())
|
||||
if ep := e.protocol.findEndpointWithAddress(netHeader.DestinationAddress()); ep != nil {
|
||||
|
||||
@@ -35,7 +35,6 @@ import (
|
||||
// Currently, only TCP tracking is supported.
|
||||
|
||||
// Our hash table has 16K buckets.
|
||||
// TODO(gvisor.dev/issue/170): These should be tunable.
|
||||
const numBuckets = 1 << 14
|
||||
|
||||
// Direction of the tuple.
|
||||
@@ -165,8 +164,6 @@ func (cn *conn) updateLocked(tcpHeader header.TCP, hook Hook) {
|
||||
// Update the state of tcb. tcb assumes it's always initialized on the
|
||||
// client. However, we only need to know whether the connection is
|
||||
// established or not, so the client/server distinction isn't important.
|
||||
// TODO(gvisor.dev/issue/170): Add support in tcpconntrack to handle
|
||||
// other tcp states.
|
||||
if cn.tcb.IsEmpty() {
|
||||
cn.tcb.Init(tcpHeader)
|
||||
} else if hook == cn.tcbHook {
|
||||
@@ -246,8 +243,7 @@ func (ct *ConnTrack) init() {
|
||||
// connFor gets the conn for pkt if it exists, or returns nil
|
||||
// if it does not. It returns an error when pkt does not contain a valid TCP
|
||||
// header.
|
||||
// TODO(gvisor.dev/issue/170): Only TCP packets are supported. Need to support
|
||||
// other transport protocols.
|
||||
// TODO(gvisor.dev/issue/6168): Support UDP.
|
||||
func (ct *ConnTrack) connFor(pkt *PacketBuffer) (*conn, direction) {
|
||||
tid, err := packetToTupleID(pkt)
|
||||
if err != nil {
|
||||
@@ -385,7 +381,7 @@ func (ct *ConnTrack) handlePacket(pkt *PacketBuffer, hook Hook, r *Route) bool {
|
||||
return false
|
||||
}
|
||||
|
||||
// TODO(gvisor.dev/issue/170): Support other transport protocols.
|
||||
// TODO(gvisor.dev/issue/6168): Support UDP.
|
||||
if pkt.Network().TransportProtocol() != header.TCPProtocolNumber {
|
||||
return false
|
||||
}
|
||||
@@ -466,8 +462,6 @@ func (ct *ConnTrack) handlePacket(pkt *PacketBuffer, hook Hook, r *Route) bool {
|
||||
}
|
||||
|
||||
// Update the state of tcb.
|
||||
// TODO(gvisor.dev/issue/170): Add support in tcpcontrack to handle
|
||||
// other tcp states.
|
||||
conn.mu.Lock()
|
||||
defer conn.mu.Unlock()
|
||||
|
||||
@@ -544,8 +538,6 @@ func (ct *ConnTrack) bucket(id tupleID) int {
|
||||
// reapUnused returns the next bucket that should be checked and the time after
|
||||
// which it should be called again.
|
||||
func (ct *ConnTrack) reapUnused(start int, prevInterval time.Duration) (int, time.Duration) {
|
||||
// TODO(gvisor.dev/issue/170): This can be more finely controlled, as
|
||||
// it is in Linux via sysctl.
|
||||
const fractionPerReaping = 128
|
||||
const maxExpiredPct = 50
|
||||
const maxFullTraversal = 60 * time.Second
|
||||
|
||||
@@ -268,10 +268,6 @@ const (
|
||||
// should continue traversing the network stack and false when it should be
|
||||
// dropped.
|
||||
//
|
||||
// TODO(gvisor.dev/issue/170): PacketBuffer should hold the route, from
|
||||
// which address can be gathered. Currently, address is only needed for
|
||||
// prerouting.
|
||||
//
|
||||
// Precondition: pkt.NetworkHeader is set.
|
||||
func (it *IPTables) Check(hook Hook, pkt *PacketBuffer, r *Route, preroutingAddr tcpip.Address, inNicName, outNicName string) bool {
|
||||
if pkt.NetworkProtocolNumber != header.IPv4ProtocolNumber && pkt.NetworkProtocolNumber != header.IPv6ProtocolNumber {
|
||||
|
||||
@@ -87,9 +87,6 @@ func (*ReturnTarget) Action(*PacketBuffer, *ConnTrack, Hook, *Route, tcpip.Addre
|
||||
// destination port/IP. Outgoing packets are redirected to the loopback device,
|
||||
// and incoming packets are redirected to the incoming interface (rather than
|
||||
// forwarded).
|
||||
//
|
||||
// TODO(gvisor.dev/issue/170): Other flags need to be added after we support
|
||||
// them.
|
||||
type RedirectTarget struct {
|
||||
// Port indicates port used to redirect. It is immutable.
|
||||
Port uint16
|
||||
@@ -100,9 +97,6 @@ type RedirectTarget struct {
|
||||
}
|
||||
|
||||
// Action implements Target.Action.
|
||||
// TODO(gvisor.dev/issue/170): Parse headers without copying. The current
|
||||
// implementation only works for Prerouting and calls pkt.Clone(), neither
|
||||
// of which should be the case.
|
||||
func (rt *RedirectTarget) Action(pkt *PacketBuffer, ct *ConnTrack, hook Hook, r *Route, address tcpip.Address) (RuleVerdict, int) {
|
||||
// Sanity check.
|
||||
if rt.NetworkProtocol != pkt.NetworkProtocolNumber {
|
||||
@@ -136,8 +130,6 @@ func (rt *RedirectTarget) Action(pkt *PacketBuffer, ct *ConnTrack, hook Hook, r
|
||||
panic("redirect target is supported only on output and prerouting hooks")
|
||||
}
|
||||
|
||||
// TODO(gvisor.dev/issue/170): Check Flags in RedirectTarget if
|
||||
// we need to change dest address (for OUTPUT chain) or ports.
|
||||
switch protocol := pkt.TransportProtocolNumber; protocol {
|
||||
case header.UDPProtocolNumber:
|
||||
udpHeader := header.UDP(pkt.TransportHeader().View())
|
||||
|
||||
@@ -242,7 +242,6 @@ type IPHeaderFilter struct {
|
||||
func (fl IPHeaderFilter) match(pkt *PacketBuffer, hook Hook, inNicName, outNicName string) bool {
|
||||
// Extract header fields.
|
||||
var (
|
||||
// TODO(gvisor.dev/issue/170): Support other filter fields.
|
||||
transProto tcpip.TransportProtocolNumber
|
||||
dstAddr tcpip.Address
|
||||
srcAddr tcpip.Address
|
||||
@@ -291,7 +290,6 @@ func (fl IPHeaderFilter) match(pkt *PacketBuffer, hook Hook, inNicName, outNicNa
|
||||
|
||||
return true
|
||||
case Postrouting:
|
||||
// TODO(gvisor.dev/issue/170): Add the check for POSTROUTING.
|
||||
return true
|
||||
default:
|
||||
panic(fmt.Sprintf("unknown hook: %d", hook))
|
||||
|
||||
@@ -787,9 +787,8 @@ func (n *nic) DeliverTransportPacket(protocol tcpip.TransportProtocolNumber, pkt
|
||||
// TransportHeader is empty only when pkt is an ICMP packet or was reassembled
|
||||
// from fragments.
|
||||
if pkt.TransportHeader().View().IsEmpty() {
|
||||
// TODO(gvisor.dev/issue/170): ICMP packets don't have their TransportHeader
|
||||
// fields set yet, parse it here. See icmp/protocol.go:protocol.Parse for a
|
||||
// full explanation.
|
||||
// ICMP packets don't have their TransportHeader fields set yet, parse it
|
||||
// here. See icmp/protocol.go:protocol.Parse for a full explanation.
|
||||
if protocol == header.ICMPv4ProtocolNumber || protocol == header.ICMPv6ProtocolNumber {
|
||||
// ICMP packets may be longer, but until icmp.Parse is implemented, here
|
||||
// we parse it using the minimum size.
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user