Remember multiple addresses owned by each container, for multi-subnet use

This commit is contained in:
Bryan Boreham committed 2015-06-10 17:21:16 +01:00
1 parent 2553850ed4
commit c7a9dfbb3f
3 files changed
+39 -19

No files matched your search

+9
View File
@@ -46,6 +46,15 @@ func (cidr CIDR) String() string {
return fmt.Sprintf("%s/%d", cidr.Start.String(), cidr.PrefixLen)
}
func (cidr1 CIDR) Overlaps(cidr2 CIDR) bool {
return cidr1.Start >= cidr2.Start && cidr1.Start < cidr2.End() ||
cidr2.Start >= cidr1.Start && cidr2.Start < cidr1.End()
}
func (cidr CIDR) Contains(addr Address) bool {
return addr >= cidr.Start && addr < cidr.End()
}
// FromIP4 converts an ipv4 address to our integer address type
func FromIP4(ip4 net.IP) (r Address) {
for _, b := range ip4.To4() {
+12 -3
View File
@@ -24,9 +24,18 @@ func (g *allocate) Try(alloc *Allocator) bool {
return true
}
// If we have previously stored an address for this container, return it.
if addr, found := alloc.owned[g.ident]; found {
g.resultChan <- allocateResult{addr, nil}
// If we have previously stored an address for this container in this subnet, return it.
if addrs, found := alloc.owned[g.ident]; found {
for _, addr := range addrs {
if g.subnet.Contains(addr) {
g.resultChan <- allocateResult{addr, nil}
return true
}
}
}
if !alloc.universe.Overlaps(g.subnet) {
g.resultChan <- allocateResult{0, fmt.Errorf("Subnet %s out of bounds: %s", g.subnet, alloc.universe)}
return true
}
+18 -16
View File
@@ -45,14 +45,14 @@ type Allocator struct {
actionChan chan<- func()
ourName router.PeerName
defaultSubnet address.CIDR
universe address.CIDR // superset of all ranges
ring *ring.Ring // information on ranges owned by all peers
space space.Space // more detail on ranges owned by us
owned map[string]address.Address // who owns what address, indexed by container-ID -- fixme - needs to be multi-subnet
nicknames map[router.PeerName]string // so we can map nicknames for rmpeer
pendingAllocates []operation // held until we get some free space
pendingClaims []operation // held until we know who owns the space
gossip router.Gossip // our link to the outside world for sending messages
universe address.CIDR // superset of all ranges
ring *ring.Ring // information on ranges owned by all peers
space space.Space // more detail on ranges owned by us
owned map[string][]address.Address // who owns what address, indexed by container-ID
nicknames map[router.PeerName]string // so we can map nicknames for rmpeer
pendingAllocates []operation // held until we get some free space
pendingClaims []operation // held until we know who owns the space
gossip router.Gossip // our link to the outside world for sending messages
paxos *paxos.Node
paxosTicker *time.Ticker
shuttingDown bool // to avoid doing any requests while trying to shut down
@@ -65,7 +65,7 @@ func NewAllocator(ourName router.PeerName, ourUID router.PeerUID, ourNickname st
ourName: ourName,
universe: universe,
ring: ring.New(universe.Start, address.Add(universe.Start, universe.Size()), ourName),
owned: make(map[string]address.Address),
owned: make(map[string][]address.Address),
paxos: paxos.NewNode(ourName, ourUID, quorum),
nicknames: map[router.PeerName]string{ourName: ourNickname},
now: time.Now,
@@ -205,7 +205,7 @@ func (alloc *Allocator) Lookup(ident string) (address.Address, error) {
alloc.actionChan <- func() {
addr, found := alloc.owned[ident]
if found {
resultChan <- allocateResult{addr: addr}
resultChan <- allocateResult{addr: addr[0]}
return
}
resultChan <- allocateResult{err: fmt.Errorf("lookup: no address found")}
@@ -237,8 +237,8 @@ func (alloc *Allocator) ContainerDied(ident string) error {
func (alloc *Allocator) free(ident string) error {
errChan := make(chan error)
alloc.actionChan <- func() {
addr, found := alloc.owned[ident]
if found {
addrs, found := alloc.owned[ident]
for _, addr := range addrs {
alloc.space.Free(addr)
}
delete(alloc.owned, ident)
@@ -669,13 +669,15 @@ func (alloc *Allocator) reportFreeSpace() {
// Owned addresses
func (alloc *Allocator) addOwned(ident string, addr address.Address) {
alloc.owned[ident] = addr
alloc.owned[ident] = append(alloc.owned[ident], addr)
}
func (alloc *Allocator) findOwner(addr address.Address) string {
for ident, candidate := range alloc.owned {
if candidate == addr {
return ident
for ident, addrs := range alloc.owned {
for _, candidate := range addrs {
if candidate == addr {
return ident
}
}
}
return ""