github.com/zhuohuang-hust/src-cbuild@v0.0.0-20230105071821-c7aab3e7c840/mergeCode/libnetwork/drivers/bridge/bridge_test.go (about) 1 package bridge 2 3 import ( 4 "bytes" 5 "encoding/json" 6 "fmt" 7 "net" 8 "regexp" 9 "testing" 10 11 "github.com/docker/libnetwork/driverapi" 12 "github.com/docker/libnetwork/ipamutils" 13 "github.com/docker/libnetwork/iptables" 14 "github.com/docker/libnetwork/netlabel" 15 "github.com/docker/libnetwork/netutils" 16 "github.com/docker/libnetwork/options" 17 "github.com/docker/libnetwork/testutils" 18 "github.com/docker/libnetwork/types" 19 "github.com/vishvananda/netlink" 20 ) 21 22 func init() { 23 ipamutils.InitNetworks() 24 } 25 26 func TestEndpointMarshalling(t *testing.T) { 27 ip1, _ := types.ParseCIDR("172.22.0.9/16") 28 ip2, _ := types.ParseCIDR("2001:db8::9") 29 mac, _ := net.ParseMAC("ac:bd:24:57:66:77") 30 e := &bridgeEndpoint{ 31 id: "d2c015a1fe5930650cbcd50493efba0500bcebd8ee1f4401a16319f8a567de33", 32 nid: "ee33fbb43c323f1920b6b35a0101552ac22ede960d0e5245e9738bccc68b2415", 33 addr: ip1, 34 addrv6: ip2, 35 macAddress: mac, 36 srcName: "veth123456", 37 config: &endpointConfiguration{MacAddress: mac}, 38 containerConfig: &containerConfiguration{ 39 ParentEndpoints: []string{"one", "due", "three"}, 40 ChildEndpoints: []string{"four", "five", "six"}, 41 }, 42 extConnConfig: &connectivityConfiguration{ 43 ExposedPorts: []types.TransportPort{ 44 { 45 Proto: 6, 46 Port: uint16(18), 47 }, 48 }, 49 PortBindings: []types.PortBinding{ 50 { 51 Proto: 6, 52 IP: net.ParseIP("17210.33.9.56"), 53 Port: uint16(18), 54 HostPort: uint16(3000), 55 HostPortEnd: uint16(14000), 56 }, 57 }, 58 }, 59 portMapping: []types.PortBinding{ 60 { 61 Proto: 17, 62 IP: net.ParseIP("172.33.9.56"), 63 Port: uint16(99), 64 HostIP: net.ParseIP("10.10.100.2"), 65 HostPort: uint16(9900), 66 HostPortEnd: uint16(10000), 67 }, 68 { 69 Proto: 6, 70 IP: net.ParseIP("171.33.9.56"), 71 Port: uint16(55), 72 HostIP: net.ParseIP("10.11.100.2"), 73 HostPort: uint16(5500), 74 HostPortEnd: uint16(55000), 75 }, 76 }, 77 } 78 79 b, err := json.Marshal(e) 80 if err != nil { 81 t.Fatal(err) 82 } 83 84 ee := &bridgeEndpoint{} 85 err = json.Unmarshal(b, ee) 86 if err != nil { 87 t.Fatal(err) 88 } 89 90 if e.id != ee.id || e.nid != ee.nid || e.srcName != ee.srcName || !bytes.Equal(e.macAddress, ee.macAddress) || 91 !types.CompareIPNet(e.addr, ee.addr) || !types.CompareIPNet(e.addrv6, ee.addrv6) || 92 !compareEpConfig(e.config, ee.config) || 93 !compareContainerConfig(e.containerConfig, ee.containerConfig) || 94 !compareConnConfig(e.extConnConfig, ee.extConnConfig) || 95 !compareBindings(e.portMapping, ee.portMapping) { 96 t.Fatalf("JSON marsh/unmarsh failed.\nOriginal:\n%#v\nDecoded:\n%#v", e, ee) 97 } 98 } 99 100 func compareEpConfig(a, b *endpointConfiguration) bool { 101 if a == b { 102 return true 103 } 104 if a == nil || b == nil { 105 return false 106 } 107 return bytes.Equal(a.MacAddress, b.MacAddress) 108 } 109 110 func compareContainerConfig(a, b *containerConfiguration) bool { 111 if a == b { 112 return true 113 } 114 if a == nil || b == nil { 115 return false 116 } 117 if len(a.ParentEndpoints) != len(b.ParentEndpoints) || 118 len(a.ChildEndpoints) != len(b.ChildEndpoints) { 119 return false 120 } 121 for i := 0; i < len(a.ParentEndpoints); i++ { 122 if a.ParentEndpoints[i] != b.ParentEndpoints[i] { 123 return false 124 } 125 } 126 for i := 0; i < len(a.ChildEndpoints); i++ { 127 if a.ChildEndpoints[i] != b.ChildEndpoints[i] { 128 return false 129 } 130 } 131 return true 132 } 133 134 func compareConnConfig(a, b *connectivityConfiguration) bool { 135 if a == b { 136 return true 137 } 138 if a == nil || b == nil { 139 return false 140 } 141 if len(a.ExposedPorts) != len(b.ExposedPorts) || 142 len(a.PortBindings) != len(b.PortBindings) { 143 return false 144 } 145 for i := 0; i < len(a.ExposedPorts); i++ { 146 if !a.ExposedPorts[i].Equal(&b.ExposedPorts[i]) { 147 return false 148 } 149 } 150 for i := 0; i < len(a.PortBindings); i++ { 151 if !a.PortBindings[i].Equal(&b.PortBindings[i]) { 152 return false 153 } 154 } 155 return true 156 } 157 158 func compareBindings(a, b []types.PortBinding) bool { 159 if len(a) != len(b) { 160 return false 161 } 162 for i := 0; i < len(a); i++ { 163 if !a[i].Equal(&b[i]) { 164 return false 165 } 166 } 167 return true 168 } 169 170 func getIPv4Data(t *testing.T, iface string) []driverapi.IPAMData { 171 ipd := driverapi.IPAMData{AddressSpace: "full"} 172 nw, _, err := netutils.ElectInterfaceAddresses(iface) 173 if err != nil { 174 t.Fatal(err) 175 } 176 ipd.Pool = nw 177 // Set network gateway to X.X.X.1 178 ipd.Gateway = types.GetIPNetCopy(nw) 179 ipd.Gateway.IP[len(ipd.Gateway.IP)-1] = 1 180 return []driverapi.IPAMData{ipd} 181 } 182 183 func TestCreateFullOptions(t *testing.T) { 184 defer testutils.SetupTestOSContext(t)() 185 d := newDriver() 186 187 config := &configuration{ 188 EnableIPForwarding: true, 189 EnableIPTables: true, 190 } 191 192 // Test this scenario: Default gw address does not belong to 193 // container network and it's greater than bridge address 194 cnw, _ := types.ParseCIDR("172.16.122.0/24") 195 bnw, _ := types.ParseCIDR("172.16.0.0/24") 196 br, _ := types.ParseCIDR("172.16.0.1/16") 197 defgw, _ := types.ParseCIDR("172.16.0.100/16") 198 199 genericOption := make(map[string]interface{}) 200 genericOption[netlabel.GenericData] = config 201 202 if err := d.configure(genericOption); err != nil { 203 t.Fatalf("Failed to setup driver config: %v", err) 204 } 205 206 netOption := make(map[string]interface{}) 207 netOption[netlabel.EnableIPv6] = true 208 netOption[netlabel.GenericData] = &networkConfiguration{ 209 BridgeName: DefaultBridgeName, 210 } 211 212 ipdList := []driverapi.IPAMData{ 213 { 214 Pool: bnw, 215 Gateway: br, 216 AuxAddresses: map[string]*net.IPNet{DefaultGatewayV4AuxKey: defgw}, 217 }, 218 } 219 err := d.CreateNetwork("dummy", netOption, nil, ipdList, nil) 220 if err != nil { 221 t.Fatalf("Failed to create bridge: %v", err) 222 } 223 224 // Verify the IP address allocated for the endpoint belongs to the container network 225 epOptions := make(map[string]interface{}) 226 te := newTestEndpoint(cnw, 10) 227 err = d.CreateEndpoint("dummy", "ep1", te.Interface(), epOptions) 228 if err != nil { 229 t.Fatalf("Failed to create an endpoint : %s", err.Error()) 230 } 231 232 if !cnw.Contains(te.Interface().Address().IP) { 233 t.Fatalf("endpoint got assigned address outside of container network(%s): %s", cnw.String(), te.Interface().Address()) 234 } 235 } 236 237 func TestCreateNoConfig(t *testing.T) { 238 if !testutils.IsRunningInContainer() { 239 defer testutils.SetupTestOSContext(t)() 240 } 241 d := newDriver() 242 243 netconfig := &networkConfiguration{BridgeName: DefaultBridgeName} 244 genericOption := make(map[string]interface{}) 245 genericOption[netlabel.GenericData] = netconfig 246 247 if err := d.CreateNetwork("dummy", genericOption, nil, getIPv4Data(t, ""), nil); err != nil { 248 t.Fatalf("Failed to create bridge: %v", err) 249 } 250 } 251 252 func TestCreateFullOptionsLabels(t *testing.T) { 253 if !testutils.IsRunningInContainer() { 254 defer testutils.SetupTestOSContext(t)() 255 } 256 d := newDriver() 257 258 config := &configuration{ 259 EnableIPForwarding: true, 260 } 261 genericOption := make(map[string]interface{}) 262 genericOption[netlabel.GenericData] = config 263 264 if err := d.configure(genericOption); err != nil { 265 t.Fatalf("Failed to setup driver config: %v", err) 266 } 267 268 bndIPs := "127.0.0.1" 269 nwV6s := "2001:db8:2600:2700:2800::/80" 270 gwV6s := "2001:db8:2600:2700:2800::25/80" 271 nwV6, _ := types.ParseCIDR(nwV6s) 272 gwV6, _ := types.ParseCIDR(gwV6s) 273 274 labels := map[string]string{ 275 BridgeName: DefaultBridgeName, 276 DefaultBridge: "true", 277 EnableICC: "true", 278 EnableIPMasquerade: "true", 279 DefaultBindingIP: bndIPs, 280 } 281 282 netOption := make(map[string]interface{}) 283 netOption[netlabel.EnableIPv6] = true 284 netOption[netlabel.GenericData] = labels 285 286 ipdList := getIPv4Data(t, "") 287 ipd6List := []driverapi.IPAMData{ 288 { 289 Pool: nwV6, 290 AuxAddresses: map[string]*net.IPNet{ 291 DefaultGatewayV6AuxKey: gwV6, 292 }, 293 }, 294 } 295 296 err := d.CreateNetwork("dummy", netOption, nil, ipdList, ipd6List) 297 if err != nil { 298 t.Fatalf("Failed to create bridge: %v", err) 299 } 300 301 nw, ok := d.networks["dummy"] 302 if !ok { 303 t.Fatalf("Cannot find dummy network in bridge driver") 304 } 305 306 if nw.config.BridgeName != DefaultBridgeName { 307 t.Fatalf("incongruent name in bridge network") 308 } 309 310 if !nw.config.EnableIPv6 { 311 t.Fatalf("incongruent EnableIPv6 in bridge network") 312 } 313 314 if !nw.config.EnableICC { 315 t.Fatalf("incongruent EnableICC in bridge network") 316 } 317 318 if !nw.config.EnableIPMasquerade { 319 t.Fatalf("incongruent EnableIPMasquerade in bridge network") 320 } 321 322 bndIP := net.ParseIP(bndIPs) 323 if !bndIP.Equal(nw.config.DefaultBindingIP) { 324 t.Fatalf("Unexpected: %v", nw.config.DefaultBindingIP) 325 } 326 327 if !types.CompareIPNet(nw.config.AddressIPv6, nwV6) { 328 t.Fatalf("Unexpected: %v", nw.config.AddressIPv6) 329 } 330 331 if !gwV6.IP.Equal(nw.config.DefaultGatewayIPv6) { 332 t.Fatalf("Unexpected: %v", nw.config.DefaultGatewayIPv6) 333 } 334 335 // In short here we are testing --fixed-cidr-v6 daemon option 336 // plus --mac-address run option 337 mac, _ := net.ParseMAC("aa:bb:cc:dd:ee:ff") 338 epOptions := map[string]interface{}{netlabel.MacAddress: mac} 339 te := newTestEndpoint(ipdList[0].Pool, 20) 340 err = d.CreateEndpoint("dummy", "ep1", te.Interface(), epOptions) 341 if err != nil { 342 t.Fatal(err) 343 } 344 345 if !nwV6.Contains(te.Interface().AddressIPv6().IP) { 346 t.Fatalf("endpoint got assigned address outside of container network(%s): %s", nwV6.String(), te.Interface().AddressIPv6()) 347 } 348 if te.Interface().AddressIPv6().IP.String() != "2001:db8:2600:2700:2800:aabb:ccdd:eeff" { 349 t.Fatalf("Unexpected endpoint IPv6 address: %v", te.Interface().AddressIPv6().IP) 350 } 351 } 352 353 func TestCreate(t *testing.T) { 354 if !testutils.IsRunningInContainer() { 355 defer testutils.SetupTestOSContext(t)() 356 } 357 358 d := newDriver() 359 360 if err := d.configure(nil); err != nil { 361 t.Fatalf("Failed to setup driver config: %v", err) 362 } 363 364 netconfig := &networkConfiguration{BridgeName: DefaultBridgeName} 365 genericOption := make(map[string]interface{}) 366 genericOption[netlabel.GenericData] = netconfig 367 368 if err := d.CreateNetwork("dummy", genericOption, nil, getIPv4Data(t, ""), nil); err != nil { 369 t.Fatalf("Failed to create bridge: %v", err) 370 } 371 372 err := d.CreateNetwork("dummy", genericOption, nil, getIPv4Data(t, ""), nil) 373 if err == nil { 374 t.Fatalf("Expected bridge driver to refuse creation of second network with default name") 375 } 376 if _, ok := err.(types.ForbiddenError); !ok { 377 t.Fatalf("Creation of second network with default name failed with unexpected error type") 378 } 379 } 380 381 func TestCreateFail(t *testing.T) { 382 if !testutils.IsRunningInContainer() { 383 defer testutils.SetupTestOSContext(t)() 384 } 385 386 d := newDriver() 387 388 if err := d.configure(nil); err != nil { 389 t.Fatalf("Failed to setup driver config: %v", err) 390 } 391 392 netconfig := &networkConfiguration{BridgeName: "dummy0", DefaultBridge: true} 393 genericOption := make(map[string]interface{}) 394 genericOption[netlabel.GenericData] = netconfig 395 396 if err := d.CreateNetwork("dummy", genericOption, nil, getIPv4Data(t, ""), nil); err == nil { 397 t.Fatal("Bridge creation was expected to fail") 398 } 399 } 400 401 func TestCreateMultipleNetworks(t *testing.T) { 402 if !testutils.IsRunningInContainer() { 403 defer testutils.SetupTestOSContext(t)() 404 } 405 406 d := newDriver() 407 408 config := &configuration{ 409 EnableIPTables: true, 410 } 411 genericOption := make(map[string]interface{}) 412 genericOption[netlabel.GenericData] = config 413 414 if err := d.configure(genericOption); err != nil { 415 t.Fatalf("Failed to setup driver config: %v", err) 416 } 417 418 config1 := &networkConfiguration{BridgeName: "net_test_1"} 419 genericOption = make(map[string]interface{}) 420 genericOption[netlabel.GenericData] = config1 421 if err := d.CreateNetwork("1", genericOption, nil, getIPv4Data(t, ""), nil); err != nil { 422 t.Fatalf("Failed to create bridge: %v", err) 423 } 424 425 config2 := &networkConfiguration{BridgeName: "net_test_2"} 426 genericOption[netlabel.GenericData] = config2 427 if err := d.CreateNetwork("2", genericOption, nil, getIPv4Data(t, ""), nil); err != nil { 428 t.Fatalf("Failed to create bridge: %v", err) 429 } 430 431 // Verify the network isolation rules are installed, each network subnet should appear 2 times 432 verifyV4INCEntries(d.networks, 2, t) 433 434 config3 := &networkConfiguration{BridgeName: "net_test_3"} 435 genericOption[netlabel.GenericData] = config3 436 if err := d.CreateNetwork("3", genericOption, nil, getIPv4Data(t, ""), nil); err != nil { 437 t.Fatalf("Failed to create bridge: %v", err) 438 } 439 440 // Verify the network isolation rules are installed, each network subnet should appear 4 times 441 verifyV4INCEntries(d.networks, 6, t) 442 443 config4 := &networkConfiguration{BridgeName: "net_test_4"} 444 genericOption[netlabel.GenericData] = config4 445 if err := d.CreateNetwork("4", genericOption, nil, getIPv4Data(t, ""), nil); err != nil { 446 t.Fatalf("Failed to create bridge: %v", err) 447 } 448 449 // Now 6 times 450 verifyV4INCEntries(d.networks, 12, t) 451 452 d.DeleteNetwork("1") 453 verifyV4INCEntries(d.networks, 6, t) 454 455 d.DeleteNetwork("2") 456 verifyV4INCEntries(d.networks, 2, t) 457 458 d.DeleteNetwork("3") 459 verifyV4INCEntries(d.networks, 0, t) 460 461 d.DeleteNetwork("4") 462 verifyV4INCEntries(d.networks, 0, t) 463 } 464 465 func verifyV4INCEntries(networks map[string]*bridgeNetwork, numEntries int, t *testing.T) { 466 out, err := iptables.Raw("-nvL", IsolationChain) 467 if err != nil { 468 t.Fatal(err) 469 } 470 471 found := 0 472 for _, x := range networks { 473 for _, y := range networks { 474 if x == y { 475 continue 476 } 477 re := regexp.MustCompile(fmt.Sprintf("%s %s", x.config.BridgeName, y.config.BridgeName)) 478 matches := re.FindAllString(string(out[:]), -1) 479 if len(matches) != 1 { 480 t.Fatalf("Cannot find expected inter-network isolation rules in IP Tables:\n%s", string(out[:])) 481 } 482 found++ 483 } 484 } 485 486 if found != numEntries { 487 t.Fatalf("Cannot find expected number (%d) of inter-network isolation rules in IP Tables:\n%s\nFound %d", numEntries, string(out[:]), found) 488 } 489 } 490 491 type testInterface struct { 492 mac net.HardwareAddr 493 addr *net.IPNet 494 addrv6 *net.IPNet 495 srcName string 496 dstName string 497 } 498 499 type testEndpoint struct { 500 iface *testInterface 501 gw net.IP 502 gw6 net.IP 503 hostsPath string 504 resolvConfPath string 505 routes []types.StaticRoute 506 } 507 508 func newTestEndpoint(nw *net.IPNet, ordinal byte) *testEndpoint { 509 addr := types.GetIPNetCopy(nw) 510 addr.IP[len(addr.IP)-1] = ordinal 511 return &testEndpoint{iface: &testInterface{addr: addr}} 512 } 513 514 func (te *testEndpoint) Interface() driverapi.InterfaceInfo { 515 if te.iface != nil { 516 return te.iface 517 } 518 519 return nil 520 } 521 522 func (i *testInterface) MacAddress() net.HardwareAddr { 523 return i.mac 524 } 525 526 func (i *testInterface) Address() *net.IPNet { 527 return i.addr 528 } 529 530 func (i *testInterface) AddressIPv6() *net.IPNet { 531 return i.addrv6 532 } 533 534 func (i *testInterface) SetMacAddress(mac net.HardwareAddr) error { 535 if i.mac != nil { 536 return types.ForbiddenErrorf("endpoint interface MAC address present (%s). Cannot be modified with %s.", i.mac, mac) 537 } 538 if mac == nil { 539 return types.BadRequestErrorf("tried to set nil MAC address to endpoint interface") 540 } 541 i.mac = types.GetMacCopy(mac) 542 return nil 543 } 544 545 func (i *testInterface) SetIPAddress(address *net.IPNet) error { 546 if address.IP == nil { 547 return types.BadRequestErrorf("tried to set nil IP address to endpoint interface") 548 } 549 if address.IP.To4() == nil { 550 return setAddress(&i.addrv6, address) 551 } 552 return setAddress(&i.addr, address) 553 } 554 555 func setAddress(ifaceAddr **net.IPNet, address *net.IPNet) error { 556 if *ifaceAddr != nil { 557 return types.ForbiddenErrorf("endpoint interface IP present (%s). Cannot be modified with (%s).", *ifaceAddr, address) 558 } 559 *ifaceAddr = types.GetIPNetCopy(address) 560 return nil 561 } 562 563 func (i *testInterface) SetNames(srcName string, dstName string) error { 564 i.srcName = srcName 565 i.dstName = dstName 566 return nil 567 } 568 569 func (te *testEndpoint) InterfaceName() driverapi.InterfaceNameInfo { 570 if te.iface != nil { 571 return te.iface 572 } 573 574 return nil 575 } 576 577 func (te *testEndpoint) SetGateway(gw net.IP) error { 578 te.gw = gw 579 return nil 580 } 581 582 func (te *testEndpoint) SetGatewayIPv6(gw6 net.IP) error { 583 te.gw6 = gw6 584 return nil 585 } 586 587 func (te *testEndpoint) AddStaticRoute(destination *net.IPNet, routeType int, nextHop net.IP) error { 588 te.routes = append(te.routes, types.StaticRoute{Destination: destination, RouteType: routeType, NextHop: nextHop}) 589 return nil 590 } 591 592 func (te *testEndpoint) AddTableEntry(tableName string, key string, value []byte) error { 593 return nil 594 } 595 596 func (te *testEndpoint) DisableGatewayService() {} 597 598 func TestQueryEndpointInfo(t *testing.T) { 599 testQueryEndpointInfo(t, true) 600 } 601 602 func TestQueryEndpointInfoHairpin(t *testing.T) { 603 testQueryEndpointInfo(t, false) 604 } 605 606 func testQueryEndpointInfo(t *testing.T, ulPxyEnabled bool) { 607 defer testutils.SetupTestOSContext(t)() 608 609 d := newDriver() 610 611 config := &configuration{ 612 EnableIPTables: true, 613 EnableUserlandProxy: ulPxyEnabled, 614 } 615 genericOption := make(map[string]interface{}) 616 genericOption[netlabel.GenericData] = config 617 618 if err := d.configure(genericOption); err != nil { 619 t.Fatalf("Failed to setup driver config: %v", err) 620 } 621 622 netconfig := &networkConfiguration{ 623 BridgeName: DefaultBridgeName, 624 EnableICC: false, 625 } 626 genericOption = make(map[string]interface{}) 627 genericOption[netlabel.GenericData] = netconfig 628 629 ipdList := getIPv4Data(t, "") 630 err := d.CreateNetwork("net1", genericOption, nil, ipdList, nil) 631 if err != nil { 632 t.Fatalf("Failed to create bridge: %v", err) 633 } 634 635 sbOptions := make(map[string]interface{}) 636 sbOptions[netlabel.PortMap] = getPortMapping() 637 638 te := newTestEndpoint(ipdList[0].Pool, 11) 639 err = d.CreateEndpoint("net1", "ep1", te.Interface(), nil) 640 if err != nil { 641 t.Fatalf("Failed to create an endpoint : %s", err.Error()) 642 } 643 644 err = d.Join("net1", "ep1", "sbox", te, sbOptions) 645 if err != nil { 646 t.Fatalf("Failed to join the endpoint: %v", err) 647 } 648 649 err = d.ProgramExternalConnectivity("net1", "ep1", sbOptions) 650 if err != nil { 651 t.Fatalf("Failed to program external connectivity: %v", err) 652 } 653 654 network, ok := d.networks["net1"] 655 if !ok { 656 t.Fatalf("Cannot find network %s inside driver", "net1") 657 } 658 ep, _ := network.endpoints["ep1"] 659 data, err := d.EndpointOperInfo(network.id, ep.id) 660 if err != nil { 661 t.Fatalf("Failed to ask for endpoint operational data: %v", err) 662 } 663 pmd, ok := data[netlabel.PortMap] 664 if !ok { 665 t.Fatalf("Endpoint operational data does not contain port mapping data") 666 } 667 pm, ok := pmd.([]types.PortBinding) 668 if !ok { 669 t.Fatalf("Unexpected format for port mapping in endpoint operational data") 670 } 671 if len(ep.portMapping) != len(pm) { 672 t.Fatalf("Incomplete data for port mapping in endpoint operational data") 673 } 674 for i, pb := range ep.portMapping { 675 if !pb.Equal(&pm[i]) { 676 t.Fatalf("Unexpected data for port mapping in endpoint operational data") 677 } 678 } 679 680 err = d.RevokeExternalConnectivity("net1", "ep1") 681 if err != nil { 682 t.Fatal(err) 683 } 684 685 // release host mapped ports 686 err = d.Leave("net1", "ep1") 687 if err != nil { 688 t.Fatal(err) 689 } 690 } 691 692 func getExposedPorts() []types.TransportPort { 693 return []types.TransportPort{ 694 {Proto: types.TCP, Port: uint16(5000)}, 695 {Proto: types.UDP, Port: uint16(400)}, 696 {Proto: types.TCP, Port: uint16(600)}, 697 } 698 } 699 700 func getPortMapping() []types.PortBinding { 701 return []types.PortBinding{ 702 {Proto: types.TCP, Port: uint16(230), HostPort: uint16(23000)}, 703 {Proto: types.UDP, Port: uint16(200), HostPort: uint16(22000)}, 704 {Proto: types.TCP, Port: uint16(120), HostPort: uint16(12000)}, 705 } 706 } 707 708 func TestLinkContainers(t *testing.T) { 709 if !testutils.IsRunningInContainer() { 710 defer testutils.SetupTestOSContext(t)() 711 } 712 713 d := newDriver() 714 715 config := &configuration{ 716 EnableIPTables: true, 717 } 718 genericOption := make(map[string]interface{}) 719 genericOption[netlabel.GenericData] = config 720 721 if err := d.configure(genericOption); err != nil { 722 t.Fatalf("Failed to setup driver config: %v", err) 723 } 724 725 netconfig := &networkConfiguration{ 726 BridgeName: DefaultBridgeName, 727 EnableICC: false, 728 } 729 genericOption = make(map[string]interface{}) 730 genericOption[netlabel.GenericData] = netconfig 731 732 ipdList := getIPv4Data(t, "") 733 err := d.CreateNetwork("net1", genericOption, nil, ipdList, nil) 734 if err != nil { 735 t.Fatalf("Failed to create bridge: %v", err) 736 } 737 738 te1 := newTestEndpoint(ipdList[0].Pool, 11) 739 err = d.CreateEndpoint("net1", "ep1", te1.Interface(), nil) 740 if err != nil { 741 t.Fatalf("Failed to create an endpoint : %s", err.Error()) 742 } 743 744 exposedPorts := getExposedPorts() 745 sbOptions := make(map[string]interface{}) 746 sbOptions[netlabel.ExposedPorts] = exposedPorts 747 748 err = d.Join("net1", "ep1", "sbox", te1, sbOptions) 749 if err != nil { 750 t.Fatalf("Failed to join the endpoint: %v", err) 751 } 752 753 err = d.ProgramExternalConnectivity("net1", "ep1", sbOptions) 754 if err != nil { 755 t.Fatalf("Failed to program external connectivity: %v", err) 756 } 757 758 addr1 := te1.iface.addr 759 if addr1.IP.To4() == nil { 760 t.Fatalf("No Ipv4 address assigned to the endpoint: ep1") 761 } 762 763 te2 := newTestEndpoint(ipdList[0].Pool, 22) 764 err = d.CreateEndpoint("net1", "ep2", te2.Interface(), nil) 765 if err != nil { 766 t.Fatalf("Failed to create an endpoint : %s", err.Error()) 767 } 768 769 addr2 := te2.iface.addr 770 if addr2.IP.To4() == nil { 771 t.Fatalf("No Ipv4 address assigned to the endpoint: ep2") 772 } 773 774 sbOptions = make(map[string]interface{}) 775 sbOptions[netlabel.GenericData] = options.Generic{ 776 "ChildEndpoints": []string{"ep1"}, 777 } 778 779 err = d.Join("net1", "ep2", "", te2, sbOptions) 780 if err != nil { 781 t.Fatalf("Failed to link ep1 and ep2") 782 } 783 784 err = d.ProgramExternalConnectivity("net1", "ep2", sbOptions) 785 if err != nil { 786 t.Fatalf("Failed to program external connectivity: %v", err) 787 } 788 789 out, err := iptables.Raw("-L", DockerChain) 790 for _, pm := range exposedPorts { 791 regex := fmt.Sprintf("%s dpt:%d", pm.Proto.String(), pm.Port) 792 re := regexp.MustCompile(regex) 793 matches := re.FindAllString(string(out[:]), -1) 794 if len(matches) != 1 { 795 t.Fatalf("IP Tables programming failed %s", string(out[:])) 796 } 797 798 regex = fmt.Sprintf("%s spt:%d", pm.Proto.String(), pm.Port) 799 matched, _ := regexp.MatchString(regex, string(out[:])) 800 if !matched { 801 t.Fatalf("IP Tables programming failed %s", string(out[:])) 802 } 803 } 804 805 err = d.RevokeExternalConnectivity("net1", "ep2") 806 if err != nil { 807 t.Fatalf("Failed to revoke external connectivity: %v", err) 808 } 809 810 err = d.Leave("net1", "ep2") 811 if err != nil { 812 t.Fatalf("Failed to unlink ep1 and ep2") 813 } 814 815 out, err = iptables.Raw("-L", DockerChain) 816 for _, pm := range exposedPorts { 817 regex := fmt.Sprintf("%s dpt:%d", pm.Proto.String(), pm.Port) 818 re := regexp.MustCompile(regex) 819 matches := re.FindAllString(string(out[:]), -1) 820 if len(matches) != 0 { 821 t.Fatalf("Leave should have deleted relevant IPTables rules %s", string(out[:])) 822 } 823 824 regex = fmt.Sprintf("%s spt:%d", pm.Proto.String(), pm.Port) 825 matched, _ := regexp.MatchString(regex, string(out[:])) 826 if matched { 827 t.Fatalf("Leave should have deleted relevant IPTables rules %s", string(out[:])) 828 } 829 } 830 831 // Error condition test with an invalid endpoint-id "ep4" 832 sbOptions = make(map[string]interface{}) 833 sbOptions[netlabel.GenericData] = options.Generic{ 834 "ChildEndpoints": []string{"ep1", "ep4"}, 835 } 836 837 err = d.Join("net1", "ep2", "", te2, sbOptions) 838 if err != nil { 839 t.Fatal(err) 840 } 841 err = d.ProgramExternalConnectivity("net1", "ep2", sbOptions) 842 if err != nil { 843 out, err = iptables.Raw("-L", DockerChain) 844 for _, pm := range exposedPorts { 845 regex := fmt.Sprintf("%s dpt:%d", pm.Proto.String(), pm.Port) 846 re := regexp.MustCompile(regex) 847 matches := re.FindAllString(string(out[:]), -1) 848 if len(matches) != 0 { 849 t.Fatalf("Error handling should rollback relevant IPTables rules %s", string(out[:])) 850 } 851 852 regex = fmt.Sprintf("%s spt:%d", pm.Proto.String(), pm.Port) 853 matched, _ := regexp.MatchString(regex, string(out[:])) 854 if matched { 855 t.Fatalf("Error handling should rollback relevant IPTables rules %s", string(out[:])) 856 } 857 } 858 } else { 859 t.Fatalf("Expected Join to fail given link conditions are not satisfied") 860 } 861 } 862 863 func TestValidateConfig(t *testing.T) { 864 if !testutils.IsRunningInContainer() { 865 defer testutils.SetupTestOSContext(t)() 866 } 867 868 // Test mtu 869 c := networkConfiguration{Mtu: -2} 870 err := c.Validate() 871 if err == nil { 872 t.Fatalf("Failed to detect invalid MTU number") 873 } 874 875 c.Mtu = 9000 876 err = c.Validate() 877 if err != nil { 878 t.Fatalf("unexpected validation error on MTU number") 879 } 880 881 // Bridge network 882 _, network, _ := net.ParseCIDR("172.28.0.0/16") 883 c = networkConfiguration{ 884 AddressIPv4: network, 885 } 886 887 err = c.Validate() 888 if err != nil { 889 t.Fatal(err) 890 } 891 892 // Test v4 gw 893 c.DefaultGatewayIPv4 = net.ParseIP("172.27.30.234") 894 err = c.Validate() 895 if err == nil { 896 t.Fatalf("Failed to detect invalid default gateway") 897 } 898 899 c.DefaultGatewayIPv4 = net.ParseIP("172.28.30.234") 900 err = c.Validate() 901 if err != nil { 902 t.Fatalf("Unexpected validation error on default gateway") 903 } 904 905 // Test v6 gw 906 _, v6nw, _ := net.ParseCIDR("2001:db8:ae:b004::/64") 907 c = networkConfiguration{ 908 EnableIPv6: true, 909 AddressIPv6: v6nw, 910 DefaultGatewayIPv6: net.ParseIP("2001:db8:ac:b004::bad:a55"), 911 } 912 err = c.Validate() 913 if err == nil { 914 t.Fatalf("Failed to detect invalid v6 default gateway") 915 } 916 917 c.DefaultGatewayIPv6 = net.ParseIP("2001:db8:ae:b004::bad:a55") 918 err = c.Validate() 919 if err != nil { 920 t.Fatalf("Unexpected validation error on v6 default gateway") 921 } 922 923 c.AddressIPv6 = nil 924 err = c.Validate() 925 if err == nil { 926 t.Fatalf("Failed to detect invalid v6 default gateway") 927 } 928 929 c.AddressIPv6 = nil 930 err = c.Validate() 931 if err == nil { 932 t.Fatalf("Failed to detect invalid v6 default gateway") 933 } 934 } 935 936 func TestSetDefaultGw(t *testing.T) { 937 if !testutils.IsRunningInContainer() { 938 defer testutils.SetupTestOSContext(t)() 939 } 940 941 d := newDriver() 942 943 if err := d.configure(nil); err != nil { 944 t.Fatalf("Failed to setup driver config: %v", err) 945 } 946 947 _, subnetv6, _ := net.ParseCIDR("2001:db8:ea9:9abc:b0c4::/80") 948 949 ipdList := getIPv4Data(t, "") 950 gw4 := types.GetIPCopy(ipdList[0].Pool.IP).To4() 951 gw4[3] = 254 952 gw6 := net.ParseIP("2001:db8:ea9:9abc:b0c4::254") 953 954 config := &networkConfiguration{ 955 BridgeName: DefaultBridgeName, 956 AddressIPv6: subnetv6, 957 DefaultGatewayIPv4: gw4, 958 DefaultGatewayIPv6: gw6, 959 } 960 961 genericOption := make(map[string]interface{}) 962 genericOption[netlabel.EnableIPv6] = true 963 genericOption[netlabel.GenericData] = config 964 965 err := d.CreateNetwork("dummy", genericOption, nil, ipdList, nil) 966 if err != nil { 967 t.Fatalf("Failed to create bridge: %v", err) 968 } 969 970 te := newTestEndpoint(ipdList[0].Pool, 10) 971 err = d.CreateEndpoint("dummy", "ep", te.Interface(), nil) 972 if err != nil { 973 t.Fatalf("Failed to create endpoint: %v", err) 974 } 975 976 err = d.Join("dummy", "ep", "sbox", te, nil) 977 if err != nil { 978 t.Fatalf("Failed to join endpoint: %v", err) 979 } 980 981 if !gw4.Equal(te.gw) { 982 t.Fatalf("Failed to configure default gateway. Expected %v. Found %v", gw4, te.gw) 983 } 984 985 if !gw6.Equal(te.gw6) { 986 t.Fatalf("Failed to configure default gateway. Expected %v. Found %v", gw6, te.gw6) 987 } 988 } 989 990 func TestCleanupIptableRules(t *testing.T) { 991 defer testutils.SetupTestOSContext(t)() 992 bridgeChain := []iptables.ChainInfo{ 993 {Name: DockerChain, Table: iptables.Nat}, 994 {Name: DockerChain, Table: iptables.Filter}, 995 {Name: IsolationChain, Table: iptables.Filter}, 996 } 997 if _, _, _, err := setupIPChains(&configuration{EnableIPTables: true}); err != nil { 998 t.Fatalf("Error setting up ip chains: %v", err) 999 } 1000 for _, chainInfo := range bridgeChain { 1001 if !iptables.ExistChain(chainInfo.Name, chainInfo.Table) { 1002 t.Fatalf("iptables chain %s of %s table should have been created", chainInfo.Name, chainInfo.Table) 1003 } 1004 } 1005 removeIPChains() 1006 for _, chainInfo := range bridgeChain { 1007 if iptables.ExistChain(chainInfo.Name, chainInfo.Table) { 1008 t.Fatalf("iptables chain %s of %s table should have been deleted", chainInfo.Name, chainInfo.Table) 1009 } 1010 } 1011 } 1012 1013 func TestCreateWithExistingBridge(t *testing.T) { 1014 defer testutils.SetupTestOSContext(t)() 1015 d := newDriver() 1016 1017 if err := d.configure(nil); err != nil { 1018 t.Fatalf("Failed to setup driver config: %v", err) 1019 } 1020 1021 brName := "br111" 1022 br := &netlink.Bridge{ 1023 LinkAttrs: netlink.LinkAttrs{ 1024 Name: brName, 1025 }, 1026 } 1027 if err := netlink.LinkAdd(br); err != nil { 1028 t.Fatalf("Failed to create bridge interface: %v", err) 1029 } 1030 defer netlink.LinkDel(br) 1031 if err := netlink.LinkSetUp(br); err != nil { 1032 t.Fatalf("Failed to set bridge interface up: %v", err) 1033 } 1034 1035 ip := net.IP{192, 168, 122, 1} 1036 addr := &netlink.Addr{IPNet: &net.IPNet{ 1037 IP: ip, 1038 Mask: net.IPv4Mask(255, 255, 255, 0), 1039 }} 1040 if err := netlink.AddrAdd(br, addr); err != nil { 1041 t.Fatalf("Failed to add IP address to bridge: %v", err) 1042 } 1043 1044 netconfig := &networkConfiguration{BridgeName: brName} 1045 genericOption := make(map[string]interface{}) 1046 genericOption[netlabel.GenericData] = netconfig 1047 1048 if err := d.CreateNetwork(brName, genericOption, nil, getIPv4Data(t, brName), nil); err != nil { 1049 t.Fatalf("Failed to create bridge network: %v", err) 1050 } 1051 1052 nw, err := d.getNetwork(brName) 1053 if err != nil { 1054 t.Fatalf("Failed to getNetwork(%s): %v", brName, err) 1055 } 1056 1057 addr4, _, err := nw.bridge.addresses() 1058 if err != nil { 1059 t.Fatalf("Failed to get the bridge network's address: %v", err) 1060 } 1061 1062 if !addr4.IP.Equal(ip) { 1063 t.Fatal("Creating bridge network with existing bridge interface unexpectedly modified the IP address of the bridge") 1064 } 1065 1066 if err := d.DeleteNetwork(brName); err != nil { 1067 t.Fatalf("Failed to delete network %s: %v", brName, err) 1068 } 1069 1070 if _, err := netlink.LinkByName(brName); err != nil { 1071 t.Fatalf("Deleting bridge network that using existing bridge interface unexpectedly deleted the bridge interface") 1072 } 1073 }