diff --git a/CHANGELOG.md b/CHANGELOG.md index 6b3c77ea..5807d208 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,59 @@ +## Release 0.11.2 + +This is a bug fix release, addressing the following issues: + +- `weave run` did not respect DOCKER_CLIENT_ARGS. #855 +- Negative result cache did not expire if requeried within TTL. #845 + +More details in the [change +log](https://github.com/weaveworks/weave/issues?q=milestone%3A0.11.2). + +*NB: This release does not change the weave protocol version. +Therefore, when upgrading an existing 0.11 installation incrementally, +connectivity between peers will be retained.* + +## Release 0.11.1 + +This is a bug fix release, addressing the following issues: + +- The IP Allocator could crash in some relatively rare + circumstances. #782/#783. +- When the proxy failed to attach a container to the weave network, + there was no failure indication and descriptive error anywhere, and + the application process would still start. Now an error is reported + to the client (i.e. typically the Docker CLI), recorded in the proxy + logs, and the container is terminated. #788/#799. +- `weave launch-proxy --with-ipam` failed to configure the entrypoint + and DNS unless a (possibly blank) `WEAVE_CIDR` was + specified. Affected containers could start the application process + w/o the weave network interface being available, and without + functioning name resolution for the weaveDNS domain. + #744/#747/#751/#752 +- The `weave status` output for the IP Allocator was misleadingly + conveying a sense of brokenness when no IP allocation requests had + been made yet. #787/#801 +- When invoking `weave launch-proxy` twice, the second invocation + would output a blank line and terminate with a success exit + status. Now it reports that the proxy is already running and exits + with a non-zero status. #767/#780 +- `weave launch-proxy` was not respecting WEAVEPROXY_DOCKER_ARGS, so + any user-supplied custom configuration for the weaveproxy container + was ignored. #755/#780 +- The proxy was not intercepting API calls to the unversioned (1.0) + Docker Remote API. Hence none of the weave functionality was + available when Docker clients were using that version of the + API. #770/#774/#777,#809 +- The proxy would crash when certain elements of the + `/containers/create` JSON were missing. We are not aware of any + Docker clients doing this, but it's been fixed regardless. #778/#777 + +More details in the [change +log](https://github.com/weaveworks/weave/issues?q=milestone%3A0.11.1). + +*NB: This release does not change the weave protocol version. +Therefore, when upgrading an existing 0.11 installation incrementally, +connectivity between peers will be retained.* + ## Release 0.11.0 **Highlights**: diff --git a/ipam/address/address.go b/ipam/address/address.go index b9f47ac3..97e162d0 100644 --- a/ipam/address/address.go +++ b/ipam/address/address.go @@ -52,3 +52,10 @@ func Subtract(a, b Address) Offset { common.Assert(a >= b) return Offset(a - b) } + +func Min(a, b Offset) Offset { + if a > b { + return b + } + return a +} diff --git a/ipam/allocator.go b/ipam/allocator.go index d7ec53cb..1fa2a0e8 100644 --- a/ipam/allocator.go +++ b/ipam/allocator.go @@ -456,10 +456,12 @@ func (alloc *Allocator) actorLoop(actionChan <-chan func()) { func (alloc *Allocator) string() string { var buf bytes.Buffer - fmt.Fprintf(&buf, "Allocator subnet %s/%d\n", alloc.subnetStart.String(), alloc.prefixLen) + fmt.Fprintf(&buf, "Allocator subnet %s/%d", alloc.subnetStart.String(), alloc.prefixLen) if alloc.ring.Empty() { - fmt.Fprintf(&buf, "Awaiting consensus: %s", alloc.paxos.String()) + if alloc.paxosTicker != nil { + fmt.Fprintf(&buf, " awaiting consensus: %s", alloc.paxos.String()) + } } else { localFreeSpace := alloc.space.NumFreeAddresses() remoteFreeSpace := alloc.ring.TotalRemoteFree() @@ -469,14 +471,14 @@ func (alloc *Allocator) string() string { fmt.Fprint(&buf, "Owned Ranges:") alloc.ring.FprintWithNicknames(&buf, alloc.nicknames) - if len(alloc.pendingAllocates)+len(alloc.pendingClaims) > 0 { - fmt.Fprintf(&buf, "\nPending requests for ") - for _, op := range alloc.pendingAllocates { - fmt.Fprintf(&buf, "%s, ", op.String()) - } - for _, op := range alloc.pendingClaims { - fmt.Fprintf(&buf, "%s, ", op.String()) - } + } + if len(alloc.pendingAllocates)+len(alloc.pendingClaims) > 0 { + fmt.Fprintf(&buf, "\nPending requests:") + for _, op := range alloc.pendingAllocates { + fmt.Fprintf(&buf, "\n %s", op.String()) + } + for _, op := range alloc.pendingClaims { + fmt.Fprintf(&buf, "\n %s", op.String()) } } return buf.String() diff --git a/ipam/ring/ring.go b/ipam/ring/ring.go index 7590a3ce..1bb891f4 100644 --- a/ipam/ring/ring.go +++ b/ipam/ring/ring.go @@ -40,7 +40,6 @@ var ( ErrInvalidEntry = errors.New("Received invalid state update!") ErrEntryInMyRange = errors.New("Received new entry in my range!") ErrNoFreeSpace = errors.New("No free space found!") - ErrTooMuchFreeSpace = errors.New("Entry reporting too much free space!") ErrInvalidTimeout = errors.New("dt must be greater than 0") ErrNotFound = errors.New("No entries for peer found") ) @@ -76,7 +75,7 @@ func (r *Ring) checkInvariants() error { distance := r.distance(entry.Token, next.Token) if entry.Free > distance { - return ErrTooMuchFreeSpace + return fmt.Errorf("Entry %s-%s reporting too much free space: %d > %d", entry.Token, next.Token, entry.Free, distance) } } @@ -167,7 +166,7 @@ func (r *Ring) GrantRangeToHost(start, end address.Address, peer router.PeerName pos := preceedingPos + 1 for ; pos < len(r.Entries) && r.Entries.entry(pos).Token < end; pos++ { entry := r.Entries.entry(pos) - entry.update(peer, entry.Free) + entry.update(peer, address.Min(entry.Free, r.distance(entry.Token, end))) } // There is never an entry with a token of r.End, as the end of diff --git a/ipam/ring/ring_test.go b/ipam/ring/ring_test.go index 1c12c777..f3ec1e0f 100644 --- a/ipam/ring/ring_test.go +++ b/ipam/ring/ring_test.go @@ -158,6 +158,17 @@ func TestGrantSplit(t *testing.T) { wt.AssertEquals(t, ring1.Entries, entries{{Token: start, Peer: peer1name, Free: 10, Version: 1}, {Token: dot10, Peer: peer2name, Free: 235}, {Token: dot245, Peer: peer1name, Free: 10}}) + ring1.assertInvariants() + + // Grant range spanning a live token, and inserting a new token + ring1.Entries = []*entry{{Token: start, Peer: peer1name, Free: 10, Version: 2}, + {Token: dot10, Peer: peer1name, Free: 118}, {Token: middle, Peer: peer1name, Free: 127}} + ring1.GrantRangeToHost(dot10, dot245, peer2name) + wt.AssertEquals(t, ring1.Entries, entries{{Token: start, Peer: peer1name, Free: 10, Version: 2}, + {Token: dot10, Peer: peer2name, Free: 118, Version: 1}, + {Token: middle, Peer: peer2name, Free: 117, Version: 1}, + {Token: dot245, Peer: peer1name, Free: 10, Version: 0}}) + ring1.assertInvariants() } func TestMergeSimple(t *testing.T) { diff --git a/nameserver/cache.go b/nameserver/cache.go index 644814f0..30937375 100644 --- a/nameserver/cache.go +++ b/nameserver/cache.go @@ -5,13 +5,14 @@ import ( "container/heap" "errors" "fmt" - "github.com/benbjohnson/clock" - "github.com/miekg/dns" - . "github.com/weaveworks/weave/common" "math" "math/rand" "sync" "time" + + "github.com/benbjohnson/clock" + "github.com/miekg/dns" + . "github.com/weaveworks/weave/common" ) var ( @@ -145,9 +146,12 @@ func (e *cacheEntry) setReply(reply *dns.Msg, ttl int, flags uint8, now time.Tim prevValidUntil = e.validUntil } - e.Status = stResolved - e.Flags = flags - e.putTime = now + // make sure we do not overwrite noLocalReplies entries + if flags&CacheNoLocalReplies != 0 { + if e.Flags&CacheNoLocalReplies != 0 { + return false + } + } if ttl != nullTTL { e.validUntil = now.Add(time.Second * time.Duration(ttl)) @@ -161,8 +165,14 @@ func (e *cacheEntry) setReply(reply *dns.Msg, ttl int, flags uint8, now time.Tim } } e.validUntil = now.Add(time.Second * time.Duration(minTTL)) + } else { + Warning.Printf("[cache] no valid TTL could be calculated") } + e.Status = stResolved + e.Flags = flags + e.putTime = now + if reply != nil { e.reply = *reply e.ReplyLen = reply.Len() diff --git a/nameserver/cache_test.go b/nameserver/cache_test.go index b53d7529..9e4c5584 100644 --- a/nameserver/cache_test.go +++ b/nameserver/cache_test.go @@ -2,13 +2,14 @@ package nameserver import ( "fmt" + "net" + "testing" + "time" + "github.com/benbjohnson/clock" "github.com/miekg/dns" . "github.com/weaveworks/weave/common" wt "github.com/weaveworks/weave/testing" - "net" - "testing" - "time" ) // Check that the cache keeps its intended capacity constant @@ -195,12 +196,23 @@ func TestCacheEntries(t *testing.T) { question3 := &questionMsg3.Question[0] t.Logf("Checking that a entry with CacheNoLocalReplies return an error") - l.Put(questionMsg3, nil, nullTTL, CacheNoLocalReplies) + l.Put(questionMsg3, nil, negLocalTTL, CacheNoLocalReplies) resp, err = l.Get(questionMsg3, minUDPSize) wt.AssertNil(t, resp, "Get() response with CacheNoLocalReplies") - wt.AssertNotNil(t, err, "Get() error with CacheNoLocalReplies") + wt.AssertTrue(t, err == errNoLocalReplies, "Get() error with CacheNoLocalReplies") - clk.Add(time.Second * time.Duration(negLocalTTL+1)) + t.Logf("Checking that more Put's do not make the negative TTL longer") + clk.Add(time.Duration(negLocalTTL/2) * time.Second) + l.Put(questionMsg3, nil, negLocalTTL, CacheNoLocalReplies) + clk.Add(time.Duration(1) * time.Second) + l.Put(questionMsg3, nil, negLocalTTL, CacheNoLocalReplies) + clk.Add(time.Duration(1) * time.Second) + l.Put(questionMsg3, nil, negLocalTTL, CacheNoLocalReplies) + resp, err = l.Get(questionMsg3, minUDPSize) + wt.AssertNil(t, resp, "Get() response with CacheNoLocalReplies") + wt.AssertTrue(t, err == errNoLocalReplies, "Get() error with CacheNoLocalReplies") + + clk.Add(time.Duration(negLocalTTL/2) * time.Second) t.Logf("Checking that we get an expired response after %f seconds", negLocalTTL) resp, err = l.Get(questionMsg3, minUDPSize) wt.AssertNil(t, resp, "expired Get() response with CacheNoLocalReplies") diff --git a/proxy/client.go b/proxy/client.go index 57cf98f4..87e1a968 100644 --- a/proxy/client.go +++ b/proxy/client.go @@ -35,7 +35,7 @@ func (c *client) ServeHTTP(w http.ResponseWriter, r *http.Request) { case err == docker.ErrNoSuchImage: http.Error(w, err.Error(), http.StatusNotFound) default: - http.Error(w, "Unable to intercept request", http.StatusInternalServerError) + http.Error(w, err.Error(), http.StatusInternalServerError) Warning.Print("Error intercepting request: ", err) } return @@ -58,7 +58,7 @@ func (c *client) ServeHTTP(w http.ResponseWriter, r *http.Request) { } err = c.InterceptResponse(resp) if err != nil { - http.Error(w, "Unable to intercept response", http.StatusInternalServerError) + http.Error(w, err.Error(), http.StatusInternalServerError) Warning.Print("Error intercepting response: ", err) return } diff --git a/proxy/common.go b/proxy/common.go index 1198ef1b..6f6480fb 100644 --- a/proxy/common.go +++ b/proxy/common.go @@ -15,7 +15,7 @@ import ( ) var ( - containerIDRegexp = regexp.MustCompile("^/v[0-9\\.]*/containers/([^/]*)/.*") + containerIDRegexp = regexp.MustCompile("^(/v[0-9\\.]*)?/containers/([^/]*)/.*") weaveWaitEntrypoint = []string{"/home/weavewait/weavewait"} ) @@ -54,7 +54,7 @@ func inspectContainerInPath(client *docker.Client, path string) (*docker.Contain Warning.Println(err) return nil, err } - containerID := subs[1] + containerID := subs[2] container, err := client.InspectContainer(containerID) if err != nil { diff --git a/proxy/create_container_interceptor.go b/proxy/create_container_interceptor.go index 2aa8c4dd..3585fbd2 100644 --- a/proxy/create_container_interceptor.go +++ b/proxy/create_container_interceptor.go @@ -15,6 +15,7 @@ type createContainerInterceptor struct { client *docker.Client withDNS bool dockerBridgeIP string + withIPAM bool } type createContainerRequestBody struct { @@ -35,9 +36,15 @@ func (i *createContainerInterceptor) InterceptRequest(r *http.Request) error { return err } - if cidrs, ok := weaveCIDRsFromConfig(container.Config); ok { + if cidrs, ok := weaveCIDRsFromConfig(container.Config); ok || i.withIPAM { Info.Printf("Creating container with WEAVE_CIDR \"%s\"", strings.Join(cidrs, " ")) + if container.HostConfig == nil { + container.HostConfig = &docker.HostConfig{} + } container.HostConfig.VolumesFrom = append(container.HostConfig.VolumesFrom, "weaveproxy") + if container.Config == nil { + container.Config = &docker.Config{} + } if err := i.setWeaveWaitEntrypoint(container.Config); err != nil { return err } diff --git a/proxy/create_exec_interceptor.go b/proxy/create_exec_interceptor.go index 00050115..e3a9bc30 100644 --- a/proxy/create_exec_interceptor.go +++ b/proxy/create_exec_interceptor.go @@ -11,7 +11,8 @@ import ( ) type createExecInterceptor struct { - client *docker.Client + client *docker.Client + withIPAM bool } type createExecRequestBody struct { @@ -37,7 +38,7 @@ func (i *createExecInterceptor) InterceptRequest(r *http.Request) error { return err } - if cidrs, ok := weaveCIDRsFromConfig(container.Config); ok { + if cidrs, ok := weaveCIDRsFromConfig(container.Config); ok || i.withIPAM { Info.Printf("Exec in container %s with WEAVE_CIDR \"%s\"", container.ID, strings.Join(cidrs, " ")) options.Cmd = append(weaveWaitEntrypoint, options.Cmd...) } diff --git a/proxy/proxy.go b/proxy/proxy.go index 03ba90eb..f781385b 100644 --- a/proxy/proxy.go +++ b/proxy/proxy.go @@ -12,9 +12,9 @@ import ( ) var ( - containerCreateRegexp = regexp.MustCompile("/v[0-9\\.]*/containers/create") - containerStartRegexp = regexp.MustCompile("^/v[0-9\\.]*/containers/[^/]*/(re)?start$") - execCreateRegexp = regexp.MustCompile("^/v[0-9\\.]*/containers/[^/]*/exec$") + containerCreateRegexp = regexp.MustCompile("^(/v[0-9\\.]*)?/containers/create$") + containerStartRegexp = regexp.MustCompile("^(/v[0-9\\.]*)?/containers/[^/]*/(re)?start$") + execCreateRegexp = regexp.MustCompile("^(/v[0-9\\.]*)?/containers/[^/]*/exec$") ) type Proxy struct { @@ -68,11 +68,11 @@ func (proxy *Proxy) ServeHTTP(w http.ResponseWriter, r *http.Request) { path := r.URL.Path switch { case containerCreateRegexp.MatchString(path): - proxy.serveWithInterceptor(&createContainerInterceptor{proxy.client, proxy.withDNS, proxy.dockerBridgeIP}, w, r) + proxy.serveWithInterceptor(&createContainerInterceptor{proxy.client, proxy.withDNS, proxy.dockerBridgeIP, proxy.withIPAM}, w, r) case containerStartRegexp.MatchString(path): proxy.serveWithInterceptor(&startContainerInterceptor{proxy.client, proxy.withDNS, proxy.withIPAM}, w, r) case execCreateRegexp.MatchString(path): - proxy.serveWithInterceptor(&createExecInterceptor{proxy.client}, w, r) + proxy.serveWithInterceptor(&createExecInterceptor{proxy.client, proxy.withIPAM}, w, r) case strings.HasPrefix(path, "/weave"): w.WriteHeader(http.StatusOK) default: diff --git a/proxy/start_container_interceptor.go b/proxy/start_container_interceptor.go index bce86074..1b95c733 100644 --- a/proxy/start_container_interceptor.go +++ b/proxy/start_container_interceptor.go @@ -1,6 +1,7 @@ package proxy import ( + "errors" "net/http" "strings" @@ -33,8 +34,10 @@ func (i *startContainerInterceptor) InterceptResponse(r *http.Response) error { args := []string{"attach"} args = append(args, cidrs...) args = append(args, container.ID) - if _, err := callWeave(args...); err != nil { - Warning.Printf("Attaching container %s to weave network failed: %v", container.ID, err) + if output, err := callWeave(args...); err != nil { + i.client.KillContainer(docker.KillContainerOptions{ID: container.ID}) + Warning.Printf("Attaching container %s to weave network failed: %s", container.ID, string(output)) + return errors.New(string(output)) } return nil } diff --git a/site/proxy.md b/site/proxy.md index 7cc16989..d6687340 100644 --- a/site/proxy.md +++ b/site/proxy.md @@ -76,8 +76,31 @@ without a `WEAVE_CIDR`, we can launch the proxy with the `--with-ipam` option. For example: host1$ weave launch-proxy --with-ipam + host1$ export DOCKER_HOST=tcp://host1:12375 -More details on IPAM can be found in the [IPAM documentation](ipam.html). +Now, containers will always be automatically assigned an IP address +and attached to the weave network when we start them. For example: + + host1$ docker run -ti ubuntu /bin/sh + +More details on IPAM can be found in the [IPAM +documentation](ipam.html). + +## Usage with WeaveDNS + +Containers started via the proxy can be automatically configured to +use WeaveDNS for name resolution. To accomplish this we need to launch +the proxy with the `--with-dns` option + + host1$ weave launch + host1$ weave launch-dns 10.2.254.1/24 + host1$ weave launch-proxy --with-dns + +With this done, any containers connected via IPAM or `WEAVE_CIDR=...`, +which are launched through the proxy will use weaveDNS for name +resolution. WeaveDNS is used in addition to any dns servers specified +via the `--dns` option. More details on weaveDNS can be found in the +[weaveDNS documentation](weavedns.html). ## Usage with WeaveDNS diff --git a/test/620_proxy_entrypoint_command_test.sh b/test/620_proxy_entrypoint_command_test.sh index 73c6401c..d216077d 100755 --- a/test/620_proxy_entrypoint_command_test.sh +++ b/test/620_proxy_entrypoint_command_test.sh @@ -26,4 +26,28 @@ run_container "grep ^1$ /sys/class/net/ethwe/carrier" build_image false '["/bin/false"]' '' run_container "--entrypoint='grep' false ^1$ /sys/class/net/ethwe/carrier" +weave_on $HOST1 launch -iprange 10.2.2.0/24 +docker_on $HOST1 kill weaveproxy +weave_on $HOST1 launch-proxy --with-ipam + +assert_raises "proxy docker_on $HOST1 run check-ethwe-up" + +create_container_json=$(cat <<-EOF +{ + "Hostname":"c1", + "AttachStdin":false, + "AttachStdout":true, + "AttachStderr":true, + "Tty":false, + "OpenStdin":false, + "StdinOnce":false, + "Image":"check-ethwe-up" +} +EOF +) + +# Test a minimal request to the unversioned (v1.0) docker api +CONTAINER_ID=$(curl -s -X POST --header "Content-Type: application/json" http://$HOST1:12375/containers/create -d "$create_container_json" | sed -e 's/.*"Id":"\([^"]*\)".*/\1/') +assert_raises "proxy docker_on $HOST1 start -ai $CONTAINER_ID" + end_suite diff --git a/weave b/weave index 8460bd9e..32d896c7 100755 --- a/weave +++ b/weave @@ -61,6 +61,7 @@ exec_remote() { -e WEAVE_DEBUG \ -e WEAVE_DOCKER_ARGS \ -e WEAVEDNS_DOCKER_ARGS \ + -e WEAVEPROXY_DOCKER_ARGS \ -e WEAVE_PASSWORD \ -e WEAVE_PORT \ -e WEAVE_CONTAINER_NAME \ @@ -141,7 +142,7 @@ if [ "$1" = "run" ]; then fi collect_cidr_args "$@" shift $CIDR_COUNT - CONTAINER=$(docker run $DNS_ARGS -d "$@") + CONTAINER=$(docker $DOCKER_CLIENT_ARGS run $DNS_ARGS -d "$@") exec_remote attach $CIDR_ARGS $CONTAINER echo $CONTAINER exit 0 @@ -167,6 +168,13 @@ MTU=65535 PORT=${WEAVE_PORT:-6783} HTTP_PORT=6784 DNS_HTTP_PORT=6785 +PROXY_PORT=12375 +PROXY_CONTAINER_NAME=weaveproxy +PROXY_HOST="localhost" +if [ "$DOCKER_HOST" != "${DOCKER_HOST#tcp://}" ] ; then + PROXY_HOST=$(echo "$DOCKER_HOST" | sed -e "s|tcp://\([^:]*\):[0-9]*|\1|") +fi + ###################################################################### # general helpers; independent of docker and weave @@ -540,6 +548,18 @@ wait_for_status() { return 1 } +# Just like wait_for_status, but takes the IP instead of a container ID +wait_for_status_ip() { + WAIT_TIME=0 + while [ $WAIT_TIME -lt 3 ]; do + sleep $WAIT_TIME + http_call_ip $1 $2 GET ${3:-/status} >/dev/null && return 0 + WAIT_TIME=$((WAIT_TIME+1)) + done + echo "Timed out waiting for container to start." >&2 + return 1 +} + # Call $1 for all containers, passing container ID, all MACs and all IPs with_container_addresses() { COMMAND=$1 @@ -688,63 +708,6 @@ get_ipam_cidr() { fi } -###################################################################### -# weave proxy helpers -###################################################################### - -PROXY_PORT=12375 -PROXY_CONTAINER_NAME=weaveproxy - -proxy_host() { - case $DOCKER_HOST in - tcp://*) - PROXY_HOST=$(echo $DOCKER_HOST | sed -e "s|tcp://\([^:]*\):[0-9]*|\1|") - ;; - *) - PROXY_HOST="localhost" - ;; - esac -} - -wait_for_proxy_to_boot() { - proxy_host - for n in $(seq 1 10); do - if curl --max-time 1 --connect-timeout 1 -s -X GET http://$PROXY_HOST:$PROXY_PORT/weave ; then - return 0 - fi - sleep 1 - done - echo "Proxy did not start within 10 seconds" >&2 - return 1 -} - -ensure_proxy_running() { - case $(docker inspect --format '{{.State.Running}} {{.Config.Image}}' $PROXY_CONTAINER_NAME 2>/dev/null) in - "true $EXEC_IMAGE") - return 0 - ;; - true*) - echo "Proxy already running with unknown image" >&2 - exit 1 - ;; - false*) - docker rm -f $PROXY_CONTAINER_NAME >/dev/null - ;; - esac - # Set WEAVEPROXY_DOCKER_ARGS in the environment in order to supply - # additional parameters, such as resource limits, to docker - # when launching the weave proxy container. - PROXY_CONTAINER=$(docker run --privileged --net=host -d \ - --name=$PROXY_CONTAINER_NAME \ - -p $PROXY_PORT:$PROXY_PORT/tcp -v /var/run/docker.sock:/var/run/docker.sock \ - -v /proc:/hostproc -e PROCFS=/hostproc \ - --entrypoint=/home/weave/weaveproxy \ - $WEAVE_DOCKER_ARGS $WEAVEPROXY_DOCKER_ARGS \ - $EXEC_IMAGE "$@") - - wait_for_proxy_to_boot -} - ########################################################################################## [ $(id -u) = 0 ] || { @@ -874,7 +837,20 @@ case "$COMMAND" in echo $DNS_CONTAINER ;; launch-proxy) - ensure_proxy_running "$@" + check_not_running $PROXY_CONTAINER_NAME $EXEC_IMAGE + # Set WEAVEPROXY_DOCKER_ARGS in the environment in order to supply + # additional parameters, such as resource limits, to docker + # when launching the weaveproxy container. + PROXY_CONTAINER=$(docker run --privileged --net=host -d \ + --name=$PROXY_CONTAINER_NAME \ + -p $PROXY_PORT:$PROXY_PORT/tcp \ + -v /var/run/docker.sock:/var/run/docker.sock \ + -v /proc:/hostproc -e PROCFS=/hostproc \ + --entrypoint=/home/weave/weaveproxy \ + $WEAVEPROXY_DOCKER_ARGS \ + $EXEC_IMAGE "$@") + + wait_for_status_ip $PROXY_HOST $PROXY_PORT /weave echo $PROXY_CONTAINER ;; connect) diff --git a/weavewait/main.go b/weavewait/main.go index abd5bf76..9d1a2783 100644 --- a/weavewait/main.go +++ b/weavewait/main.go @@ -10,22 +10,22 @@ import ( ) func main() { - if _, err := net.EnsureInterface("ethwe", 20); err != nil { - fmt.Fprintln(os.Stderr, err) - } + _, err := net.EnsureInterface("ethwe", 20) + checkErr(err) if len(os.Args) <= 1 { os.Exit(0) } binary, err := exec.LookPath(os.Args[1]) + checkErr(err) + + checkErr(syscall.Exec(binary, os.Args[1:], os.Environ())) +} + +func checkErr(err error) { if err != nil { fmt.Fprintln(os.Stderr, err) os.Exit(1) } - - if err := syscall.Exec(binary, os.Args[1:], os.Environ()); err != nil { - fmt.Fprintln(os.Stderr, err) - os.Exit(1) - } }