Safe Haskell  SafeInfered 

Implementation of clusterwide logic.
This module holds all pure clusterlogic; I/O related functionality goes into the Main module for the individual binaries.
 data AllocSolution = AllocSolution {
 asFailures :: [FailMode]
 asAllocs :: Int
 asSolution :: Maybe AllocElement
 asLog :: [String]
 data EvacSolution = EvacSolution {}
 type AllocResult = (FailStats, List, List, [Instance], [CStats])
 type AllocSolutionList = [(Instance, AllocSolution)]
 type AllocNodes = Either [Ndx] [(Ndx, [Ndx])]
 emptyAllocSolution :: AllocSolution
 emptyEvacSolution :: EvacSolution
 data Table = Table List List Score [Placement]
 data CStats = CStats {
 csFmem :: Integer
 csFdsk :: Integer
 csFspn :: Integer
 csAmem :: Integer
 csAdsk :: Integer
 csAcpu :: Integer
 csMmem :: Integer
 csMdsk :: Integer
 csMcpu :: Integer
 csImem :: Integer
 csIdsk :: Integer
 csIspn :: Integer
 csIcpu :: Integer
 csTmem :: Double
 csTdsk :: Double
 csTspn :: Double
 csTcpu :: Double
 csVcpu :: Integer
 csNcpu :: Double
 csXmem :: Integer
 csNmem :: Integer
 csScore :: Score
 csNinst :: Int
 type AllocMethod = List > List > Maybe Int > Instance > AllocNodes > [Instance] > [CStats] > Result AllocResult
 type EvacInnerState = Either String (List, Instance, Score, Ndx)
 verifyN1 :: [Node] > [Node]
 computeBadItems :: List > List > ([Node], [Instance])
 instanceNodes :: List > Instance > (Ndx, Ndx, Node, Node)
 emptyCStats :: CStats
 updateCStats :: CStats > Node > CStats
 totalResources :: List > CStats
 computeAllocationDelta :: CStats > CStats > AllocStats
 detailedCVInfoExt :: [((Double, String), ([Double] > Statistics, Bool))]
 detailedCVInfo :: [(Double, String)]
 detailedCVWeights :: [Double]
 detailedCVAggregation :: [([Double] > Statistics, Bool)]
 detailedCVOnlineStatus :: [Bool]
 compDetailedCVNode :: Node > [Double]
 compClusterStatistics :: [Node] > [Statistics]
 updateClusterStatistics :: [Statistics] > (Node, Node) > [Statistics]
 updateClusterStatisticsTwice :: [Statistics] > (Node, Node) > (Node, Node) > [Statistics]
 compDetailedCV :: [Node] > [Double]
 compCVfromStats :: [Statistics] > Double
 compCVNodes :: [Node] > Double
 compCV :: List > Double
 getOnline :: List > [Node]
 compareTables :: Table > Table > Table
 applyMove :: List > Instance > IMove > OpResult (List, Instance, Ndx, Ndx)
 allocateOnSingle :: List > Instance > Ndx > OpResult AllocElement
 allocateOnPair :: [Statistics] > List > Instance > Ndx > Ndx > OpResult AllocElement
 checkSingleStep :: Table > Instance > Table > IMove > Table
 possibleMoves :: MirrorType > Bool > Bool > Bool > (Bool, Bool) > Ndx > [IMove]
 checkInstanceMove :: [Ndx] > Bool > Bool > Bool > Table > Instance > Table
 checkMove :: [Ndx] > Bool > Bool > Bool > Table > [Instance] > Table
 doNextBalance :: Table > Int > Score > Bool
 tryBalance :: Table > Bool > Bool > Bool > Bool > Score > Score > Maybe Table
 collapseFailures :: [FailMode] > FailStats
 bestAllocElement :: Maybe AllocElement > Maybe AllocElement > Maybe AllocElement
 concatAllocs :: AllocSolution > OpResult AllocElement > AllocSolution
 sumAllocs :: AllocSolution > AllocSolution > AllocSolution
 describeSolution :: AllocSolution > String
 annotateSolution :: AllocSolution > AllocSolution
 reverseEvacSolution :: EvacSolution > EvacSolution
 genAllocNodes :: List > List > Int > Bool > Result AllocNodes
 tryAlloc :: Monad m => List > List > Instance > AllocNodes > m AllocSolution
 solutionDescription :: (Group, Result AllocSolution) > [String]
 filterMGResults :: [(Group, Result AllocSolution)] > [(Group, AllocSolution)]
 sortMGResults :: [(Group, AllocSolution)] > [(Group, AllocSolution)]
 filterValidGroups :: [(Group, (List, List))] > Instance > ([(Group, (List, List))], [String])
 findBestAllocGroup :: List > List > List > Maybe [Gdx] > Instance > Int > Result (Group, AllocSolution, [String])
 tryMGAlloc :: List > List > List > Instance > Int > Result AllocSolution
 updateIl :: List > Maybe AllocElement > List
 extractNl :: List > Maybe AllocElement > List
 allocList :: List > List > List > [(Instance, Int)] > AllocSolutionList > Result (List, List, AllocSolutionList)
 failOnSecondaryChange :: Monad m => EvacMode > DiskTemplate > m ()
 nodeEvacInstance :: List > List > EvacMode > Instance > Gdx > [Ndx] > Result (List, List, [OpCode])
 evacOneNodeOnly :: List > List > Instance > Gdx > [Ndx] > Result (List, List, [OpCode])
 evacOneNodeInner :: List > Instance > Gdx > (Ndx > IMove) > EvacInnerState > Ndx > EvacInnerState
 evacDrbdAllInner :: List > List > Instance > Gdx > (Ndx, Ndx) > Result (List, List, [OpCode], Score)
 availableGroupNodes :: [(Gdx, [Ndx])] > IntSet > Gdx > Result [Ndx]
 updateEvacSolution :: (List, List, EvacSolution) > Idx > Result (List, List, [OpCode]) > (List, List, EvacSolution)
 tryNodeEvac :: List > List > List > EvacMode > [Idx] > Result (List, List, EvacSolution)
 tryChangeGroup :: List > List > List > [Gdx] > [Idx] > Result (List, List, EvacSolution)
 iterateAlloc :: AllocMethod
 sufficesShrinking :: (Instance > AllocSolution) > Instance > FailMode > Maybe Instance
 tieredAlloc :: AllocMethod
 computeMoves :: Instance > String > IMove > String > String > (String, [String])
 printSolutionLine :: List > List > Int > Int > Placement > Int > (String, [String])
 involvedNodes :: List > Placement > [Ndx]
 getMoves :: (Table, Table) > [MoveJob]
 mergeJobs :: ([JobSet], [Ndx]) > MoveJob > ([JobSet], [Ndx])
 splitJobs :: [MoveJob] > [JobSet]
 formatJob :: Int > Int > (Int, MoveJob) > [String]
 formatCmds :: [JobSet] > String
 printNodes :: List > [String] > String
 printInsts :: List > List > String
 printStats :: String > List > String
 iMoveToJob :: List > List > Idx > IMove > [OpCode]
 instanceGroup :: List > Instance > Result Gdx
 instancePriGroup :: List > Instance > Gdx
 findSplitInstances :: List > List > [Instance]
 splitCluster :: List > List > [(Gdx, (List, List))]
 nodesToEvacuate :: List > EvacMode > [Idx] > IntSet
Types
data AllocSolution Source
Allocation/relocation solution.
AllocSolution  

data EvacSolution Source
Node evacuation/group change iallocator result type. This result type consists of actual opcodes (a restricted subset) that are transmitted back to Ganeti.
Show EvacSolution 
type AllocResult = (FailStats, List, List, [Instance], [CStats])Source
Allocation results, as used in iterateAlloc
and tieredAlloc
.
type AllocSolutionList = [(Instance, AllocSolution)]Source
Type alias for easier handling.
type AllocNodes = Either [Ndx] [(Ndx, [Ndx])]Source
A type denoting the valid allocation mode/pairs.
For a onenode allocation, this will be a Left [
, whereas
for a twonode allocation, this will be a Ndx
]Right [(
. In the latter case, the list is basically an
association list, grouped by primary node and holding the potential
secondary nodes in the sublist.
Ndx
,
[Ndx
])]
The complete state for the balancing solution.
Show Table 
Cluster statistics data type.
CStats  

Show CStats 
type AllocMethodSource
= List  Node list 
> List  Instance list 
> Maybe Int  Optional allocation limit 
> Instance  Instance spec for allocation 
> AllocNodes  Which nodes we should allocate on 
> [Instance]  Allocated instances 
> [CStats]  Running cluster stats 
> Result AllocResult  Allocation result 
A simple type for allocation functions.
Utility functions
computeBadItems :: List > List > ([Node], [Instance])Source
Computes the pair of bad nodes and instances.
The bad node list is computed via a simple verifyN1
check, and the
bad instance list is the list of primary and secondary instances of
those nodes.
updateCStats :: CStats > Node > CStatsSource
totalResources :: List > CStatsSource
Compute the total free disk and memory in the cluster.
computeAllocationDelta :: CStats > CStats > AllocStatsSource
Compute the delta between two cluster state.
This is used when doing allocations, to understand better the available cluster resources. The return value is a triple of the current used values, the delta that was still allocated, and what was left unallocated.
detailedCVInfoExt :: [((Double, String), ([Double] > Statistics, Bool))]Source
detailedCVInfo :: [(Double, String)]Source
detailedCVWeights :: [Double]Source
detailedCVAggregation :: [([Double] > Statistics, Bool)]Source
detailedCVOnlineStatus :: [Bool]Source
compDetailedCVNode :: Node > [Double]Source
compClusterStatistics :: [Node] > [Statistics]Source
updateClusterStatistics :: [Statistics] > (Node, Node) > [Statistics]Source
updateClusterStatisticsTwice :: [Statistics] > (Node, Node) > (Node, Node) > [Statistics]Source
compDetailedCV :: [Node] > [Double]Source
Compute cluster statistics
compCVfromStats :: [Statistics] > DoubleSource
compCVNodes :: [Node] > DoubleSource
Compute the total variance.
compCV :: List > DoubleSource
Wrapper over compCVNodes
for callers that have a List
.
Balancing functions
compareTables :: Table > Table > TableSource
allocateOnSingle :: List > Instance > Ndx > OpResult AllocElementSource
allocateOnPair :: [Statistics] > List > Instance > Ndx > Ndx > OpResult AllocElementSource
possibleMoves :: MirrorType > Bool > Bool > Bool > (Bool, Bool) > Ndx > [IMove]Source
:: [Ndx]  Allowed target node indices 
> Bool  Whether disk moves are allowed 
> Bool  Whether instance moves are allowed 
> Bool  Whether migration is restricted 
> Table  The current solution 
> [Instance]  List of instances still to move 
> Table  The new solution 
Compute the best next move.
:: Table  The starting table 
> Int  Remaining length 
> Score  Score at which to stop 
> Bool  The resulting table and commands 
Check if we are allowed to go deeper in the balancing.
:: Table  The starting table 
> Bool  Allow disk moves 
> Bool  Allow instance moves 
> Bool  Only evacuate moves 
> Bool  Restrict migration 
> Score  Min gain threshold 
> Score  Min gain 
> Maybe Table  The resulting table and commands 
Run a balance move.
Allocation functions
collapseFailures :: [FailMode] > FailStatsSource
Build failure stats out of a list of failures.
bestAllocElement :: Maybe AllocElement > Maybe AllocElement > Maybe AllocElementSource
describeSolution :: AllocSolution > StringSource
:: List  Group list 
> List  The node map 
> Int  The number of nodes required 
> Bool  Whether to drop or not unallocable nodes 
> Result AllocNodes  The (monadic) result 
Generate the valid node allocation singles or pairs for a new instance.
:: Monad m  
=> List  The node list 
> List  The instance list 
> Instance  The instance to allocate 
> AllocNodes  The allocation targets 
> m AllocSolution  Possible solution list 
Try to allocate an instance on the cluster.
solutionDescription :: (Group, Result AllocSolution) > [String]Source
filterMGResults :: [(Group, Result AllocSolution)] > [(Group, AllocSolution)]Source
sortMGResults :: [(Group, AllocSolution)] > [(Group, AllocSolution)]Source
filterValidGroups :: [(Group, (List, List))] > Instance > ([(Group, (List, List))], [String])Source
findBestAllocGroup :: List > List > List > Maybe [Gdx] > Instance > Int > Result (Group, AllocSolution, [String])Source
:: List  The group list 
> List  The node list 
> List  The instance list 
> Instance  The instance to allocate 
> Int  Required number of nodes 
> Result AllocSolution  Possible solution list 
Try to allocate an instance on a multigroup cluster.
updateIl :: List > Maybe AllocElement > ListSource
extractNl :: List > Maybe AllocElement > ListSource
:: List  The group list 
> List  The node list 
> List  The instance list 
> [(Instance, Int)]  The instance to allocate 
> AllocSolutionList  Possible solution list 
> Result (List, List, AllocSolutionList)  The final solution list 
Try to allocate a list of instances on a multigroup cluster.
failOnSecondaryChange :: Monad m => EvacMode > DiskTemplate > m ()Source
nodeEvacInstance :: List > List > EvacMode > Instance > Gdx > [Ndx] > Result (List, List, [OpCode])Source
evacOneNodeInner :: List > Instance > Gdx > (Ndx > IMove) > EvacInnerState > Ndx > EvacInnerStateSource
evacDrbdAllInner :: List > List > Instance > Gdx > (Ndx, Ndx) > Result (List, List, [OpCode], Score)Source
updateEvacSolution :: (List, List, EvacSolution) > Idx > Result (List, List, [OpCode]) > (List, List, EvacSolution)Source
:: List  The cluster groups 
> List  The node list (clusterwide, not per group) 
> List  Instance list (clusterwide) 
> EvacMode  The evacuation mode 
> [Idx]  List of instance (indices) to be evacuated 
> Result (List, List, EvacSolution) 
Nodeevacuation IAllocator mode main function.
:: List  The cluster groups 
> List  The node list (clusterwide) 
> List  Instance list (clusterwide) 
> [Gdx]  Target groups; if empty, any groups not being evacuated 
> [Idx]  List of instance (indices) to be evacuated 
> Result (List, List, EvacSolution) 
Changegroup IAllocator mode main function.
This is very similar to tryNodeEvac
, the only difference is that
we don't choose as target group the current instance group, but
instead:
 at the start of the function, we compute which are the target groups; either no groups were passed in, in which case we choose all groups out of which we don't evacuate instance, or there were some groups passed, in which case we use those
 for each instance, we use
findBestAllocGroup
to choose the best group to hold the instance, and then we do whattryNodeEvac
does, except for this group instead of the current instance group.
Note that the correct behaviour of this function relies on the
function nodeEvacInstance
to be able to do correctly both
intragroup and intergroup moves when passed the ChangeAll
mode.
iterateAlloc :: AllocMethodSource
Standardsized allocation method.
This places instances of the same size on the cluster until we're out of space. The result will be a list of identicallysized instances.
sufficesShrinking :: (Instance > AllocSolution) > Instance > FailMode > Maybe InstanceSource
tieredAlloc :: AllocMethodSource
Tiered allocation method.
This places instances on the cluster, and decreases the spec until we can allocate again. The result will be a list of decreasing instance specs.
Formatting functions
computeMoves :: Instance > String > IMove > String > String > (String, [String])Source
:: List  The node list 
> List  The instance list 
> Int  Maximum node name length 
> Int  Maximum instance name length 
> Placement  The current placement 
> Int  The index of the placement in the solution 
> (String, [String]) 
Converts a placement to string format.
:: List  Instance list, used for retrieving the instance from its index; note that this must be the original instance list, so that we can retrieve the old nodes 
> Placement  The placement we're investigating, containing the new nodes and instance index 
> [Ndx]  Resulting list of node indices 
Return the instance and involved nodes in an instance move.
Note that the output list length can vary, and is not required nor guaranteed to be of any specific length.
getMoves :: (Table, Table) > [MoveJob]Source
From two adjacent cluster tables get the list of moves that transitions from to the other
splitJobs :: [MoveJob] > [JobSet]Source
Break a list of moves into independent groups. Note that this will reverse the order of jobs.
formatCmds :: [JobSet] > StringSource
Given a list of commands, prefix them with gntinstance
and
also beautify the display a little.
printNodes :: List > [String] > StringSource
Print the node list.
printInsts :: List > List > StringSource
Print the instance list.
printStats :: String > List > StringSource
Shows statistics for a given node list.
:: List  The node list; only used for node names, so any version is good (before or after the operation) 
> List  The instance list; also used for names only 
> Idx  The index of the instance being moved 
> IMove  The actual move to be described 
> [OpCode]  The list of opcodes equivalent to the given move 
Convert a placement into a list of OpCodes (basically a job).
Node group functions
instancePriGroup :: List > Instance > GdxSource
findSplitInstances :: List > List > [Instance]Source
Compute the list of badly allocated instances (split across node groups).
splitCluster :: List > List > [(Gdx, (List, List))]Source
Splits a cluster into the component node groups.
nodesToEvacuate :: List > EvacMode > [Idx] > IntSetSource