Merge pull request #276 from mrjana/cnm

Generate container mac address based on IP
This commit is contained in:
Jana Radhakrishnan
2015-06-10 21:34:30 -07:00

View File

@@ -852,14 +852,6 @@ func (d *driver) CreateEndpoint(nid, eid types.UUID, epInfo driverapi.EndpointIn
}
}()
// Set the sbox's MAC. If specified, use the one configured by user, otherwise use a random one
mac := electMacAddress(epConfig)
err = netlink.LinkSetHardwareAddr(sbox, mac)
if err != nil {
return err
}
endpoint.macAddress = mac
n.Lock()
config := n.config
n.Unlock()
@@ -889,6 +881,14 @@ func (d *driver) CreateEndpoint(nid, eid types.UUID, epInfo driverapi.EndpointIn
}
ipv4Addr := &net.IPNet{IP: ip4, Mask: n.bridge.bridgeIPv4.Mask}
// Set the sbox's MAC. If specified, use the one configured by user, otherwise generate one based on IP.
mac := electMacAddress(epConfig, ip4)
err = netlink.LinkSetHardwareAddr(sbox, mac)
if err != nil {
return err
}
endpoint.macAddress = mac
// v6 address for the sandbox side pipe interface
ipv6Addr = &net.IPNet{}
if config.EnableIPv6 {
@@ -1289,9 +1289,34 @@ func parseContainerOptions(cOptions map[string]interface{}) (*containerConfigura
}
}
func electMacAddress(epConfig *endpointConfiguration) net.HardwareAddr {
// Generate a IEEE802 compliant MAC address from the given IP address.
//
// The generator is guaranteed to be consistent: the same IP will always yield the same
// MAC address. This is to avoid ARP cache issues.
func generateMacAddr(ip net.IP) net.HardwareAddr {
hw := make(net.HardwareAddr, 6)
// The first byte of the MAC address has to comply with these rules:
// 1. Unicast: Set the least-significant bit to 0.
// 2. Address is locally administered: Set the second-least-significant bit (U/L) to 1.
// 3. As "small" as possible: The veth address has to be "smaller" than the bridge address.
hw[0] = 0x02
// The first 24 bits of the MAC represent the Organizationally Unique Identifier (OUI).
// Since this address is locally administered, we can do whatever we want as long as
// it doesn't conflict with other addresses.
hw[1] = 0x42
// Insert the IP address into the last 32 bits of the MAC address.
// This is a simple way to guarantee the address will be consistent and unique.
copy(hw[2:], ip.To4())
return hw
}
func electMacAddress(epConfig *endpointConfiguration, ip net.IP) net.HardwareAddr {
if epConfig != nil && epConfig.MacAddress != nil {
return epConfig.MacAddress
}
return netutils.GenerateRandomMAC()
return generateMacAddr(ip)
}