Browse code

Don't allow passing EnableIPv6 as a driver option (a label)

Signed-off-by: Aidan Hobson Sayers <aidanhs@cantab.net>

Aidan Hobson Sayers authored on 2016/01/30 09:54:57
Showing 7 changed files
... ...
@@ -5,6 +5,7 @@ import (
5 5
 	"fmt"
6 6
 	"io/ioutil"
7 7
 	"net/http"
8
+	"strconv"
8 9
 	"strings"
9 10
 
10 11
 	"github.com/docker/libnetwork"
... ...
@@ -276,22 +277,33 @@ func procCreateNetwork(c libnetwork.NetworkController, vars map[string]string, b
276 276
 
277 277
 	err := json.Unmarshal(body, &create)
278 278
 	if err != nil {
279
-		return "", &responseStatus{Status: "Invalid body: " + err.Error(), StatusCode: http.StatusBadRequest}
279
+		return nil, &responseStatus{Status: "Invalid body: " + err.Error(), StatusCode: http.StatusBadRequest}
280 280
 	}
281 281
 	processCreateDefaults(c, &create)
282 282
 
283 283
 	options := []libnetwork.NetworkOption{}
284
-	if len(create.NetworkOpts) > 0 {
285
-		if _, ok := create.NetworkOpts[netlabel.Internal]; ok {
284
+	if val, ok := create.NetworkOpts[netlabel.Internal]; ok {
285
+		internal, err := strconv.ParseBool(val)
286
+		if err != nil {
287
+			return nil, &responseStatus{Status: err.Error(), StatusCode: http.StatusBadRequest}
288
+		}
289
+		if internal {
286 290
 			options = append(options, libnetwork.NetworkOptionInternalNetwork())
287 291
 		}
288 292
 	}
293
+	if val, ok := create.NetworkOpts[netlabel.EnableIPv6]; ok {
294
+		enableIPv6, err := strconv.ParseBool(val)
295
+		if err != nil {
296
+			return nil, &responseStatus{Status: err.Error(), StatusCode: http.StatusBadRequest}
297
+		}
298
+		options = append(options, libnetwork.NetworkOptionEnableIPv6(enableIPv6))
299
+	}
289 300
 	if len(create.DriverOpts) > 0 {
290 301
 		options = append(options, libnetwork.NetworkOptionDriverOpts(create.DriverOpts))
291 302
 	}
292 303
 	nw, err := c.NewNetwork(create.NetworkType, create.Name, options...)
293 304
 	if err != nil {
294
-		return "", convertNetworkError(err)
305
+		return nil, convertNetworkError(err)
295 306
 	}
296 307
 
297 308
 	return nw.ID(), &createdResponse
... ...
@@ -225,11 +225,13 @@ func TestCreateDeleteNetwork(t *testing.T) {
225 225
 		t.Fatalf("Expected StatusBadRequest status code, got: %v", errRsp)
226 226
 	}
227 227
 
228
-	ops := map[string]string{
229
-		bridge.BridgeName:   "abc",
228
+	dops := map[string]string{
229
+		bridge.BridgeName: "abc",
230
+	}
231
+	nops := map[string]string{
230 232
 		netlabel.EnableIPv6: "true",
231 233
 	}
232
-	nc := networkCreate{Name: "network_1", NetworkType: bridgeNetType, DriverOpts: ops}
234
+	nc := networkCreate{Name: "network_1", NetworkType: bridgeNetType, DriverOpts: dops, NetworkOpts: nops}
233 235
 	goodBody, err := json.Marshal(nc)
234 236
 	if err != nil {
235 237
 		t.Fatal(err)
... ...
@@ -257,29 +259,6 @@ func TestCreateDeleteNetwork(t *testing.T) {
257 257
 	if errRsp != &successResponse {
258 258
 		t.Fatalf("Unexepected failure: %v", errRsp)
259 259
 	}
260
-
261
-	// Create with labels
262
-	labels := map[string]string{
263
-		netlabel.EnableIPv6: "true",
264
-		bridge.BridgeName:   "abc",
265
-	}
266
-	nc = networkCreate{Name: "network_2", NetworkType: bridgeNetType, DriverOpts: labels}
267
-	goodBody, err = json.Marshal(nc)
268
-	if err != nil {
269
-		t.Fatal(err)
270
-	}
271
-
272
-	_, errRsp = procCreateNetwork(c, vars, goodBody)
273
-	if errRsp != &createdResponse {
274
-		t.Fatalf("Unexepected failure: %v", errRsp)
275
-	}
276
-
277
-	vars[urlNwName] = "network_2"
278
-	_, errRsp = procDeleteNetwork(c, vars, nil)
279
-	if errRsp != &successResponse {
280
-		t.Fatalf("Unexepected failure: %v", errRsp)
281
-	}
282
-
283 260
 }
284 261
 
285 262
 func TestGetNetworksAndEndpoints(t *testing.T) {
... ...
@@ -1830,14 +1809,16 @@ func TestEndToEnd(t *testing.T) {
1830 1830
 
1831 1831
 	handleRequest := NewHTTPHandler(c)
1832 1832
 
1833
-	ops := map[string]string{
1834
-		bridge.BridgeName:   "cdef",
1833
+	dops := map[string]string{
1834
+		bridge.BridgeName:  "cdef",
1835
+		netlabel.DriverMTU: "1460",
1836
+	}
1837
+	nops := map[string]string{
1835 1838
 		netlabel.EnableIPv6: "true",
1836
-		netlabel.DriverMTU:  "1460",
1837 1839
 	}
1838 1840
 
1839 1841
 	// Create network
1840
-	nc := networkCreate{Name: "network-fiftyfive", NetworkType: bridgeNetType, DriverOpts: ops}
1842
+	nc := networkCreate{Name: "network-fiftyfive", NetworkType: bridgeNetType, DriverOpts: dops, NetworkOpts: nops}
1841 1843
 	body, err := json.Marshal(nc)
1842 1844
 	if err != nil {
1843 1845
 		t.Fatal(err)
... ...
@@ -43,6 +43,7 @@ func (cli *NetworkCli) CmdNetworkCreate(chain string, args ...string) error {
43 43
 	cmd := cli.Subcmd(chain, "create", "NETWORK-NAME", "Creates a new network with a name specified by the user", false)
44 44
 	flDriver := cmd.String([]string{"d", "-driver"}, "", "Driver to manage the Network")
45 45
 	flInternal := cmd.Bool([]string{"-internal"}, false, "Config the network to be internal")
46
+	flIPv6 := cmd.Bool([]string{"-ipv6"}, false, "Enable IPv6 on the network")
46 47
 	cmd.Require(flag.Exact, 1)
47 48
 	err := cmd.ParseFlags(args, true)
48 49
 	if err != nil {
... ...
@@ -52,6 +53,9 @@ func (cli *NetworkCli) CmdNetworkCreate(chain string, args ...string) error {
52 52
 	if *flInternal {
53 53
 		networkOpts[netlabel.Internal] = "true"
54 54
 	}
55
+	if *flIPv6 {
56
+		networkOpts[netlabel.EnableIPv6] = "true"
57
+	}
55 58
 	// Construct network create request body
56 59
 	var driverOpts []string
57 60
 	nc := networkCreate{Name: cmd.Arg(0), NetworkType: *flDriver, DriverOpts: driverOpts, NetworkOpts: networkOpts}
... ...
@@ -5,8 +5,6 @@ import (
5 5
 	"strconv"
6 6
 
7 7
 	"github.com/docker/libnetwork/drivers/bridge"
8
-	"github.com/docker/libnetwork/netlabel"
9
-	"github.com/docker/libnetwork/options"
10 8
 )
11 9
 
12 10
 func (c *controller) createGWNetwork() (Network, error) {
... ...
@@ -17,10 +15,9 @@ func (c *controller) createGWNetwork() (Network, error) {
17 17
 	}
18 18
 
19 19
 	n, err := c.NewNetwork("bridge", libnGWNetwork,
20
-		NetworkOptionGeneric(options.Generic{
21
-			netlabel.GenericData: netOption,
22
-			netlabel.EnableIPv6:  false,
23
-		}))
20
+		NetworkOptionDriverOpts(netOption),
21
+		NetworkOptionEnableIPv6(false),
22
+	)
24 23
 
25 24
 	if err != nil {
26 25
 		return nil, fmt.Errorf("error creating external connectivity network: %v", err)
... ...
@@ -45,10 +45,6 @@ func TestCreateFullOptions(t *testing.T) {
45 45
 	br, _ := types.ParseCIDR("172.16.0.1/16")
46 46
 	defgw, _ := types.ParseCIDR("172.16.0.100/16")
47 47
 
48
-	netConfig := &networkConfiguration{
49
-		BridgeName: DefaultBridgeName,
50
-		EnableIPv6: true,
51
-	}
52 48
 	genericOption := make(map[string]interface{})
53 49
 	genericOption[netlabel.GenericData] = config
54 50
 
... ...
@@ -57,7 +53,10 @@ func TestCreateFullOptions(t *testing.T) {
57 57
 	}
58 58
 
59 59
 	netOption := make(map[string]interface{})
60
-	netOption[netlabel.GenericData] = netConfig
60
+	netOption[netlabel.EnableIPv6] = true
61
+	netOption[netlabel.GenericData] = &networkConfiguration{
62
+		BridgeName: DefaultBridgeName,
63
+	}
61 64
 
62 65
 	ipdList := []driverapi.IPAMData{
63 66
 		driverapi.IPAMData{
... ...
@@ -118,15 +117,15 @@ func TestCreateFullOptionsLabels(t *testing.T) {
118 118
 	gwV6, _ := types.ParseCIDR(gwV6s)
119 119
 
120 120
 	labels := map[string]string{
121
-		BridgeName:          DefaultBridgeName,
122
-		DefaultBridge:       "true",
123
-		netlabel.EnableIPv6: "true",
124
-		EnableICC:           "true",
125
-		EnableIPMasquerade:  "true",
126
-		DefaultBindingIP:    bndIPs,
121
+		BridgeName:         DefaultBridgeName,
122
+		DefaultBridge:      "true",
123
+		EnableICC:          "true",
124
+		EnableIPMasquerade: "true",
125
+		DefaultBindingIP:   bndIPs,
127 126
 	}
128 127
 
129 128
 	netOption := make(map[string]interface{})
129
+	netOption[netlabel.EnableIPv6] = true
130 130
 	netOption[netlabel.GenericData] = labels
131 131
 
132 132
 	ipdList := getIPv4Data(t)
... ...
@@ -783,13 +782,13 @@ func TestSetDefaultGw(t *testing.T) {
783 783
 
784 784
 	config := &networkConfiguration{
785 785
 		BridgeName:         DefaultBridgeName,
786
-		EnableIPv6:         true,
787 786
 		AddressIPv6:        subnetv6,
788 787
 		DefaultGatewayIPv4: gw4,
789 788
 		DefaultGatewayIPv6: gw6,
790 789
 	}
791 790
 
792 791
 	genericOption := make(map[string]interface{})
792
+	genericOption[netlabel.EnableIPv6] = true
793 793
 	genericOption[netlabel.GenericData] = config
794 794
 
795 795
 	err := d.CreateNetwork("dummy", genericOption, ipdList, nil)
... ...
@@ -269,9 +269,9 @@ func TestBridge(t *testing.T) {
269 269
 	}
270 270
 
271 271
 	netOption := options.Generic{
272
+		netlabel.EnableIPv6: true,
272 273
 		netlabel.GenericData: options.Generic{
273 274
 			"BridgeName":         "testnetwork",
274
-			"EnableIPv6":         true,
275 275
 			"EnableICC":          true,
276 276
 			"EnableIPMasquerade": true,
277 277
 		},
... ...
@@ -323,7 +323,6 @@ func TestBridgeIpv6FromMac(t *testing.T) {
323 323
 	netOption := options.Generic{
324 324
 		netlabel.GenericData: options.Generic{
325 325
 			"BridgeName":         "testipv6mac",
326
-			"EnableIPv6":         true,
327 326
 			"EnableICC":          true,
328 327
 			"EnableIPMasquerade": true,
329 328
 		},
... ...
@@ -333,6 +332,7 @@ func TestBridgeIpv6FromMac(t *testing.T) {
333 333
 
334 334
 	network, err := controller.NewNetwork(bridgeNetType, "testipv6mac",
335 335
 		libnetwork.NetworkOptionGeneric(netOption),
336
+		libnetwork.NetworkOptionEnableIPv6(true),
336 337
 		libnetwork.NetworkOptionIpam(ipamapi.DefaultIPAM, "", ipamV4ConfList, ipamV6ConfList, nil),
337 338
 		libnetwork.NetworkOptionDeferIPv6Alloc(true))
338 339
 	if err != nil {
... ...
@@ -1008,7 +1008,6 @@ func TestEndpointJoin(t *testing.T) {
1008 1008
 	netOption := options.Generic{
1009 1009
 		netlabel.GenericData: options.Generic{
1010 1010
 			"BridgeName":         "testnetwork1",
1011
-			"EnableIPv6":         true,
1012 1011
 			"EnableICC":          true,
1013 1012
 			"EnableIPMasquerade": true,
1014 1013
 		},
... ...
@@ -1016,6 +1015,7 @@ func TestEndpointJoin(t *testing.T) {
1016 1016
 	ipamV6ConfList := []*libnetwork.IpamConf{&libnetwork.IpamConf{PreferredPool: "fe90::/64", Gateway: "fe90::22"}}
1017 1017
 	n1, err := controller.NewNetwork(bridgeNetType, "testnetwork1",
1018 1018
 		libnetwork.NetworkOptionGeneric(netOption),
1019
+		libnetwork.NetworkOptionEnableIPv6(true),
1019 1020
 		libnetwork.NetworkOptionIpam(ipamapi.DefaultIPAM, "", nil, ipamV6ConfList, nil),
1020 1021
 		libnetwork.NetworkOptionDeferIPv6Alloc(true))
1021 1022
 	if err != nil {
... ...
@@ -4,7 +4,6 @@ import (
4 4
 	"encoding/json"
5 5
 	"fmt"
6 6
 	"net"
7
-	"strconv"
8 7
 	"strings"
9 8
 	"sync"
10 9
 
... ...
@@ -476,9 +475,17 @@ type NetworkOption func(n *network)
476 476
 // in a Dictionary of Key-Value pair
477 477
 func NetworkOptionGeneric(generic map[string]interface{}) NetworkOption {
478 478
 	return func(n *network) {
479
-		n.generic = generic
480
-		if _, ok := generic[netlabel.EnableIPv6]; ok {
481
-			n.enableIPv6 = generic[netlabel.EnableIPv6].(bool)
479
+		if n.generic == nil {
480
+			n.generic = make(map[string]interface{})
481
+		}
482
+		if val, ok := generic[netlabel.EnableIPv6]; ok {
483
+			n.enableIPv6 = val.(bool)
484
+		}
485
+		if val, ok := generic[netlabel.Internal]; ok {
486
+			n.internal = val.(bool)
487
+		}
488
+		for k, v := range generic {
489
+			n.generic[k] = v
482 490
 		}
483 491
 	}
484 492
 }
... ...
@@ -490,14 +497,25 @@ func NetworkOptionPersist(persist bool) NetworkOption {
490 490
 	}
491 491
 }
492 492
 
493
+// NetworkOptionEnableIPv6 returns an option setter to explicitly configure IPv6
494
+func NetworkOptionEnableIPv6(enableIPv6 bool) NetworkOption {
495
+	return func(n *network) {
496
+		if n.generic == nil {
497
+			n.generic = make(map[string]interface{})
498
+		}
499
+		n.enableIPv6 = enableIPv6
500
+		n.generic[netlabel.EnableIPv6] = enableIPv6
501
+	}
502
+}
503
+
493 504
 // NetworkOptionInternalNetwork returns an option setter to config the network
494 505
 // to be internal which disables default gateway service
495 506
 func NetworkOptionInternalNetwork() NetworkOption {
496 507
 	return func(n *network) {
497
-		n.internal = true
498 508
 		if n.generic == nil {
499 509
 			n.generic = make(map[string]interface{})
500 510
 		}
511
+		n.internal = true
501 512
 		n.generic[netlabel.Internal] = true
502 513
 	}
503 514
 }
... ...
@@ -526,13 +544,6 @@ func NetworkOptionDriverOpts(opts map[string]string) NetworkOption {
526 526
 		}
527 527
 		// Store the options
528 528
 		n.generic[netlabel.GenericData] = opts
529
-		// Decode and store the endpoint options of libnetwork interest
530
-		if val, ok := opts[netlabel.EnableIPv6]; ok {
531
-			var err error
532
-			if n.enableIPv6, err = strconv.ParseBool(val); err != nil {
533
-				log.Warnf("Failed to parse %s' value: %s (%s)", netlabel.EnableIPv6, val, err.Error())
534
-			}
535
-		}
536 529
 	}
537 530
 }
538 531