Statistics
| Branch: | Tag: | Revision:

root / htools / Ganeti / Confd / Utils.hs @ 29a30533

History | View | Annotate | Download (2.5 kB)

1 62377cf5 Iustin Pop
{-| Implementation of the Ganeti confd utilities.
2 62377cf5 Iustin Pop
3 62377cf5 Iustin Pop
This holds a few utility functions that could be useful in both
4 62377cf5 Iustin Pop
clients and servers.
5 62377cf5 Iustin Pop
6 62377cf5 Iustin Pop
-}
7 62377cf5 Iustin Pop
8 62377cf5 Iustin Pop
{-
9 62377cf5 Iustin Pop
10 62377cf5 Iustin Pop
Copyright (C) 2011, 2012 Google Inc.
11 62377cf5 Iustin Pop
12 62377cf5 Iustin Pop
This program is free software; you can redistribute it and/or modify
13 62377cf5 Iustin Pop
it under the terms of the GNU General Public License as published by
14 62377cf5 Iustin Pop
the Free Software Foundation; either version 2 of the License, or
15 62377cf5 Iustin Pop
(at your option) any later version.
16 62377cf5 Iustin Pop
17 62377cf5 Iustin Pop
This program is distributed in the hope that it will be useful, but
18 62377cf5 Iustin Pop
WITHOUT ANY WARRANTY; without even the implied warranty of
19 62377cf5 Iustin Pop
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
20 62377cf5 Iustin Pop
General Public License for more details.
21 62377cf5 Iustin Pop
22 62377cf5 Iustin Pop
You should have received a copy of the GNU General Public License
23 62377cf5 Iustin Pop
along with this program; if not, write to the Free Software
24 62377cf5 Iustin Pop
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
25 62377cf5 Iustin Pop
02110-1301, USA.
26 62377cf5 Iustin Pop
27 62377cf5 Iustin Pop
-}
28 62377cf5 Iustin Pop
29 62377cf5 Iustin Pop
module Ganeti.Confd.Utils
30 62377cf5 Iustin Pop
  ( getClusterHmac
31 62377cf5 Iustin Pop
  , parseRequest
32 62377cf5 Iustin Pop
  , parseMessage
33 62377cf5 Iustin Pop
  , signMessage
34 62377cf5 Iustin Pop
  ) where
35 62377cf5 Iustin Pop
36 62377cf5 Iustin Pop
import qualified Data.ByteString as B
37 62377cf5 Iustin Pop
import qualified Text.JSON as J
38 62377cf5 Iustin Pop
39 62377cf5 Iustin Pop
import Ganeti.BasicTypes
40 cdc2392b Iustin Pop
import Ganeti.Confd.Types
41 62377cf5 Iustin Pop
import Ganeti.Hash
42 62377cf5 Iustin Pop
import qualified Ganeti.Constants as C
43 9eeb0aa5 Michael Hanselmann
import qualified Ganeti.Path as Path
44 f3baf5ef Iustin Pop
import Ganeti.JSON
45 26d62e4c Iustin Pop
import Ganeti.Utils
46 62377cf5 Iustin Pop
47 62377cf5 Iustin Pop
-- | Returns the HMAC key.
48 62377cf5 Iustin Pop
getClusterHmac :: IO HashKey
49 29a30533 Iustin Pop
getClusterHmac = Path.confdHmacKey >>= fmap B.unpack . B.readFile
50 62377cf5 Iustin Pop
51 62377cf5 Iustin Pop
-- | Parses a signed request.
52 62377cf5 Iustin Pop
parseRequest :: HashKey -> String -> Result (String, String, ConfdRequest)
53 62377cf5 Iustin Pop
parseRequest key str = do
54 62377cf5 Iustin Pop
  (SignedMessage hmac msg salt) <- fromJResult "parsing request" $ J.decode str
55 62377cf5 Iustin Pop
  req <- if verifyMac key (Just salt) msg hmac
56 62377cf5 Iustin Pop
           then fromJResult "parsing message" $ J.decode msg
57 62377cf5 Iustin Pop
           else Bad "HMAC verification failed"
58 62377cf5 Iustin Pop
  return (salt, msg, req)
59 62377cf5 Iustin Pop
60 62377cf5 Iustin Pop
-- | Mesage parsing. This can either result in a good, valid message,
61 62377cf5 Iustin Pop
-- or fail in the Result monad.
62 62377cf5 Iustin Pop
parseMessage :: HashKey -> String -> Integer
63 62377cf5 Iustin Pop
             -> Result (String, ConfdRequest)
64 62377cf5 Iustin Pop
parseMessage hmac msg curtime = do
65 62377cf5 Iustin Pop
  (salt, origmsg, request) <- parseRequest hmac msg
66 62377cf5 Iustin Pop
  ts <- tryRead "Parsing timestamp" salt::Result Integer
67 5b11f8db Iustin Pop
  if abs (ts - curtime) > fromIntegral C.confdMaxClockSkew
68 62377cf5 Iustin Pop
    then fail "Too old/too new timestamp or clock skew"
69 62377cf5 Iustin Pop
    else return (origmsg, request)
70 62377cf5 Iustin Pop
71 62377cf5 Iustin Pop
-- | Signs a message with a given key and salt.
72 62377cf5 Iustin Pop
signMessage :: HashKey -> String -> String -> SignedMessage
73 62377cf5 Iustin Pop
signMessage key salt msg =
74 62377cf5 Iustin Pop
  SignedMessage { signedMsgMsg  = msg
75 62377cf5 Iustin Pop
                , signedMsgSalt = salt
76 62377cf5 Iustin Pop
                , signedMsgHmac = hmac
77 62377cf5 Iustin Pop
                }
78 62377cf5 Iustin Pop
    where hmac = computeMac key (Just salt) msg