diff --git a/Godeps/Godeps.json b/Godeps/Godeps.json index 51e0c241..97208555 100644 --- a/Godeps/Godeps.json +++ b/Godeps/Godeps.json @@ -8,38 +8,38 @@ "Deps": [ { "ImportPath": "github.com/containernetworking/cni/libcni", - "Comment": "v0.5.2", - "Rev": "137b4975ecab6e1f0c24c1e3c228a50a3cfba75e" + "Comment": "v0.5.2-git49d814c", + "Rev": "49d814cf37bfea351a1caedd0c66825c9d6fca52" }, { "ImportPath": "github.com/containernetworking/cni/pkg/invoke", - "Comment": "v0.5.2", - "Rev": "137b4975ecab6e1f0c24c1e3c228a50a3cfba75e" + "Comment": "v0.5.2-git49d814c", + "Rev": "49d814cf37bfea351a1caedd0c66825c9d6fca52" }, { "ImportPath": "github.com/containernetworking/cni/pkg/skel", - "Comment": "v0.5.2", - "Rev": "137b4975ecab6e1f0c24c1e3c228a50a3cfba75e" + "Comment": "v0.5.2-git49d814c", + "Rev": "49d814cf37bfea351a1caedd0c66825c9d6fca52" }, { "ImportPath": "github.com/containernetworking/cni/pkg/types", - "Comment": "v0.5.2", - "Rev": "137b4975ecab6e1f0c24c1e3c228a50a3cfba75e" + "Comment": "v0.5.2-git49d814c", + "Rev": "49d814cf37bfea351a1caedd0c66825c9d6fca52" }, { "ImportPath": "github.com/containernetworking/cni/pkg/types/020", - "Comment": "v0.5.2", - "Rev": "137b4975ecab6e1f0c24c1e3c228a50a3cfba75e" + "Comment": "v0.5.2-git49d814c", + "Rev": "49d814cf37bfea351a1caedd0c66825c9d6fca52" }, { "ImportPath": "github.com/containernetworking/cni/pkg/types/current", - "Comment": "v0.5.2", - "Rev": "137b4975ecab6e1f0c24c1e3c228a50a3cfba75e" + "Comment": "v0.5.2-git49d814c", + "Rev": "49d814cf37bfea351a1caedd0c66825c9d6fca52" }, { "ImportPath": "github.com/containernetworking/cni/pkg/version", - "Comment": "v0.5.2", - "Rev": "137b4975ecab6e1f0c24c1e3c228a50a3cfba75e" + "Comment": "v0.5.2-git49d814c", + "Rev": "49d814cf37bfea351a1caedd0c66825c9d6fca52" }, { "ImportPath": "github.com/coreos/go-iptables/iptables", diff --git a/pkg/ipam/ipam.go b/pkg/ipam/ipam.go index 54f80c0e..0685679d 100644 --- a/pkg/ipam/ipam.go +++ b/pkg/ipam/ipam.go @@ -53,7 +53,11 @@ func ConfigureIface(ifName string, res *current.Result) error { var v4gw, v6gw net.IP for _, ipc := range res.IPs { - if int(ipc.Interface) >= len(res.Interfaces) || res.Interfaces[ipc.Interface].Name != ifName { + if ipc.Interface == nil { + continue + } + intIdx := *ipc.Interface + if intIdx < 0 || intIdx >= len(res.Interfaces) || res.Interfaces[intIdx].Name != ifName { // IP address is for a different interface return fmt.Errorf("failed to add IP addr %v to %q: invalid interface index", ipc, ifName) } diff --git a/pkg/ipam/ipam_test.go b/pkg/ipam/ipam_test.go index 844867f2..cf851175 100644 --- a/pkg/ipam/ipam_test.go +++ b/pkg/ipam/ipam_test.go @@ -109,13 +109,13 @@ var _ = Describe("IPAM Operations", func() { IPs: []*current.IPConfig{ { Version: "4", - Interface: 0, + Interface: current.Int(0), Address: *ipv4, Gateway: ipgw4, }, { Version: "6", - Interface: 0, + Interface: current.Int(0), Address: *ipv6, Gateway: ipgw6, }, @@ -226,7 +226,7 @@ var _ = Describe("IPAM Operations", func() { }) It("returns an error when the interface index doesn't match the link name", func() { - result.IPs[0].Interface = 1 + result.IPs[0].Interface = current.Int(1) err := originalNS.Do(func(ns.NetNS) error { return ConfigureIface(LINK_NAME, result) }) @@ -234,7 +234,15 @@ var _ = Describe("IPAM Operations", func() { }) It("returns an error when the interface index is too big", func() { - result.IPs[0].Interface = 2 + result.IPs[0].Interface = current.Int(2) + err := originalNS.Do(func(ns.NetNS) error { + return ConfigureIface(LINK_NAME, result) + }) + Expect(err).To(HaveOccurred()) + }) + + It("returns an error when the interface index is too small", func() { + result.IPs[0].Interface = current.Int(-1) err := originalNS.Do(func(ns.NetNS) error { return ConfigureIface(LINK_NAME, result) }) @@ -255,4 +263,37 @@ var _ = Describe("IPAM Operations", func() { }) Expect(err).To(HaveOccurred()) }) + + It("does not panic when interface is not specified", func() { + result = ¤t.Result{ + Interfaces: []*current.Interface{ + { + Name: "eth0", + Mac: "00:11:22:33:44:55", + Sandbox: "/proc/3553/ns/net", + }, + { + Name: "fake0", + Mac: "00:33:44:55:66:77", + Sandbox: "/proc/1234/ns/net", + }, + }, + IPs: []*current.IPConfig{ + { + Version: "4", + Address: *ipv4, + Gateway: ipgw4, + }, + { + Version: "6", + Address: *ipv6, + Gateway: ipgw6, + }, + }, + } + err := originalNS.Do(func(ns.NetNS) error { + return ConfigureIface(LINK_NAME, result) + }) + Expect(err).NotTo(HaveOccurred()) + }) }) diff --git a/plugins/ipam/host-local/host_local_test.go b/plugins/ipam/host-local/host_local_test.go index 68942ea1..30b73c81 100644 --- a/plugins/ipam/host-local/host_local_test.go +++ b/plugins/ipam/host-local/host_local_test.go @@ -86,27 +86,25 @@ var _ = Describe("host-local Operations", func() { // Gomega is cranky about slices with different caps Expect(*result.IPs[0]).To(Equal( current.IPConfig{ - Version: "4", - Interface: 0, - Address: mustCIDR("10.1.2.2/24"), - Gateway: net.ParseIP("10.1.2.1"), + Version: "4", + Address: mustCIDR("10.1.2.2/24"), + Gateway: net.ParseIP("10.1.2.1"), })) Expect(*result.IPs[1]).To(Equal( current.IPConfig{ - Version: "6", - Interface: 0, - Address: mustCIDR("2001:db8:1::2/64"), - Gateway: net.ParseIP("2001:db8:1::1"), + Version: "6", + Address: mustCIDR("2001:db8:1::2/64"), + Gateway: net.ParseIP("2001:db8:1::1"), }, )) Expect(len(result.IPs)).To(Equal(2)) Expect(result.Routes).To(Equal([]*types.Route{ - &types.Route{Dst: mustCIDR("0.0.0.0/0"), GW: nil}, - &types.Route{Dst: mustCIDR("::/0"), GW: nil}, - &types.Route{Dst: mustCIDR("192.168.0.0/16"), GW: net.ParseIP("1.1.1.1")}, - &types.Route{Dst: mustCIDR("2001:db8:2::0/64"), GW: net.ParseIP("2001:db8:3::1")}, + {Dst: mustCIDR("0.0.0.0/0"), GW: nil}, + {Dst: mustCIDR("::/0"), GW: nil}, + {Dst: mustCIDR("192.168.0.0/16"), GW: net.ParseIP("1.1.1.1")}, + {Dst: mustCIDR("2001:db8:2::0/64"), GW: net.ParseIP("2001:db8:3::1")}, })) ipFilePath1 := filepath.Join(tmpDir, "mynet", "10.1.2.2") diff --git a/plugins/main/bridge/bridge.go b/plugins/main/bridge/bridge.go index 797409e1..4e5bb1e4 100644 --- a/plugins/main/bridge/bridge.go +++ b/plugins/main/bridge/bridge.go @@ -100,7 +100,7 @@ func calcGateways(result *current.Result, n *NetConf) (*gwInfo, *gwInfo, error) defaultNet.Mask = net.IPMask(defaultNet.IP) // All IPs currently refer to the container interface - ipc.Interface = 2 + ipc.Interface = current.Int(2) // If not provided, calculate the gateway address corresponding // to the selected IP address diff --git a/plugins/main/ipvlan/ipvlan.go b/plugins/main/ipvlan/ipvlan.go index b9c7b1b3..09924ef3 100644 --- a/plugins/main/ipvlan/ipvlan.go +++ b/plugins/main/ipvlan/ipvlan.go @@ -159,7 +159,7 @@ func cmdAdd(args *skel.CmdArgs) error { } for _, ipc := range result.IPs { // All addresses belong to the ipvlan interface - ipc.Interface = 0 + ipc.Interface = current.Int(0) } result.Interfaces = []*current.Interface{ipvlanInterface} diff --git a/plugins/main/macvlan/macvlan.go b/plugins/main/macvlan/macvlan.go index 98e46a40..3b69194b 100644 --- a/plugins/main/macvlan/macvlan.go +++ b/plugins/main/macvlan/macvlan.go @@ -179,7 +179,7 @@ func cmdAdd(args *skel.CmdArgs) error { for _, ipc := range result.IPs { // All addresses apply to the container macvlan interface - ipc.Interface = 0 + ipc.Interface = current.Int(0) } err = netns.Do(func(_ ns.NetNS) error { diff --git a/plugins/main/ptp/ptp.go b/plugins/main/ptp/ptp.go index 42b26707..12a77221 100644 --- a/plugins/main/ptp/ptp.go +++ b/plugins/main/ptp/ptp.go @@ -75,7 +75,7 @@ func setupContainerVeth(netns ns.NetNS, ifName string, mtu int, pr *current.Resu for _, ipc := range pr.IPs { // All addresses apply to the container veth interface - ipc.Interface = 1 + ipc.Interface = current.Int(1) } pr.Interfaces = []*current.Interface{hostInterface, containerInterface} diff --git a/plugins/main/vlan/vlan.go b/plugins/main/vlan/vlan.go index b9aa4fee..7f527b55 100644 --- a/plugins/main/vlan/vlan.go +++ b/plugins/main/vlan/vlan.go @@ -148,7 +148,7 @@ func cmdAdd(args *skel.CmdArgs) error { } for _, ipc := range result.IPs { // All addresses belong to the vlan interface - ipc.Interface = 0 + ipc.Interface = current.Int(0) } result.Interfaces = []*current.Interface{vlanInterface} diff --git a/plugins/meta/portmap/main.go b/plugins/meta/portmap/main.go index c58db6aa..6424a777 100644 --- a/plugins/meta/portmap/main.go +++ b/plugins/meta/portmap/main.go @@ -164,9 +164,14 @@ func parseConfig(stdin []byte, ifName string) (*PortMapConf, error) { } // Skip known non-sandbox interfaces - intIdx := ip.Interface - if intIdx >= 0 && intIdx < len(conf.PrevResult.Interfaces) && conf.PrevResult.Interfaces[intIdx].Name != ifName { - continue + if ip.Interface != nil { + intIdx := *ip.Interface + if intIdx >= 0 && + intIdx < len(conf.PrevResult.Interfaces) && + (conf.PrevResult.Interfaces[intIdx].Name != ifName || + conf.PrevResult.Interfaces[intIdx].Sandbox == "") { + continue + } } switch ip.Version { case "6": diff --git a/plugins/meta/portmap/portmap_integ_test.go b/plugins/meta/portmap/portmap_integ_test.go index bcdbcfd9..158b9057 100644 --- a/plugins/meta/portmap/portmap_integ_test.go +++ b/plugins/meta/portmap/portmap_integ_test.go @@ -134,7 +134,8 @@ var _ = Describe("portmap integration tests", func() { var contIP net.IP for _, ip := range result.IPs { - if result.Interfaces[ip.Interface].Sandbox == "" { + intfIndex := *ip.Interface + if result.Interfaces[intfIndex].Sandbox == "" { continue } contIP = ip.Address.IP diff --git a/plugins/meta/portmap/portmap_test.go b/plugins/meta/portmap/portmap_test.go index e67907f8..cf5ed5fb 100644 --- a/plugins/meta/portmap/portmap_test.go +++ b/plugins/meta/portmap/portmap_test.go @@ -124,6 +124,34 @@ var _ = Describe("portmapping configuration", func() { _, err := parseConfig(configBytes, "container") Expect(err).To(MatchError("Invalid host port number: 0")) }) + + It("Does not fail on missing prevResult interface index", func() { + configBytes := []byte(`{ + "name": "test", + "type": "portmap", + "cniVersion": "0.3.1", + "runtimeConfig": { + "portMappings": [ + { "hostPort": 8080, "containerPort": 80, "protocol": "tcp"} + ] + }, + "conditionsV4": ["a", "b"], + "prevResult": { + "interfaces": [ + {"name": "host"} + ], + "ips": [ + { + "version": "4", + "address": "10.0.0.1/24", + "gateway": "10.0.0.1" + } + ] + } +}`) + _, err := parseConfig(configBytes, "container") + Expect(err).NotTo(HaveOccurred()) + }) }) Describe("Generating chains", func() { diff --git a/plugins/sample/main.go b/plugins/sample/main.go index e55953c9..1abdc165 100644 --- a/plugins/sample/main.go +++ b/plugins/sample/main.go @@ -106,7 +106,10 @@ func cmdAdd(args *skel.CmdArgs) error { } } else { for _, ip := range conf.PrevResult.IPs { - intIdx := ip.Interface + if ip.Interface == nil { + continue + } + intIdx := *ip.Interface // Every IP is indexed in to the interfaces array, with "-1" standing // for an unknown interface (which we'll assume to be Container-side // Skip all IPs we know belong to an interface with the wrong name. diff --git a/vendor/github.com/containernetworking/cni/pkg/invoke/args.go b/vendor/github.com/containernetworking/cni/pkg/invoke/args.go index ba9d0c3b..39b63972 100644 --- a/vendor/github.com/containernetworking/cni/pkg/invoke/args.go +++ b/vendor/github.com/containernetworking/cni/pkg/invoke/args.go @@ -57,13 +57,16 @@ func (args *Args) AsEnv() []string { pluginArgsStr = stringify(args.PluginArgs) } - env = append(env, - "CNI_COMMAND="+args.Command, - "CNI_CONTAINERID="+args.ContainerID, - "CNI_NETNS="+args.NetNS, - "CNI_ARGS="+pluginArgsStr, - "CNI_IFNAME="+args.IfName, - "CNI_PATH="+args.Path) + // Ensure that the custom values are first, so any value present in + // the process environment won't override them. + env = append([]string{ + "CNI_COMMAND=" + args.Command, + "CNI_CONTAINERID=" + args.ContainerID, + "CNI_NETNS=" + args.NetNS, + "CNI_ARGS=" + pluginArgsStr, + "CNI_IFNAME=" + args.IfName, + "CNI_PATH=" + args.Path, + }, env...) return env } diff --git a/vendor/github.com/containernetworking/cni/pkg/invoke/raw_exec.go b/vendor/github.com/containernetworking/cni/pkg/invoke/raw_exec.go index d1bd860d..93f1e75d 100644 --- a/vendor/github.com/containernetworking/cni/pkg/invoke/raw_exec.go +++ b/vendor/github.com/containernetworking/cni/pkg/invoke/raw_exec.go @@ -50,13 +50,9 @@ func pluginErr(err error, output []byte) error { if _, ok := err.(*exec.ExitError); ok { emsg := types.Error{} if perr := json.Unmarshal(output, &emsg); perr != nil { - return fmt.Errorf("netplugin failed but error parsing its diagnostic message %q: %v", string(output), perr) + emsg.Msg = fmt.Sprintf("netplugin failed but error parsing its diagnostic message %q: %v", string(output), perr) } - details := "" - if emsg.Details != "" { - details = fmt.Sprintf("; %v", emsg.Details) - } - return fmt.Errorf("%v%v", emsg.Msg, details) + return &emsg } return err diff --git a/vendor/github.com/containernetworking/cni/pkg/types/020/types.go b/vendor/github.com/containernetworking/cni/pkg/types/020/types.go index 666cfe93..2833aba7 100644 --- a/vendor/github.com/containernetworking/cni/pkg/types/020/types.go +++ b/vendor/github.com/containernetworking/cni/pkg/types/020/types.go @@ -23,9 +23,9 @@ import ( "github.com/containernetworking/cni/pkg/types" ) -const implementedSpecVersion string = "0.2.0" +const ImplementedSpecVersion string = "0.2.0" -var SupportedVersions = []string{"", "0.1.0", implementedSpecVersion} +var SupportedVersions = []string{"", "0.1.0", ImplementedSpecVersion} // Compatibility types for CNI version 0.1.0 and 0.2.0 @@ -39,7 +39,7 @@ func NewResult(data []byte) (types.Result, error) { func GetResult(r types.Result) (*Result, error) { // We expect version 0.1.0/0.2.0 results - result020, err := r.GetAsVersion(implementedSpecVersion) + result020, err := r.GetAsVersion(ImplementedSpecVersion) if err != nil { return nil, err } @@ -52,18 +52,20 @@ func GetResult(r types.Result) (*Result, error) { // Result is what gets returned from the plugin (via stdout) to the caller type Result struct { - IP4 *IPConfig `json:"ip4,omitempty"` - IP6 *IPConfig `json:"ip6,omitempty"` - DNS types.DNS `json:"dns,omitempty"` + CNIVersion string `json:"cniVersion,omitempty"` + IP4 *IPConfig `json:"ip4,omitempty"` + IP6 *IPConfig `json:"ip6,omitempty"` + DNS types.DNS `json:"dns,omitempty"` } func (r *Result) Version() string { - return implementedSpecVersion + return ImplementedSpecVersion } func (r *Result) GetAsVersion(version string) (types.Result, error) { for _, supportedVersion := range SupportedVersions { if version == supportedVersion { + r.CNIVersion = version return r, nil } } diff --git a/vendor/github.com/containernetworking/cni/pkg/types/current/types.go b/vendor/github.com/containernetworking/cni/pkg/types/current/types.go index b89a5d3a..caac92ba 100644 --- a/vendor/github.com/containernetworking/cni/pkg/types/current/types.go +++ b/vendor/github.com/containernetworking/cni/pkg/types/current/types.go @@ -24,9 +24,9 @@ import ( "github.com/containernetworking/cni/pkg/types/020" ) -const implementedSpecVersion string = "0.3.1" +const ImplementedSpecVersion string = "0.3.1" -var SupportedVersions = []string{"0.3.0", implementedSpecVersion} +var SupportedVersions = []string{"0.3.0", ImplementedSpecVersion} func NewResult(data []byte) (types.Result, error) { result := &Result{} @@ -37,7 +37,7 @@ func NewResult(data []byte) (types.Result, error) { } func GetResult(r types.Result) (*Result, error) { - resultCurrent, err := r.GetAsVersion(implementedSpecVersion) + resultCurrent, err := r.GetAsVersion(ImplementedSpecVersion) if err != nil { return nil, err } @@ -63,16 +63,16 @@ func convertFrom020(result types.Result) (*Result, error) { } newResult := &Result{ - DNS: oldResult.DNS, - Routes: []*types.Route{}, + CNIVersion: ImplementedSpecVersion, + DNS: oldResult.DNS, + Routes: []*types.Route{}, } if oldResult.IP4 != nil { newResult.IPs = append(newResult.IPs, &IPConfig{ - Version: "4", - Interface: -1, - Address: oldResult.IP4.IP, - Gateway: oldResult.IP4.Gateway, + Version: "4", + Address: oldResult.IP4.IP, + Gateway: oldResult.IP4.Gateway, }) for _, route := range oldResult.IP4.Routes { gw := route.GW @@ -88,10 +88,9 @@ func convertFrom020(result types.Result) (*Result, error) { if oldResult.IP6 != nil { newResult.IPs = append(newResult.IPs, &IPConfig{ - Version: "6", - Interface: -1, - Address: oldResult.IP6.IP, - Gateway: oldResult.IP6.Gateway, + Version: "6", + Address: oldResult.IP6.IP, + Gateway: oldResult.IP6.Gateway, }) for _, route := range oldResult.IP6.Routes { gw := route.GW @@ -117,6 +116,7 @@ func convertFrom030(result types.Result) (*Result, error) { if !ok { return nil, fmt.Errorf("failed to convert result") } + newResult.CNIVersion = ImplementedSpecVersion return newResult, nil } @@ -134,6 +134,7 @@ func NewResultFromResult(result types.Result) (*Result, error) { // Result is what gets returned from the plugin (via stdout) to the caller type Result struct { + CNIVersion string `json:"cniVersion,omitempty"` Interfaces []*Interface `json:"interfaces,omitempty"` IPs []*IPConfig `json:"ips,omitempty"` Routes []*types.Route `json:"routes,omitempty"` @@ -143,7 +144,8 @@ type Result struct { // Convert to the older 0.2.0 CNI spec Result type func (r *Result) convertTo020() (*types020.Result, error) { oldResult := &types020.Result{ - DNS: r.DNS, + CNIVersion: types020.ImplementedSpecVersion, + DNS: r.DNS, } for _, ip := range r.IPs { @@ -189,12 +191,13 @@ func (r *Result) convertTo020() (*types020.Result, error) { } func (r *Result) Version() string { - return implementedSpecVersion + return ImplementedSpecVersion } func (r *Result) GetAsVersion(version string) (types.Result, error) { switch version { - case "0.3.0", implementedSpecVersion: + case "0.3.0", ImplementedSpecVersion: + r.CNIVersion = version return r, nil case types020.SupportedVersions[0], types020.SupportedVersions[1], types020.SupportedVersions[2]: return r.convertTo020() @@ -244,12 +247,18 @@ func (i *Interface) String() string { return fmt.Sprintf("%+v", *i) } +// Int returns a pointer to the int value passed in. Used to +// set the IPConfig.Interface field. +func Int(v int) *int { + return &v +} + // IPConfig contains values necessary to configure an IP address on an interface type IPConfig struct { // IP version, either "4" or "6" Version string // Index into Result structs Interfaces list - Interface int + Interface *int Address net.IPNet Gateway net.IP } @@ -261,7 +270,7 @@ func (i *IPConfig) String() string { // JSON (un)marshallable types type ipConfig struct { Version string `json:"version"` - Interface int `json:"interface,omitempty"` + Interface *int `json:"interface,omitempty"` Address types.IPNet `json:"address"` Gateway net.IP `json:"gateway,omitempty"` } diff --git a/vendor/github.com/containernetworking/cni/pkg/types/types.go b/vendor/github.com/containernetworking/cni/pkg/types/types.go index 3263015a..64127560 100644 --- a/vendor/github.com/containernetworking/cni/pkg/types/types.go +++ b/vendor/github.com/containernetworking/cni/pkg/types/types.go @@ -136,7 +136,11 @@ type Error struct { } func (e *Error) Error() string { - return e.Msg + details := "" + if e.Details != "" { + details = fmt.Sprintf("; %v", e.Details) + } + return fmt.Sprintf("%v%v", e.Msg, details) } func (e *Error) Print() error {