in freelist.go [125:170]
func (f *freelist) AllocContinuousRegion(order *allocOrder, n uint) region {
if f.avail < n || (f.avail == n && len(f.regions) > 1) {
return region{}
}
if n > math.MaxUint32 { // continuous regions max out at 4GB
return region{}
}
bestFit := -1
bestSz := uint(math.MaxUint32)
for i, end, next := order.iter(len(f.regions)); i != end; i = next(i) {
count := uint(f.regions[i].count)
if n <= count && count < bestSz {
bestFit = i
bestSz = count
if bestSz == n {
break
}
}
}
if bestFit < 0 {
// no continuous region found
return region{}
}
// allocate best fitting region from list
i := bestFit
selected := f.regions[i]
allocated, rest := order.allocFromRegion(selected, uint32(n))
invariant.Check(allocated.count == uint32(n), "allocation mismatch")
invariant.Check(allocated.count+rest.count == selected.count, "region split page count mismatch")
if rest.count == 0 {
// remove entry
copy(f.regions[i:], f.regions[i+1:])
f.regions = f.regions[:len(f.regions)-1]
} else {
f.regions[i] = rest
}
f.avail -= uint(allocated.count)
return allocated
}