github.com/zhuohuang-hust/src-cbuild@v0.0.0-20230105071821-c7aab3e7c840/mergeCode/libnetwork/drivers/bridge/interface.go (about) 1 package bridge 2 3 import ( 4 "fmt" 5 "net" 6 7 "github.com/Sirupsen/logrus" 8 "github.com/vishvananda/netlink" 9 ) 10 11 const ( 12 // DefaultBridgeName is the default name for the bridge interface managed 13 // by the driver when unspecified by the caller. 14 DefaultBridgeName = "docker0" 15 ) 16 17 // Interface models the bridge network device. 18 type bridgeInterface struct { 19 Link netlink.Link 20 bridgeIPv4 *net.IPNet 21 bridgeIPv6 *net.IPNet 22 gatewayIPv4 net.IP 23 gatewayIPv6 net.IP 24 nlh *netlink.Handle 25 } 26 27 // newInterface creates a new bridge interface structure. It attempts to find 28 // an already existing device identified by the configuration BridgeName field, 29 // or the default bridge name when unspecified, but doesn't attempt to create 30 // one when missing 31 func newInterface(nlh *netlink.Handle, config *networkConfiguration) (*bridgeInterface, error) { 32 var err error 33 i := &bridgeInterface{nlh: nlh} 34 35 // Initialize the bridge name to the default if unspecified. 36 if config.BridgeName == "" { 37 config.BridgeName = DefaultBridgeName 38 } 39 40 // Attempt to find an existing bridge named with the specified name. 41 i.Link, err = nlh.LinkByName(config.BridgeName) 42 if err != nil { 43 logrus.Debugf("Did not find any interface with name %s: %v", config.BridgeName, err) 44 } else if _, ok := i.Link.(*netlink.Bridge); !ok { 45 return nil, fmt.Errorf("existing interface %s is not a bridge", i.Link.Attrs().Name) 46 } 47 return i, nil 48 } 49 50 // exists indicates if the existing bridge interface exists on the system. 51 func (i *bridgeInterface) exists() bool { 52 return i.Link != nil 53 } 54 55 // addresses returns a single IPv4 address and all IPv6 addresses for the 56 // bridge interface. 57 func (i *bridgeInterface) addresses() (netlink.Addr, []netlink.Addr, error) { 58 v4addr, err := i.nlh.AddrList(i.Link, netlink.FAMILY_V4) 59 if err != nil { 60 return netlink.Addr{}, nil, fmt.Errorf("Failed to retrieve V4 addresses: %v", err) 61 } 62 63 v6addr, err := i.nlh.AddrList(i.Link, netlink.FAMILY_V6) 64 if err != nil { 65 return netlink.Addr{}, nil, fmt.Errorf("Failed to retrieve V6 addresses: %v", err) 66 } 67 68 if len(v4addr) == 0 { 69 return netlink.Addr{}, v6addr, nil 70 } 71 return v4addr[0], v6addr, nil 72 } 73 74 func (i *bridgeInterface) programIPv6Address() error { 75 _, nlAddressList, err := i.addresses() 76 if err != nil { 77 return &IPv6AddrAddError{IP: i.bridgeIPv6, Err: fmt.Errorf("failed to retrieve address list: %v", err)} 78 } 79 nlAddr := netlink.Addr{IPNet: i.bridgeIPv6} 80 if findIPv6Address(nlAddr, nlAddressList) { 81 return nil 82 } 83 if err := i.nlh.AddrAdd(i.Link, &nlAddr); err != nil { 84 return &IPv6AddrAddError{IP: i.bridgeIPv6, Err: err} 85 } 86 return nil 87 }