mirror of
https://github.com/moby/moby.git
synced 2022-11-09 12:21:53 -05:00
Merge pull request #19705 from mavenugo/18222
Vendor libnetwork v0.6.0-rc4 & corresponding changes in engine for port-map sandobx handling.
This commit is contained in:
commit
269a6d7d36
7 changed files with 119 additions and 37 deletions
|
@ -125,18 +125,26 @@ func (container *Container) buildPortMapInfo(ep libnetwork.Endpoint) error {
|
||||||
return derr.ErrorCodeEmptyNetwork
|
return derr.ErrorCodeEmptyNetwork
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if len(networkSettings.Ports) == 0 {
|
||||||
|
pm, err := getEndpointPortMapInfo(ep)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
networkSettings.Ports = pm
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func getEndpointPortMapInfo(ep libnetwork.Endpoint) (nat.PortMap, error) {
|
||||||
|
pm := nat.PortMap{}
|
||||||
driverInfo, err := ep.DriverInfo()
|
driverInfo, err := ep.DriverInfo()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return pm, err
|
||||||
}
|
}
|
||||||
|
|
||||||
if driverInfo == nil {
|
if driverInfo == nil {
|
||||||
// It is not an error for epInfo to be nil
|
// It is not an error for epInfo to be nil
|
||||||
return nil
|
return pm, nil
|
||||||
}
|
|
||||||
|
|
||||||
if networkSettings.Ports == nil {
|
|
||||||
networkSettings.Ports = nat.PortMap{}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if expData, ok := driverInfo[netlabel.ExposedPorts]; ok {
|
if expData, ok := driverInfo[netlabel.ExposedPorts]; ok {
|
||||||
|
@ -144,30 +152,45 @@ func (container *Container) buildPortMapInfo(ep libnetwork.Endpoint) error {
|
||||||
for _, tp := range exposedPorts {
|
for _, tp := range exposedPorts {
|
||||||
natPort, err := nat.NewPort(tp.Proto.String(), strconv.Itoa(int(tp.Port)))
|
natPort, err := nat.NewPort(tp.Proto.String(), strconv.Itoa(int(tp.Port)))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return derr.ErrorCodeParsingPort.WithArgs(tp.Port, err)
|
return pm, derr.ErrorCodeParsingPort.WithArgs(tp.Port, err)
|
||||||
}
|
}
|
||||||
networkSettings.Ports[natPort] = nil
|
pm[natPort] = nil
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
mapData, ok := driverInfo[netlabel.PortMap]
|
mapData, ok := driverInfo[netlabel.PortMap]
|
||||||
if !ok {
|
if !ok {
|
||||||
return nil
|
return pm, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
if portMapping, ok := mapData.([]types.PortBinding); ok {
|
if portMapping, ok := mapData.([]types.PortBinding); ok {
|
||||||
for _, pp := range portMapping {
|
for _, pp := range portMapping {
|
||||||
natPort, err := nat.NewPort(pp.Proto.String(), strconv.Itoa(int(pp.Port)))
|
natPort, err := nat.NewPort(pp.Proto.String(), strconv.Itoa(int(pp.Port)))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return pm, err
|
||||||
}
|
}
|
||||||
natBndg := nat.PortBinding{HostIP: pp.HostIP.String(), HostPort: strconv.Itoa(int(pp.HostPort))}
|
natBndg := nat.PortBinding{HostIP: pp.HostIP.String(), HostPort: strconv.Itoa(int(pp.HostPort))}
|
||||||
networkSettings.Ports[natPort] = append(networkSettings.Ports[natPort], natBndg)
|
pm[natPort] = append(pm[natPort], natBndg)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return nil
|
return pm, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func getSandboxPortMapInfo(sb libnetwork.Sandbox) nat.PortMap {
|
||||||
|
pm := nat.PortMap{}
|
||||||
|
if sb == nil {
|
||||||
|
return pm
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, ep := range sb.Endpoints() {
|
||||||
|
pm, _ = getEndpointPortMapInfo(ep)
|
||||||
|
if len(pm) > 0 {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return pm
|
||||||
}
|
}
|
||||||
|
|
||||||
// BuildEndpointInfo sets endpoint-related fields on container.NetworkSettings based on the provided network and endpoint.
|
// BuildEndpointInfo sets endpoint-related fields on container.NetworkSettings based on the provided network and endpoint.
|
||||||
|
@ -261,7 +284,7 @@ func (container *Container) BuildJoinOptions(n libnetwork.Network) ([]libnetwork
|
||||||
}
|
}
|
||||||
|
|
||||||
// BuildCreateEndpointOptions builds endpoint options from a given network.
|
// BuildCreateEndpointOptions builds endpoint options from a given network.
|
||||||
func (container *Container) BuildCreateEndpointOptions(n libnetwork.Network, epConfig *network.EndpointSettings) ([]libnetwork.EndpointOption, error) {
|
func (container *Container) BuildCreateEndpointOptions(n libnetwork.Network, epConfig *network.EndpointSettings, sb libnetwork.Sandbox) ([]libnetwork.EndpointOption, error) {
|
||||||
var (
|
var (
|
||||||
portSpecs = make(nat.PortSet)
|
portSpecs = make(nat.PortSet)
|
||||||
bindings = make(nat.PortMap)
|
bindings = make(nat.PortMap)
|
||||||
|
@ -290,10 +313,29 @@ func (container *Container) BuildCreateEndpointOptions(n libnetwork.Network, epC
|
||||||
createOptions = append(createOptions, libnetwork.CreateOptionDisableResolution())
|
createOptions = append(createOptions, libnetwork.CreateOptionDisableResolution())
|
||||||
}
|
}
|
||||||
|
|
||||||
// Other configs are applicable only for the endpoint in the network
|
// configs that are applicable only for the endpoint in the network
|
||||||
// to which container was connected to on docker run.
|
// to which container was connected to on docker run.
|
||||||
if n.Name() != container.HostConfig.NetworkMode.NetworkName() &&
|
// Ideally all these network-specific endpoint configurations must be moved under
|
||||||
!(n.Name() == "bridge" && container.HostConfig.NetworkMode.IsDefault()) {
|
// container.NetworkSettings.Networks[n.Name()]
|
||||||
|
if n.Name() == container.HostConfig.NetworkMode.NetworkName() ||
|
||||||
|
(n.Name() == "bridge" && container.HostConfig.NetworkMode.IsDefault()) {
|
||||||
|
if container.Config.MacAddress != "" {
|
||||||
|
mac, err := net.ParseMAC(container.Config.MacAddress)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
genericOption := options.Generic{
|
||||||
|
netlabel.MacAddress: mac,
|
||||||
|
}
|
||||||
|
|
||||||
|
createOptions = append(createOptions, libnetwork.EndpointOptionGeneric(genericOption))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Port-mapping rules belong to the container & applicable only to non-internal networks
|
||||||
|
portmaps := getSandboxPortMapInfo(sb)
|
||||||
|
if n.Info().Internal() || len(portmaps) > 0 {
|
||||||
return createOptions, nil
|
return createOptions, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -353,19 +395,6 @@ func (container *Container) BuildCreateEndpointOptions(n libnetwork.Network, epC
|
||||||
libnetwork.CreateOptionPortMapping(pbList),
|
libnetwork.CreateOptionPortMapping(pbList),
|
||||||
libnetwork.CreateOptionExposedPorts(exposeList))
|
libnetwork.CreateOptionExposedPorts(exposeList))
|
||||||
|
|
||||||
if container.Config.MacAddress != "" {
|
|
||||||
mac, err := net.ParseMAC(container.Config.MacAddress)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
|
|
||||||
genericOption := options.Generic{
|
|
||||||
netlabel.MacAddress: mac,
|
|
||||||
}
|
|
||||||
|
|
||||||
createOptions = append(createOptions, libnetwork.EndpointOptionGeneric(genericOption))
|
|
||||||
}
|
|
||||||
|
|
||||||
return createOptions, nil
|
return createOptions, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -765,7 +765,8 @@ func (daemon *Daemon) connectToNetwork(container *container.Container, idOrName
|
||||||
|
|
||||||
controller := daemon.netController
|
controller := daemon.netController
|
||||||
|
|
||||||
createOptions, err := container.BuildCreateEndpointOptions(n, endpointConfig)
|
sb := daemon.getNetworkSandbox(container)
|
||||||
|
createOptions, err := container.BuildCreateEndpointOptions(n, endpointConfig, sb)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -791,7 +792,6 @@ func (daemon *Daemon) connectToNetwork(container *container.Container, idOrName
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
sb := daemon.getNetworkSandbox(container)
|
|
||||||
if sb == nil {
|
if sb == nil {
|
||||||
options, err := daemon.buildSandboxOptions(container, n)
|
options, err := daemon.buildSandboxOptions(container, n)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
|
@ -27,7 +27,7 @@ clone git github.com/RackSec/srslog 6eb773f331e46fbba8eecb8e794e635e75fc04de
|
||||||
clone git github.com/imdario/mergo 0.2.1
|
clone git github.com/imdario/mergo 0.2.1
|
||||||
|
|
||||||
#get libnetwork packages
|
#get libnetwork packages
|
||||||
clone git github.com/docker/libnetwork v0.6.0-rc3
|
clone git github.com/docker/libnetwork v0.6.0-rc4
|
||||||
clone git github.com/armon/go-metrics eb0af217e5e9747e41dd5303755356b62d28e3ec
|
clone git github.com/armon/go-metrics eb0af217e5e9747e41dd5303755356b62d28e3ec
|
||||||
clone git github.com/hashicorp/go-msgpack 71c2886f5a673a35f909803f38ece5810165097b
|
clone git github.com/hashicorp/go-msgpack 71c2886f5a673a35f909803f38ece5810165097b
|
||||||
clone git github.com/hashicorp/memberlist 9a1e242e454d2443df330bdd51a436d5a9058fc4
|
clone git github.com/hashicorp/memberlist 9a1e242e454d2443df330bdd51a436d5a9058fc4
|
||||||
|
|
|
@ -293,3 +293,24 @@ func (s *DockerSuite) TestPortExposeHostBinding(c *check.C) {
|
||||||
// Port is still bound after the Container is removed
|
// Port is still bound after the Container is removed
|
||||||
c.Assert(err, checker.NotNil, check.Commentf("out: %s", out))
|
c.Assert(err, checker.NotNil, check.Commentf("out: %s", out))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (s *DockerSuite) TestPortBindingOnSandbox(c *check.C) {
|
||||||
|
testRequires(c, DaemonIsLinux, NotUserNamespace)
|
||||||
|
dockerCmd(c, "network", "create", "--internal", "-d", "bridge", "internal-net")
|
||||||
|
dockerCmd(c, "run", "--net", "internal-net", "-d", "--name", "c1",
|
||||||
|
"-p", "8080:8080", "busybox", "nc", "-l", "-p", "8080")
|
||||||
|
c.Assert(waitRun("c1"), check.IsNil)
|
||||||
|
|
||||||
|
_, _, err := dockerCmdWithError("run", "--net=host", "busybox", "nc", "localhost", "8080")
|
||||||
|
c.Assert(err, check.NotNil,
|
||||||
|
check.Commentf("Port mapping on internal network is expected to fail"))
|
||||||
|
|
||||||
|
// Connect container to another normal bridge network
|
||||||
|
dockerCmd(c, "network", "create", "-d", "bridge", "foo-net")
|
||||||
|
dockerCmd(c, "network", "connect", "foo-net", "c1")
|
||||||
|
|
||||||
|
_, _, err = dockerCmdWithError("run", "--net=host", "busybox", "nc", "localhost", "8080")
|
||||||
|
c.Assert(err, check.IsNil,
|
||||||
|
check.Commentf("Port mapping on the new network is expected to succeed"))
|
||||||
|
|
||||||
|
}
|
||||||
|
|
|
@ -1,5 +1,9 @@
|
||||||
# Changelog
|
# Changelog
|
||||||
|
|
||||||
|
## 0.6.0-rc4 (2016-01-25)
|
||||||
|
- Add Endpoints() API to Sandbox interface
|
||||||
|
- Fixed a race-condition in default gateway network creation
|
||||||
|
|
||||||
## 0.6.0-rc3 (2016-01-25)
|
## 0.6.0-rc3 (2016-01-25)
|
||||||
- Fixes docker/docker#19576
|
- Fixes docker/docker#19576
|
||||||
- Fixed embedded DNS to listen in TCP as well
|
- Fixed embedded DNS to listen in TCP as well
|
||||||
|
|
|
@ -12,6 +12,8 @@ const (
|
||||||
gwEPlen = 12
|
gwEPlen = 12
|
||||||
)
|
)
|
||||||
|
|
||||||
|
var procGwNetwork = make(chan (bool), 1)
|
||||||
|
|
||||||
/*
|
/*
|
||||||
libnetwork creates a bridge network "docker_gw_bridge" for provding
|
libnetwork creates a bridge network "docker_gw_bridge" for provding
|
||||||
default gateway for the containers if none of the container's endpoints
|
default gateway for the containers if none of the container's endpoints
|
||||||
|
@ -35,13 +37,11 @@ func (sb *sandbox) setupDefaultGW(srcEp *endpoint) error {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Look for default gw network. In case of error (includes not found),
|
||||||
|
// retry and create it if needed in a serialized execution.
|
||||||
n, err := c.NetworkByName(libnGWNetwork)
|
n, err := c.NetworkByName(libnGWNetwork)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
if _, ok := err.(types.NotFoundError); !ok {
|
if n, err = c.defaultGwNetwork(); err != nil {
|
||||||
return err
|
|
||||||
}
|
|
||||||
n, err = c.createGWNetwork()
|
|
||||||
if err != nil {
|
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -150,3 +150,18 @@ func (sb *sandbox) getEPwithoutGateway() *endpoint {
|
||||||
}
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Looks for the default gw network and creates it if not there.
|
||||||
|
// Parallel executions are serialized.
|
||||||
|
func (c *controller) defaultGwNetwork() (Network, error) {
|
||||||
|
procGwNetwork <- true
|
||||||
|
defer func() { <-procGwNetwork }()
|
||||||
|
|
||||||
|
n, err := c.NetworkByName(libnGWNetwork)
|
||||||
|
if err != nil {
|
||||||
|
if _, ok := err.(types.NotFoundError); ok {
|
||||||
|
n, err = c.createGWNetwork()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return n, err
|
||||||
|
}
|
||||||
|
|
|
@ -47,6 +47,8 @@ type Sandbox interface {
|
||||||
// ResolveIP returns the service name for the passed in IP. IP is in reverse dotted
|
// ResolveIP returns the service name for the passed in IP. IP is in reverse dotted
|
||||||
// notation; the format used for DNS PTR records
|
// notation; the format used for DNS PTR records
|
||||||
ResolveIP(name string) string
|
ResolveIP(name string) string
|
||||||
|
// Endpoints returns all the endpoints connected to the sandbox
|
||||||
|
Endpoints() []Endpoint
|
||||||
}
|
}
|
||||||
|
|
||||||
// SandboxOption is a option setter function type used to pass varios options to
|
// SandboxOption is a option setter function type used to pass varios options to
|
||||||
|
@ -347,6 +349,17 @@ func (sb *sandbox) setupResolutionFiles() error {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (sb *sandbox) Endpoints() []Endpoint {
|
||||||
|
sb.Lock()
|
||||||
|
defer sb.Unlock()
|
||||||
|
|
||||||
|
endpoints := make([]Endpoint, len(sb.endpoints))
|
||||||
|
for i, ep := range sb.endpoints {
|
||||||
|
endpoints[i] = ep
|
||||||
|
}
|
||||||
|
return endpoints
|
||||||
|
}
|
||||||
|
|
||||||
func (sb *sandbox) getConnectedEndpoints() []*endpoint {
|
func (sb *sandbox) getConnectedEndpoints() []*endpoint {
|
||||||
sb.Lock()
|
sb.Lock()
|
||||||
defer sb.Unlock()
|
defer sb.Unlock()
|
||||||
|
|
Loading…
Add table
Reference in a new issue