Class: OsCtld::UGidRegistry

Inherits:
Object
  • Object
show all
Includes:
Lockable, Singleton
Defined in:
lib/osctld/ugid_registry.rb

Overview

Registry for user/group IDs allocated to dynamic users

Constant Summary collapse

ID_POOL =
(100_000..199_999)

Class Method Summary collapse

Instance Method Summary collapse

Methods included from Lockable

#exclusively, included, #inclusively, #init_lock, #lock, #unlock

Constructor Details

#initializeUGidRegistry

Returns a new instance of UGidRegistry.



22
23
24
25
26
# File 'lib/osctld/ugid_registry.rb', line 22

def initialize
  init_lock
  @allocated = []
  @free = ID_POOL.to_a
end

Class Method Details

.setupObject



13
14
15
# File 'lib/osctld/ugid_registry.rb', line 13

def setup
  instance
end

Instance Method Details

#<<(ugid) ⇒ UGidRegistry

Parameters:

  • ugid (Integer)

Returns:



36
37
38
39
40
41
42
43
44
45
46
47
# File 'lib/osctld/ugid_registry.rb', line 36

def <<(ugid)
  return self unless in_range?(ugid)

  exclusively do
    next if taken?(ugid)

    @free.delete(ugid)
    insert_sort(@allocated, ugid)
  end

  self
end

#exportObject



79
80
81
82
83
84
85
86
# File 'lib/osctld/ugid_registry.rb', line 79

def export
  inclusively do
    {
      allocated: @allocated.clone,
      free: @free.clone
    }
  end
end

#getInteger

Returns allocated user/group ID.

Returns:

  • (Integer)

    allocated user/group ID



75
76
77
# File 'lib/osctld/ugid_registry.rb', line 75

def get
  exclusively { @free.shift }
end

#in_range?(ugid) ⇒ Boolean

Parameters:

  • ugid (Integer)

Returns:

  • (Boolean)


30
31
32
# File 'lib/osctld/ugid_registry.rb', line 30

def in_range?(ugid)
  ugid >= ID_POOL.begin && ugid <= ID_POOL.end
end

#insert_sort(arr, i) ⇒ Object (protected)



90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
# File 'lib/osctld/ugid_registry.rb', line 90

def insert_sort(arr, i)
  index = arr.bsearch_index { |v| v >= i }

  if index.nil?
    arr << i

  elsif arr[index] > i
    arr.insert(index, i)

  else
    raise ArgumentError, "array already includes #{i}"
  end

  arr
end

#remove(ugid) ⇒ Integer?

Parameters:

  • ugid (Integer)

Returns:

  • (Integer, nil)


51
52
53
54
55
56
57
58
59
60
61
62
63
64
# File 'lib/osctld/ugid_registry.rb', line 51

def remove(ugid)
  return unless in_range?(ugid)

  exclusively do
    unless taken?(ugid)
      raise ArgumentError, "ugid #{ugid} is not registered"
    end

    @allocated.delete(ugid)
    insert_sort(@free, ugid)
  end

  ugid
end

#taken?(ugid) ⇒ Boolean

Parameters:

  • ugid (Integer)

Returns:

  • (Boolean)


68
69
70
71
72
# File 'lib/osctld/ugid_registry.rb', line 68

def taken?(ugid)
  inclusively do
    @allocated.bsearch { |v| v >= ugid } == ugid
  end
end