@@ -3,6 +3,7 @@ package ipam
33import  (
44	"fmt" 
55	"net" 
6+ 	"sync" 
67
78	"github.com/bits-and-blooms/bitset" 
89	"github.com/cybozu-go/netutil" 
@@ -13,12 +14,15 @@ type allocator struct {
1314	ipv6          * net.IPNet 
1415	usage         * bitset.BitSet 
1516	lastAllocIdx  int64 
17+ 	mu            sync.Mutex 
1618}
1719
1820func  newAllocator (ipv4 , ipv6  * string ) * allocator  {
1921	a  :=  & allocator {
2022		lastAllocIdx : - 1 ,
2123	}
24+ 	a .mu .Lock ()
25+ 	defer  a .mu .Unlock ()
2226	if  ipv4  !=  nil  {
2327		ip , n , _  :=  net .ParseCIDR (* ipv4 )
2428		if  ip .To4 () ==  nil  {
@@ -40,21 +44,29 @@ func newAllocator(ipv4, ipv6 *string) *allocator {
4044}
4145
4246func  (a  * allocator ) isFull () bool  {
47+ 	a .mu .Lock ()
48+ 	defer  a .mu .Unlock ()
4349	return  a .usage .All ()
4450}
4551
4652func  (a  * allocator ) isEmpty () bool  {
53+ 	a .mu .Lock ()
54+ 	defer  a .mu .Unlock ()
4755	return  a .usage .None ()
4856}
4957
5058func  (a  * allocator ) fill () {
59+ 	a .mu .Lock ()
60+ 	defer  a .mu .Unlock ()
5161	for  i  :=  uint (0 ); i  <  a .usage .Len (); i ++  {
5262		a .usage .Set (i )
5363	}
5464	a .lastAllocIdx  =  int64 (a .usage .Len () -  1 )
5565}
5666
5767func  (a  * allocator ) register (ipv4 , ipv6  net.IP ) (uint , bool ) {
68+ 	a .mu .Lock ()
69+ 	defer  a .mu .Unlock ()
5870	if  a .ipv4  !=  nil  &&  a .ipv4 .Contains (ipv4 ) {
5971		offset  :=  netutil .IPDiff (a .ipv4 .IP , ipv4 )
6072		if  offset  <  0  {
@@ -77,6 +89,8 @@ func (a *allocator) register(ipv4, ipv6 net.IP) (uint, bool) {
7789}
7890
7991func  (a  * allocator ) allocate () (ipv4 , ipv6  net.IP , idx  uint , ok  bool ) {
92+ 	a .mu .Lock ()
93+ 	defer  a .mu .Unlock ()
8094	// try to get an usable index from the last allocated index 
8195	idx , ok  =  a .usage .NextClear (uint (a .lastAllocIdx  +  1 ))
8296	if  ! ok  {
@@ -98,5 +112,7 @@ func (a *allocator) allocate() (ipv4, ipv6 net.IP, idx uint, ok bool) {
98112}
99113
100114func  (a  * allocator ) free (idx  uint ) {
115+ 	a .mu .Lock ()
116+ 	defer  a .mu .Unlock ()
101117	a .usage .Clear (idx )
102118}
0 commit comments