{-| Module describing an instance.

The instance data type holds very few fields, the algorithm
intelligence is in the "Node" and "Cluster" modules.

-}

{-

Copyright (C) 2009, 2010, 2011, 2012, 2013 Google Inc.
All rights reserved.

Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:

1. Redistributions of source code must retain the above copyright notice,
this list of conditions and the following disclaimer.

2. Redistributions in binary form must reproduce the above copyright
notice, this list of conditions and the following disclaimer in the
documentation and/or other materials provided with the distribution.

THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

-}

module Ganeti.HTools.Instance
  ( Instance(..)
  , Disk(..)
  , AssocList
  , List
  , create
  , isRunning
  , isOffline
  , notOffline
  , instanceDown
  , usesSecMem
  , applyIfOnline
  , setIdx
  , setName
  , setAlias
  , setPri
  , setSec
  , setBoth
  , setMovable
  , specOf
  , getTotalSpindles
  , instBelowISpec
  , instAboveISpec
  , instMatchesPolicy
  , shrinkByType
  , localStorageTemplates
  , hasSecondary
  , requiredNodes
  , allNodes
  , usesLocalStorage
  , mirrorType
  , usesMemory
  ) where

import Control.Monad (liftM2)
import qualified Data.Set as Set

import Ganeti.BasicTypes
import qualified Ganeti.HTools.Types as T
import qualified Ganeti.HTools.Container as Container
import Ganeti.HTools.Nic (Nic)

import Ganeti.Utils

-- * Type declarations
data Disk = Disk
  { dskSize     :: Int       -- ^ Size in bytes
  , dskSpindles :: Maybe Int -- ^ Number of spindles
  } deriving (Show, Eq)

-- | The instance type.
data Instance = Instance
  { name         :: String    -- ^ The instance name
  , alias        :: String    -- ^ The shortened name
  , mem          :: Int       -- ^ Memory of the instance
  , dsk          :: Int       -- ^ Total disk usage of the instance
  , disks        :: [Disk]    -- ^ Sizes of the individual disks
  , vcpus        :: Int       -- ^ Number of VCPUs
  , runSt        :: T.InstanceStatus -- ^ Original run status
  , pNode        :: T.Ndx     -- ^ Original primary node
  , sNode        :: T.Ndx     -- ^ Original secondary node
  , idx          :: T.Idx     -- ^ Internal index
  , util         :: T.DynUtil -- ^ Dynamic resource usage
  , movable      :: Bool      -- ^ Can and should the instance be moved?
  , autoBalance  :: Bool      -- ^ Is the instance auto-balanced?
  , diskTemplate :: T.DiskTemplate -- ^ The disk template of the instance
  , spindleUse   :: Int       -- ^ The numbers of used spindles
  , allTags      :: [String]  -- ^ List of all instance tags
  , exclTags     :: [String]  -- ^ List of instance exclusion tags
  , dsrdLocTags  :: Set.Set String -- ^ Instance desired location tags
  , locationScore :: Int      -- ^ The number of common-failures between
                              -- primary and secondary node of the instance
  , arPolicy     :: T.AutoRepairPolicy -- ^ Instance's auto-repair policy
  , nics         :: [Nic]     -- ^ NICs of the instance
  , forthcoming  :: Bool      -- ^ Is the instance is forthcoming?
  } deriving (Show, Eq)

instance T.Element Instance where
  nameOf   = name
  idxOf    = idx
  setAlias = setAlias
  setIdx   = setIdx
  allNames n = [name n, alias n]

-- | Check if instance is running.
isRunning :: Instance -> Bool
isRunning (Instance {runSt = T.Running}) = True
isRunning (Instance {runSt = T.ErrorUp}) = True
isRunning _                              = False

-- | Check if instance is offline.
isOffline :: Instance -> Bool
isOffline (Instance {runSt = T.StatusOffline}) = True
isOffline _                                    = False


-- | Helper to check if the instance is not offline.
notOffline :: Instance -> Bool
notOffline = not . isOffline

-- | Check if instance is down.
instanceDown :: Instance -> Bool
instanceDown inst | isRunning inst = False
instanceDown inst | isOffline inst = False
instanceDown _                     = True

-- | Apply the function if the instance is online. Otherwise use
-- the initial value
applyIfOnline :: Instance -> (a -> a) -> a -> a
applyIfOnline = applyIf . notOffline

-- | Helper for determining whether an instance's memory needs to be
-- taken into account for secondary memory reservation.
usesSecMem :: Instance -> Bool
usesSecMem inst = notOffline inst && autoBalance inst

-- | Constant holding the local storage templates.
--
-- /Note:/ Currently Ganeti only exports node total/free disk space
-- for LVM-based storage; file-based storage is ignored in this model,
-- so even though file-based storage uses in reality disk space on the
-- node, in our model it won't affect it and we can't compute whether
-- there is enough disk space for a file-based instance. Therefore we
-- will treat this template as \'foreign\' storage.
localStorageTemplates :: [T.DiskTemplate]
localStorageTemplates = [ T.DTDrbd8, T.DTPlain ]

-- | Constant holding the movable disk templates.
--
-- This only determines the initial 'movable' state of the
-- instance. Further the movable state can be restricted more due to
-- user choices, etc.
movableDiskTemplates :: [T.DiskTemplate]
movableDiskTemplates =
  [ T.DTDrbd8
  , T.DTBlock
  , T.DTSharedFile
  , T.DTGluster
  , T.DTRbd
  , T.DTExt
  ]

-- | A simple name for the int, instance association list.
type AssocList = [(T.Idx, Instance)]

-- | A simple name for an instance map.
type List = Container.Container Instance

-- * Initialization

-- | Create an instance.
--
-- Some parameters are not initialized by function, and must be set
-- later (via 'setIdx' for example).
create :: String -> Int -> Int -> [Disk] -> Int -> T.InstanceStatus
       -> [String] -> Bool -> T.Ndx -> T.Ndx -> T.DiskTemplate -> Int
       -> [Nic] -> Bool -> Instance
create name_init mem_init dsk_init disks_init vcpus_init run_init tags_init
       auto_balance_init pn sn dt su nics_init forthcoming_init =
  Instance { name = name_init
           , alias = name_init
           , mem = mem_init
           , dsk = dsk_init
           , disks = disks_init
           , vcpus = vcpus_init
           , runSt = run_init
           , pNode = pn
           , sNode = sn
           , idx = -1
           , util = T.baseUtil
           , movable = supportsMoves dt
           , autoBalance = auto_balance_init
           , diskTemplate = dt
           , spindleUse = su
           , allTags = tags_init
           , exclTags = []
           , dsrdLocTags = Set.empty
           , locationScore = 0
           , arPolicy = T.ArNotEnabled
           , nics = nics_init
           , forthcoming = forthcoming_init
           }

-- | Changes the index.
--
-- This is used only during the building of the data structures.
setIdx :: Instance -- ^ The original instance
       -> T.Idx    -- ^ New index
       -> Instance -- ^ The modified instance
setIdx t i = t { idx = i }

-- | Changes the name.
--
-- This is used only during the building of the data structures.
setName :: Instance -- ^ The original instance
        -> String   -- ^ New name
        -> Instance -- ^ The modified instance
setName t s = t { name = s, alias = s }

-- | Changes the alias.
--
-- This is used only during the building of the data structures.
setAlias :: Instance -- ^ The original instance
         -> String   -- ^ New alias
         -> Instance -- ^ The modified instance
setAlias t s = t { alias = s }

-- * Update functions

-- | Changes the primary node of the instance.
setPri :: Instance  -- ^ the original instance
        -> T.Ndx    -- ^ the new primary node
        -> Instance -- ^ the modified instance
setPri t p = t { pNode = p }

-- | Changes the secondary node of the instance.
setSec :: Instance  -- ^ the original instance
        -> T.Ndx    -- ^ the new secondary node
        -> Instance -- ^ the modified instance
setSec t s = t { sNode = s }

-- | Changes both nodes of the instance.
setBoth :: Instance  -- ^ the original instance
         -> T.Ndx    -- ^ new primary node index
         -> T.Ndx    -- ^ new secondary node index
         -> Instance -- ^ the modified instance
setBoth t p s = t { pNode = p, sNode = s }

-- | Sets the movable flag on an instance.
setMovable :: Instance -- ^ The original instance
           -> Bool     -- ^ New movable flag
           -> Instance -- ^ The modified instance
setMovable t m = t { movable = m }

-- | Try to shrink the instance based on the reason why we can't
-- allocate it.
shrinkByType :: Instance -> T.FailMode -> Result Instance
shrinkByType inst T.FailMem = let v = mem inst - T.unitMem
                              in if v < T.unitMem
                                 then Bad "out of memory"
                                 else Ok inst { mem = v }
shrinkByType inst T.FailDisk =
  let newdisks = [d {dskSize = dskSize d - T.unitDsk}| d <- disks inst]
      v = dsk inst - (length . disks $ inst) * T.unitDsk
  in if any (< T.unitDsk) $ map dskSize newdisks
     then Bad "out of disk"
     else Ok inst { dsk = v, disks = newdisks }
shrinkByType inst T.FailCPU = let v = vcpus inst - T.unitCpu
                              in if v < T.unitCpu
                                 then Bad "out of vcpus"
                                 else Ok inst { vcpus = v }
shrinkByType inst T.FailSpindles =
  case disks inst of
    [Disk ds sp] -> case sp of
                      Nothing -> Bad "No spindles, shouldn't have happened"
                      Just sp' -> let v = sp' - T.unitSpindle
                                  in if v < T.unitSpindle
                                     then Bad "out of spindles"
                                     else Ok inst { disks = [Disk ds (Just v)] }
    d -> Bad $ "Expected one disk, but found " ++ show d
shrinkByType _ f = Bad $ "Unhandled failure mode " ++ show f

-- | Get the number of disk spindles
getTotalSpindles :: Instance -> Maybe Int
getTotalSpindles inst =
  foldr (liftM2 (+) . dskSpindles ) (Just 0) (disks inst)

-- | Return the spec of an instance.
specOf :: Instance -> T.RSpec
specOf Instance { mem = m, dsk = d, vcpus = c, disks = dl } =
  let sp = case dl of
             [Disk _ (Just sp')] -> sp'
             _ -> 0
  in T.RSpec { T.rspecCpu = c, T.rspecMem = m,
               T.rspecDsk = d, T.rspecSpn = sp }

-- | Checks if an instance is smaller/bigger than a given spec. Returns
-- OpGood for a correct spec, otherwise Bad one of the possible
-- failure modes.
instCompareISpec :: Ordering -> Instance-> T.ISpec -> Bool -> T.OpResult ()
instCompareISpec which inst ispec exclstor
  | which == mem inst `compare` T.iSpecMemorySize ispec = Bad T.FailMem
  | which `elem` map ((`compare` T.iSpecDiskSize ispec) . dskSize)
    (disks inst) = Bad T.FailDisk
  | which == vcpus inst `compare` T.iSpecCpuCount ispec = Bad T.FailCPU
  | exclstor &&
    case getTotalSpindles inst of
      Nothing -> True
      Just sp_sum -> which == sp_sum `compare` T.iSpecSpindleUse ispec
    = Bad T.FailSpindles
  | not exclstor && which == spindleUse inst `compare` T.iSpecSpindleUse ispec
    = Bad T.FailSpindles
  | diskTemplate inst /= T.DTDiskless &&
    which == length (disks inst) `compare` T.iSpecDiskCount ispec
    = Bad T.FailDiskCount
  | otherwise = Ok ()

-- | Checks if an instance is smaller than a given spec.
instBelowISpec :: Instance -> T.ISpec -> Bool -> T.OpResult ()
instBelowISpec = instCompareISpec GT

-- | Checks if an instance is bigger than a given spec.
instAboveISpec :: Instance -> T.ISpec -> Bool -> T.OpResult ()
instAboveISpec inst spec exclstore =
  genericResult (const $ Bad T.FailTooSmall) Ok
  $ instCompareISpec LT inst spec exclstore

-- | Checks if an instance matches a min/max specs pair
instMatchesMinMaxSpecs :: Instance -> T.MinMaxISpecs -> Bool -> T.OpResult ()
instMatchesMinMaxSpecs inst minmax exclstor = do
  instAboveISpec inst (T.minMaxISpecsMinSpec minmax) exclstor
  instBelowISpec inst (T.minMaxISpecsMaxSpec minmax) exclstor

-- | Checks if an instance matches any specs of a policy
instMatchesSpecs :: Instance -> [T.MinMaxISpecs] -> Bool -> T.OpResult ()
 -- Return Ok for no constraints, though this should never happen
instMatchesSpecs _ [] _ = Ok ()
instMatchesSpecs inst minmaxes exclstor =
  -- The initial "Bad" should be always replaced by a real result
  foldr eithermatch (Bad T.FailInternal) minmaxes
  where eithermatch mm (Bad _) = instMatchesMinMaxSpecs inst mm exclstor
        eithermatch _ y@(Ok ()) = y

-- | Checks if an instance matches a policy.
instMatchesPolicy :: Instance -> T.IPolicy -> Bool -> T.OpResult ()
instMatchesPolicy inst ipol exclstor = do
  instMatchesSpecs inst (T.iPolicyMinMaxISpecs ipol) exclstor
  if diskTemplate inst `elem` T.iPolicyDiskTemplates ipol
    then Ok ()
    else Bad T.FailDisk

-- | Checks whether the instance uses a secondary node.
--
-- /Note:/ This should be reconciled with @'sNode' ==
-- 'Node.noSecondary'@.
hasSecondary :: Instance -> Bool
hasSecondary = (== T.DTDrbd8) . diskTemplate

-- | Computed the number of nodes for a given disk template.
requiredNodes :: T.DiskTemplate -> Int
requiredNodes T.DTDrbd8 = 2
requiredNodes _         = 1

-- | Computes all nodes of an instance.
allNodes :: Instance -> [T.Ndx]
allNodes inst = case diskTemplate inst of
                  T.DTDrbd8 -> [pNode inst, sNode inst]
                  _ -> [pNode inst]

-- | Checks whether a given disk template uses local storage.
usesLocalStorage :: Instance -> Bool
usesLocalStorage = (`elem` localStorageTemplates) . diskTemplate

-- | Checks whether a given disk template supported moves.
supportsMoves :: T.DiskTemplate -> Bool
supportsMoves = (`elem` movableDiskTemplates)

-- | A simple wrapper over 'T.templateMirrorType'.
mirrorType :: Instance -> T.MirrorType
mirrorType = T.templateMirrorType . diskTemplate


-- | Whether the instance uses memory on its host node.
-- Depends on the `InstanceStatus` and on whether the instance is forthcoming;
-- instances that aren't running or existent don't use memory.
usesMemory :: Instance -> Bool
usesMemory inst
  | forthcoming inst = False
  | otherwise        = case runSt inst of
      T.StatusDown    -> False
      T.StatusOffline -> False
      T.ErrorDown     -> False
      T.ErrorUp       -> True
      T.NodeDown      -> True -- value has little meaning when node is down
      T.NodeOffline   -> True -- value has little meaning when node is offline
      T.Running       -> True
      T.UserDown      -> False
      T.WrongNode     -> True
