Statistics
| Branch: | Tag: | Revision:

root / lib / server / noded.py @ 5483fd73

History | View | Annotate | Download (28.7 kB)

1 69cf3abd Michael Hanselmann
#
2 a8083063 Iustin Pop
#
3 a8083063 Iustin Pop
4 c417e115 Iustin Pop
# Copyright (C) 2006, 2007, 2010, 2011 Google Inc.
5 a8083063 Iustin Pop
#
6 a8083063 Iustin Pop
# This program is free software; you can redistribute it and/or modify
7 a8083063 Iustin Pop
# it under the terms of the GNU General Public License as published by
8 a8083063 Iustin Pop
# the Free Software Foundation; either version 2 of the License, or
9 a8083063 Iustin Pop
# (at your option) any later version.
10 a8083063 Iustin Pop
#
11 a8083063 Iustin Pop
# This program is distributed in the hope that it will be useful, but
12 a8083063 Iustin Pop
# WITHOUT ANY WARRANTY; without even the implied warranty of
13 a8083063 Iustin Pop
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 a8083063 Iustin Pop
# General Public License for more details.
15 a8083063 Iustin Pop
#
16 a8083063 Iustin Pop
# You should have received a copy of the GNU General Public License
17 a8083063 Iustin Pop
# along with this program; if not, write to the Free Software
18 a8083063 Iustin Pop
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
19 a8083063 Iustin Pop
# 02110-1301, USA.
20 a8083063 Iustin Pop
21 a8083063 Iustin Pop
22 a8083063 Iustin Pop
"""Ganeti node daemon"""
23 a8083063 Iustin Pop
24 b459a848 Andrea Spadaccini
# pylint: disable=C0103,W0142
25 7260cfbe Iustin Pop
26 7260cfbe Iustin Pop
# C0103: Functions in this module need to have a given name structure,
27 7260cfbe Iustin Pop
# and the name of the daemon doesn't match
28 7260cfbe Iustin Pop
29 7260cfbe Iustin Pop
# W0142: Used * or ** magic, since we do use it extensively in this
30 7260cfbe Iustin Pop
# module
31 3ecf6786 Iustin Pop
32 a8083063 Iustin Pop
import os
33 a8083063 Iustin Pop
import sys
34 c89189b1 Iustin Pop
import logging
35 84b58db2 Michael Hanselmann
import signal
36 f01738fc Iustin Pop
import codecs
37 a8083063 Iustin Pop
38 a8083063 Iustin Pop
from optparse import OptionParser
39 a8083063 Iustin Pop
40 a8083063 Iustin Pop
from ganeti import backend
41 a8083063 Iustin Pop
from ganeti import constants
42 a8083063 Iustin Pop
from ganeti import objects
43 a8083063 Iustin Pop
from ganeti import errors
44 25d6d12a Michael Hanselmann
from ganeti import jstore
45 cc28af80 Michael Hanselmann
from ganeti import daemon
46 1df6506c Michael Hanselmann
from ganeti import http
47 16abfbc2 Alexander Schreiber
from ganeti import utils
48 e337de97 Michael Hanselmann
from ganeti import storage
49 ab221ddf Michael Hanselmann
from ganeti import serializer
50 a744b676 Manuel Franceschini
from ganeti import netutils
51 a8083063 Iustin Pop
52 b459a848 Andrea Spadaccini
import ganeti.http.server # pylint: disable=W0611
53 19205c39 Michael Hanselmann
54 a8083063 Iustin Pop
55 25d6d12a Michael Hanselmann
queue_lock = None
56 25d6d12a Michael Hanselmann
57 25d6d12a Michael Hanselmann
58 81198f6e Iustin Pop
def _PrepareQueueLock():
59 81198f6e Iustin Pop
  """Try to prepare the queue lock.
60 81198f6e Iustin Pop

61 81198f6e Iustin Pop
  @return: None for success, otherwise an exception object
62 81198f6e Iustin Pop

63 81198f6e Iustin Pop
  """
64 b459a848 Andrea Spadaccini
  global queue_lock # pylint: disable=W0603
65 81198f6e Iustin Pop
66 81198f6e Iustin Pop
  if queue_lock is not None:
67 81198f6e Iustin Pop
    return None
68 81198f6e Iustin Pop
69 81198f6e Iustin Pop
  # Prepare job queue
70 81198f6e Iustin Pop
  try:
71 81198f6e Iustin Pop
    queue_lock = jstore.InitAndVerifyQueue(must_lock=False)
72 81198f6e Iustin Pop
    return None
73 81198f6e Iustin Pop
  except EnvironmentError, err:
74 81198f6e Iustin Pop
    return err
75 81198f6e Iustin Pop
76 81198f6e Iustin Pop
77 7f30777b Michael Hanselmann
def _RequireJobQueueLock(fn):
78 7f30777b Michael Hanselmann
  """Decorator for job queue manipulating functions.
79 7f30777b Michael Hanselmann

80 7f30777b Michael Hanselmann
  """
81 8785cb30 Michael Hanselmann
  QUEUE_LOCK_TIMEOUT = 10
82 8785cb30 Michael Hanselmann
83 7f30777b Michael Hanselmann
  def wrapper(*args, **kwargs):
84 7f30777b Michael Hanselmann
    # Locking in exclusive, blocking mode because there could be several
85 506cff12 Michael Hanselmann
    # children running at the same time. Waiting up to 10 seconds.
86 81198f6e Iustin Pop
    if _PrepareQueueLock() is not None:
87 81198f6e Iustin Pop
      raise errors.JobQueueError("Job queue failed initialization,"
88 81198f6e Iustin Pop
                                 " cannot update jobs")
89 8785cb30 Michael Hanselmann
    queue_lock.Exclusive(blocking=True, timeout=QUEUE_LOCK_TIMEOUT)
90 7f30777b Michael Hanselmann
    try:
91 7f30777b Michael Hanselmann
      return fn(*args, **kwargs)
92 7f30777b Michael Hanselmann
    finally:
93 7f30777b Michael Hanselmann
      queue_lock.Unlock()
94 8785cb30 Michael Hanselmann
95 7f30777b Michael Hanselmann
  return wrapper
96 7f30777b Michael Hanselmann
97 7f30777b Michael Hanselmann
98 1651d116 Michael Hanselmann
def _DecodeImportExportIO(ieio, ieioargs):
99 1651d116 Michael Hanselmann
  """Decodes import/export I/O information.
100 1651d116 Michael Hanselmann

101 1651d116 Michael Hanselmann
  """
102 1651d116 Michael Hanselmann
  if ieio == constants.IEIO_RAW_DISK:
103 1651d116 Michael Hanselmann
    assert len(ieioargs) == 1
104 1651d116 Michael Hanselmann
    return (objects.Disk.FromDict(ieioargs[0]), )
105 1651d116 Michael Hanselmann
106 1651d116 Michael Hanselmann
  if ieio == constants.IEIO_SCRIPT:
107 1651d116 Michael Hanselmann
    assert len(ieioargs) == 2
108 1651d116 Michael Hanselmann
    return (objects.Disk.FromDict(ieioargs[0]), ieioargs[1])
109 1651d116 Michael Hanselmann
110 1651d116 Michael Hanselmann
  return ieioargs
111 1651d116 Michael Hanselmann
112 1651d116 Michael Hanselmann
113 38b77287 Luca Bigliardi
class MlockallRequestExecutor(http.server.HttpServerRequestExecutor):
114 38b77287 Luca Bigliardi
  """Custom Request Executor class that ensures NodeHttpServer children are
115 38b77287 Luca Bigliardi
  locked in ram.
116 38b77287 Luca Bigliardi

117 38b77287 Luca Bigliardi
  """
118 38b77287 Luca Bigliardi
  def __init__(self, *args, **kwargs):
119 38b77287 Luca Bigliardi
    utils.Mlockall()
120 38b77287 Luca Bigliardi
121 38b77287 Luca Bigliardi
    http.server.HttpServerRequestExecutor.__init__(self, *args, **kwargs)
122 38b77287 Luca Bigliardi
123 38b77287 Luca Bigliardi
124 19205c39 Michael Hanselmann
class NodeHttpServer(http.server.HttpServer):
125 3ecf6786 Iustin Pop
  """The server implementation.
126 3ecf6786 Iustin Pop

127 3ecf6786 Iustin Pop
  This class holds all methods exposed over the RPC interface.
128 3ecf6786 Iustin Pop

129 3ecf6786 Iustin Pop
  """
130 2d54e29c Iustin Pop
  # too many public methods, and unused args - all methods get params
131 2d54e29c Iustin Pop
  # due to the API
132 b459a848 Andrea Spadaccini
  # pylint: disable=R0904,W0613
133 cc28af80 Michael Hanselmann
  def __init__(self, *args, **kwargs):
134 19205c39 Michael Hanselmann
    http.server.HttpServer.__init__(self, *args, **kwargs)
135 cc28af80 Michael Hanselmann
    self.noded_pid = os.getpid()
136 cc28af80 Michael Hanselmann
137 cc28af80 Michael Hanselmann
  def HandleRequest(self, req):
138 1df6506c Michael Hanselmann
    """Handle a request.
139 a8083063 Iustin Pop

140 098c0958 Michael Hanselmann
    """
141 19205c39 Michael Hanselmann
    if req.request_method.upper() != http.HTTP_PUT:
142 84f2756e Michael Hanselmann
      raise http.HttpBadRequest()
143 1df6506c Michael Hanselmann
144 cc28af80 Michael Hanselmann
    path = req.request_path
145 81010134 Iustin Pop
    if path.startswith("/"):
146 81010134 Iustin Pop
      path = path[1:]
147 81010134 Iustin Pop
148 1df6506c Michael Hanselmann
    method = getattr(self, "perspective_%s" % path, None)
149 1df6506c Michael Hanselmann
    if method is None:
150 84f2756e Michael Hanselmann
      raise http.HttpNotFound()
151 a8083063 Iustin Pop
152 81010134 Iustin Pop
    try:
153 ab221ddf Michael Hanselmann
      result = (True, method(serializer.LoadJson(req.request_body)))
154 4dd42c9d Iustin Pop
155 0623d351 Iustin Pop
    except backend.RPCFail, err:
156 0623d351 Iustin Pop
      # our custom failure exception; str(err) works fine if the
157 0623d351 Iustin Pop
      # exception was constructed with a single argument, and in
158 0623d351 Iustin Pop
      # this case, err.message == err.args[0] == str(err)
159 ab221ddf Michael Hanselmann
      result = (False, str(err))
160 9ae49f27 Guido Trotter
    except errors.QuitGanetiException, err:
161 84b58db2 Michael Hanselmann
      # Tell parent to quit
162 0623d351 Iustin Pop
      logging.info("Shutting down the node daemon, arguments: %s",
163 0623d351 Iustin Pop
                   str(err.args))
164 cc28af80 Michael Hanselmann
      os.kill(self.noded_pid, signal.SIGTERM)
165 0623d351 Iustin Pop
      # And return the error's arguments, which must be already in
166 0623d351 Iustin Pop
      # correct tuple format
167 ab221ddf Michael Hanselmann
      result = err.args
168 4dd42c9d Iustin Pop
    except Exception, err:
169 0623d351 Iustin Pop
      logging.exception("Error in RPC call")
170 ab221ddf Michael Hanselmann
      result = (False, "Error while executing backend function: %s" % str(err))
171 ab221ddf Michael Hanselmann
172 ab221ddf Michael Hanselmann
    return serializer.DumpJson(result, indent=False)
173 a8083063 Iustin Pop
174 a8083063 Iustin Pop
  # the new block devices  --------------------------
175 a8083063 Iustin Pop
176 3ecf6786 Iustin Pop
  @staticmethod
177 3ecf6786 Iustin Pop
  def perspective_blockdev_create(params):
178 3ecf6786 Iustin Pop
    """Create a block device.
179 3ecf6786 Iustin Pop

180 3ecf6786 Iustin Pop
    """
181 3f78eef2 Iustin Pop
    bdev_s, size, owner, on_primary, info = params
182 319856a9 Michael Hanselmann
    bdev = objects.Disk.FromDict(bdev_s)
183 a8083063 Iustin Pop
    if bdev is None:
184 a8083063 Iustin Pop
      raise ValueError("can't unserialize data!")
185 821d1bd1 Iustin Pop
    return backend.BlockdevCreate(bdev, size, owner, on_primary, info)
186 a8083063 Iustin Pop
187 3ecf6786 Iustin Pop
  @staticmethod
188 9c007da8 Renรฉ Nussbaumer
  def perspective_blockdev_pause_resume_sync(params):
189 9c007da8 Renรฉ Nussbaumer
    """Pause/resume sync of a block device.
190 9c007da8 Renรฉ Nussbaumer

191 9c007da8 Renรฉ Nussbaumer
    """
192 9c007da8 Renรฉ Nussbaumer
    disks_s, pause = params
193 9c007da8 Renรฉ Nussbaumer
    disks = [objects.Disk.FromDict(bdev_s) for bdev_s in disks_s]
194 9c007da8 Renรฉ Nussbaumer
    return backend.BlockdevPauseResumeSync(disks, pause)
195 9c007da8 Renรฉ Nussbaumer
196 9c007da8 Renรฉ Nussbaumer
  @staticmethod
197 271b7cf9 Renรฉ Nussbaumer
  def perspective_blockdev_wipe(params):
198 271b7cf9 Renรฉ Nussbaumer
    """Wipe a block device.
199 271b7cf9 Renรฉ Nussbaumer

200 271b7cf9 Renรฉ Nussbaumer
    """
201 271b7cf9 Renรฉ Nussbaumer
    bdev_s, offset, size = params
202 271b7cf9 Renรฉ Nussbaumer
    bdev = objects.Disk.FromDict(bdev_s)
203 271b7cf9 Renรฉ Nussbaumer
    return backend.BlockdevWipe(bdev, offset, size)
204 271b7cf9 Renรฉ Nussbaumer
205 271b7cf9 Renรฉ Nussbaumer
  @staticmethod
206 3ecf6786 Iustin Pop
  def perspective_blockdev_remove(params):
207 3ecf6786 Iustin Pop
    """Remove a block device.
208 3ecf6786 Iustin Pop

209 3ecf6786 Iustin Pop
    """
210 a8083063 Iustin Pop
    bdev_s = params[0]
211 319856a9 Michael Hanselmann
    bdev = objects.Disk.FromDict(bdev_s)
212 821d1bd1 Iustin Pop
    return backend.BlockdevRemove(bdev)
213 a8083063 Iustin Pop
214 3ecf6786 Iustin Pop
  @staticmethod
215 f3e513ad Iustin Pop
  def perspective_blockdev_rename(params):
216 f3e513ad Iustin Pop
    """Remove a block device.
217 f3e513ad Iustin Pop

218 f3e513ad Iustin Pop
    """
219 8a31717c Michael Hanselmann
    devlist = [(objects.Disk.FromDict(ds), uid) for ds, uid in params[0]]
220 821d1bd1 Iustin Pop
    return backend.BlockdevRename(devlist)
221 f3e513ad Iustin Pop
222 f3e513ad Iustin Pop
  @staticmethod
223 3ecf6786 Iustin Pop
  def perspective_blockdev_assemble(params):
224 3ecf6786 Iustin Pop
    """Assemble a block device.
225 3ecf6786 Iustin Pop

226 3ecf6786 Iustin Pop
    """
227 c417e115 Iustin Pop
    bdev_s, owner, on_primary, idx = params
228 319856a9 Michael Hanselmann
    bdev = objects.Disk.FromDict(bdev_s)
229 a8083063 Iustin Pop
    if bdev is None:
230 a8083063 Iustin Pop
      raise ValueError("can't unserialize data!")
231 c417e115 Iustin Pop
    return backend.BlockdevAssemble(bdev, owner, on_primary, idx)
232 a8083063 Iustin Pop
233 3ecf6786 Iustin Pop
  @staticmethod
234 3ecf6786 Iustin Pop
  def perspective_blockdev_shutdown(params):
235 3ecf6786 Iustin Pop
    """Shutdown a block device.
236 3ecf6786 Iustin Pop

237 3ecf6786 Iustin Pop
    """
238 a8083063 Iustin Pop
    bdev_s = params[0]
239 319856a9 Michael Hanselmann
    bdev = objects.Disk.FromDict(bdev_s)
240 a8083063 Iustin Pop
    if bdev is None:
241 a8083063 Iustin Pop
      raise ValueError("can't unserialize data!")
242 821d1bd1 Iustin Pop
    return backend.BlockdevShutdown(bdev)
243 a8083063 Iustin Pop
244 3ecf6786 Iustin Pop
  @staticmethod
245 153d9724 Iustin Pop
  def perspective_blockdev_addchildren(params):
246 3ecf6786 Iustin Pop
    """Add a child to a mirror device.
247 3ecf6786 Iustin Pop

248 3ecf6786 Iustin Pop
    Note: this is only valid for mirror devices. It's the caller's duty
249 3ecf6786 Iustin Pop
    to send a correct disk, otherwise we raise an error.
250 3ecf6786 Iustin Pop

251 3ecf6786 Iustin Pop
    """
252 a8083063 Iustin Pop
    bdev_s, ndev_s = params
253 319856a9 Michael Hanselmann
    bdev = objects.Disk.FromDict(bdev_s)
254 153d9724 Iustin Pop
    ndevs = [objects.Disk.FromDict(disk_s) for disk_s in ndev_s]
255 153d9724 Iustin Pop
    if bdev is None or ndevs.count(None) > 0:
256 a8083063 Iustin Pop
      raise ValueError("can't unserialize data!")
257 821d1bd1 Iustin Pop
    return backend.BlockdevAddchildren(bdev, ndevs)
258 a8083063 Iustin Pop
259 3ecf6786 Iustin Pop
  @staticmethod
260 153d9724 Iustin Pop
  def perspective_blockdev_removechildren(params):
261 3ecf6786 Iustin Pop
    """Remove a child from a mirror device.
262 3ecf6786 Iustin Pop

263 3ecf6786 Iustin Pop
    This is only valid for mirror devices, of course. It's the callers
264 3ecf6786 Iustin Pop
    duty to send a correct disk, otherwise we raise an error.
265 3ecf6786 Iustin Pop

266 3ecf6786 Iustin Pop
    """
267 a8083063 Iustin Pop
    bdev_s, ndev_s = params
268 319856a9 Michael Hanselmann
    bdev = objects.Disk.FromDict(bdev_s)
269 153d9724 Iustin Pop
    ndevs = [objects.Disk.FromDict(disk_s) for disk_s in ndev_s]
270 153d9724 Iustin Pop
    if bdev is None or ndevs.count(None) > 0:
271 a8083063 Iustin Pop
      raise ValueError("can't unserialize data!")
272 821d1bd1 Iustin Pop
    return backend.BlockdevRemovechildren(bdev, ndevs)
273 a8083063 Iustin Pop
274 3ecf6786 Iustin Pop
  @staticmethod
275 3ecf6786 Iustin Pop
  def perspective_blockdev_getmirrorstatus(params):
276 3ecf6786 Iustin Pop
    """Return the mirror status for a list of disks.
277 3ecf6786 Iustin Pop

278 3ecf6786 Iustin Pop
    """
279 319856a9 Michael Hanselmann
    disks = [objects.Disk.FromDict(dsk_s)
280 e437117f Michael Hanselmann
             for dsk_s in params[0]]
281 36145b12 Michael Hanselmann
    return [status.ToDict()
282 36145b12 Michael Hanselmann
            for status in backend.BlockdevGetmirrorstatus(disks)]
283 a8083063 Iustin Pop
284 3ecf6786 Iustin Pop
  @staticmethod
285 b8d26c6e Michael Hanselmann
  def perspective_blockdev_getmirrorstatus_multi(params):
286 b8d26c6e Michael Hanselmann
    """Return the mirror status for a list of disks.
287 b8d26c6e Michael Hanselmann

288 b8d26c6e Michael Hanselmann
    """
289 b8d26c6e Michael Hanselmann
    (node_disks, ) = params
290 b8d26c6e Michael Hanselmann
291 b8d26c6e Michael Hanselmann
    node_name = netutils.Hostname.GetSysName()
292 b8d26c6e Michael Hanselmann
293 b8d26c6e Michael Hanselmann
    disks = [objects.Disk.FromDict(dsk_s)
294 b8d26c6e Michael Hanselmann
             for dsk_s in node_disks.get(node_name, [])]
295 b8d26c6e Michael Hanselmann
296 c6a9dffa Michael Hanselmann
    result = []
297 c6a9dffa Michael Hanselmann
298 c6a9dffa Michael Hanselmann
    for (success, status) in backend.BlockdevGetmirrorstatusMulti(disks):
299 c6a9dffa Michael Hanselmann
      if success:
300 c6a9dffa Michael Hanselmann
        result.append((success, status.ToDict()))
301 c6a9dffa Michael Hanselmann
      else:
302 c6a9dffa Michael Hanselmann
        result.append((success, status))
303 c6a9dffa Michael Hanselmann
304 c6a9dffa Michael Hanselmann
    return result
305 b8d26c6e Michael Hanselmann
306 b8d26c6e Michael Hanselmann
  @staticmethod
307 3ecf6786 Iustin Pop
  def perspective_blockdev_find(params):
308 3ecf6786 Iustin Pop
    """Expose the FindBlockDevice functionality for a disk.
309 3ecf6786 Iustin Pop

310 3ecf6786 Iustin Pop
    This will try to find but not activate a disk.
311 3ecf6786 Iustin Pop

312 3ecf6786 Iustin Pop
    """
313 319856a9 Michael Hanselmann
    disk = objects.Disk.FromDict(params[0])
314 ddfe2228 Michael Hanselmann
315 ddfe2228 Michael Hanselmann
    result = backend.BlockdevFind(disk)
316 ddfe2228 Michael Hanselmann
    if result is None:
317 ddfe2228 Michael Hanselmann
      return None
318 ddfe2228 Michael Hanselmann
319 ddfe2228 Michael Hanselmann
    return result.ToDict()
320 a8083063 Iustin Pop
321 3ecf6786 Iustin Pop
  @staticmethod
322 3ecf6786 Iustin Pop
  def perspective_blockdev_snapshot(params):
323 3ecf6786 Iustin Pop
    """Create a snapshot device.
324 3ecf6786 Iustin Pop

325 3ecf6786 Iustin Pop
    Note that this is only valid for LVM disks, if we get passed
326 3ecf6786 Iustin Pop
    something else we raise an exception. The snapshot device can be
327 3ecf6786 Iustin Pop
    remove by calling the generic block device remove call.
328 3ecf6786 Iustin Pop

329 3ecf6786 Iustin Pop
    """
330 319856a9 Michael Hanselmann
    cfbd = objects.Disk.FromDict(params[0])
331 821d1bd1 Iustin Pop
    return backend.BlockdevSnapshot(cfbd)
332 a8083063 Iustin Pop
333 4c8ba8b3 Iustin Pop
  @staticmethod
334 4c8ba8b3 Iustin Pop
  def perspective_blockdev_grow(params):
335 4c8ba8b3 Iustin Pop
    """Grow a stack of devices.
336 4c8ba8b3 Iustin Pop

337 4c8ba8b3 Iustin Pop
    """
338 4c8ba8b3 Iustin Pop
    cfbd = objects.Disk.FromDict(params[0])
339 4c8ba8b3 Iustin Pop
    amount = params[1]
340 a59faf4b Iustin Pop
    dryrun = params[2]
341 a59faf4b Iustin Pop
    return backend.BlockdevGrow(cfbd, amount, dryrun)
342 4c8ba8b3 Iustin Pop
343 d61cbe76 Iustin Pop
  @staticmethod
344 d61cbe76 Iustin Pop
  def perspective_blockdev_close(params):
345 d61cbe76 Iustin Pop
    """Closes the given block devices.
346 d61cbe76 Iustin Pop

347 d61cbe76 Iustin Pop
    """
348 b2e7666a Iustin Pop
    disks = [objects.Disk.FromDict(cf) for cf in params[1]]
349 821d1bd1 Iustin Pop
    return backend.BlockdevClose(params[0], disks)
350 d61cbe76 Iustin Pop
351 968a7623 Iustin Pop
  @staticmethod
352 968a7623 Iustin Pop
  def perspective_blockdev_getsize(params):
353 968a7623 Iustin Pop
    """Compute the sizes of the given block devices.
354 968a7623 Iustin Pop

355 968a7623 Iustin Pop
    """
356 968a7623 Iustin Pop
    disks = [objects.Disk.FromDict(cf) for cf in params[0]]
357 968a7623 Iustin Pop
    return backend.BlockdevGetsize(disks)
358 968a7623 Iustin Pop
359 858f3d18 Iustin Pop
  @staticmethod
360 858f3d18 Iustin Pop
  def perspective_blockdev_export(params):
361 858f3d18 Iustin Pop
    """Compute the sizes of the given block devices.
362 858f3d18 Iustin Pop

363 858f3d18 Iustin Pop
    """
364 858f3d18 Iustin Pop
    disk = objects.Disk.FromDict(params[0])
365 858f3d18 Iustin Pop
    dest_node, dest_path, cluster_name = params[1:]
366 858f3d18 Iustin Pop
    return backend.BlockdevExport(disk, dest_node, dest_path, cluster_name)
367 858f3d18 Iustin Pop
368 6b93ec9d Iustin Pop
  # blockdev/drbd specific methods ----------
369 6b93ec9d Iustin Pop
370 6b93ec9d Iustin Pop
  @staticmethod
371 6b93ec9d Iustin Pop
  def perspective_drbd_disconnect_net(params):
372 6b93ec9d Iustin Pop
    """Disconnects the network connection of drbd disks.
373 6b93ec9d Iustin Pop

374 6b93ec9d Iustin Pop
    Note that this is only valid for drbd disks, so the members of the
375 6b93ec9d Iustin Pop
    disk list must all be drbd devices.
376 6b93ec9d Iustin Pop

377 6b93ec9d Iustin Pop
    """
378 6b93ec9d Iustin Pop
    nodes_ip, disks = params
379 6b93ec9d Iustin Pop
    disks = [objects.Disk.FromDict(cf) for cf in disks]
380 6b93ec9d Iustin Pop
    return backend.DrbdDisconnectNet(nodes_ip, disks)
381 6b93ec9d Iustin Pop
382 6b93ec9d Iustin Pop
  @staticmethod
383 6b93ec9d Iustin Pop
  def perspective_drbd_attach_net(params):
384 6b93ec9d Iustin Pop
    """Attaches the network connection of drbd disks.
385 6b93ec9d Iustin Pop

386 6b93ec9d Iustin Pop
    Note that this is only valid for drbd disks, so the members of the
387 6b93ec9d Iustin Pop
    disk list must all be drbd devices.
388 6b93ec9d Iustin Pop

389 6b93ec9d Iustin Pop
    """
390 6b93ec9d Iustin Pop
    nodes_ip, disks, instance_name, multimaster = params
391 6b93ec9d Iustin Pop
    disks = [objects.Disk.FromDict(cf) for cf in disks]
392 821d1bd1 Iustin Pop
    return backend.DrbdAttachNet(nodes_ip, disks,
393 821d1bd1 Iustin Pop
                                     instance_name, multimaster)
394 6b93ec9d Iustin Pop
395 6b93ec9d Iustin Pop
  @staticmethod
396 6b93ec9d Iustin Pop
  def perspective_drbd_wait_sync(params):
397 6b93ec9d Iustin Pop
    """Wait until DRBD disks are synched.
398 6b93ec9d Iustin Pop

399 6b93ec9d Iustin Pop
    Note that this is only valid for drbd disks, so the members of the
400 6b93ec9d Iustin Pop
    disk list must all be drbd devices.
401 6b93ec9d Iustin Pop

402 6b93ec9d Iustin Pop
    """
403 6b93ec9d Iustin Pop
    nodes_ip, disks = params
404 6b93ec9d Iustin Pop
    disks = [objects.Disk.FromDict(cf) for cf in disks]
405 6b93ec9d Iustin Pop
    return backend.DrbdWaitSync(nodes_ip, disks)
406 6b93ec9d Iustin Pop
407 c46b9782 Luca Bigliardi
  @staticmethod
408 c46b9782 Luca Bigliardi
  def perspective_drbd_helper(params):
409 c46b9782 Luca Bigliardi
    """Query drbd helper.
410 c46b9782 Luca Bigliardi

411 c46b9782 Luca Bigliardi
    """
412 c46b9782 Luca Bigliardi
    return backend.GetDrbdUsermodeHelper()
413 c46b9782 Luca Bigliardi
414 a8083063 Iustin Pop
  # export/import  --------------------------
415 a8083063 Iustin Pop
416 3ecf6786 Iustin Pop
  @staticmethod
417 3ecf6786 Iustin Pop
  def perspective_finalize_export(params):
418 3ecf6786 Iustin Pop
    """Expose the finalize export functionality.
419 a8083063 Iustin Pop

420 3ecf6786 Iustin Pop
    """
421 319856a9 Michael Hanselmann
    instance = objects.Instance.FromDict(params[0])
422 7b651654 Michael Hanselmann
423 7b651654 Michael Hanselmann
    snap_disks = []
424 7b651654 Michael Hanselmann
    for disk in params[1]:
425 7b651654 Michael Hanselmann
      if isinstance(disk, bool):
426 7b651654 Michael Hanselmann
        snap_disks.append(disk)
427 7b651654 Michael Hanselmann
      else:
428 7b651654 Michael Hanselmann
        snap_disks.append(objects.Disk.FromDict(disk))
429 7b651654 Michael Hanselmann
430 a8083063 Iustin Pop
    return backend.FinalizeExport(instance, snap_disks)
431 a8083063 Iustin Pop
432 3ecf6786 Iustin Pop
  @staticmethod
433 3ecf6786 Iustin Pop
  def perspective_export_info(params):
434 3ecf6786 Iustin Pop
    """Query information about an existing export on this node.
435 3ecf6786 Iustin Pop

436 3ecf6786 Iustin Pop
    The given path may not contain an export, in which case we return
437 3ecf6786 Iustin Pop
    None.
438 3ecf6786 Iustin Pop

439 3ecf6786 Iustin Pop
    """
440 3ecf6786 Iustin Pop
    path = params[0]
441 3eccac06 Iustin Pop
    return backend.ExportInfo(path)
442 a8083063 Iustin Pop
443 3ecf6786 Iustin Pop
  @staticmethod
444 3ecf6786 Iustin Pop
  def perspective_export_list(params):
445 3ecf6786 Iustin Pop
    """List the available exports on this node.
446 3ecf6786 Iustin Pop

447 3ecf6786 Iustin Pop
    Note that as opposed to export_info, which may query data about an
448 3ecf6786 Iustin Pop
    export in any path, this only queries the standard Ganeti path
449 3ecf6786 Iustin Pop
    (constants.EXPORT_DIR).
450 3ecf6786 Iustin Pop

451 3ecf6786 Iustin Pop
    """
452 a8083063 Iustin Pop
    return backend.ListExports()
453 a8083063 Iustin Pop
454 3ecf6786 Iustin Pop
  @staticmethod
455 3ecf6786 Iustin Pop
  def perspective_export_remove(params):
456 3ecf6786 Iustin Pop
    """Remove an export.
457 3ecf6786 Iustin Pop

458 3ecf6786 Iustin Pop
    """
459 a8083063 Iustin Pop
    export = params[0]
460 a8083063 Iustin Pop
    return backend.RemoveExport(export)
461 a8083063 Iustin Pop
462 2be7273c Apollon Oikonomopoulos
  # block device ---------------------
463 2be7273c Apollon Oikonomopoulos
  @staticmethod
464 2be7273c Apollon Oikonomopoulos
  def perspective_bdev_sizes(params):
465 2be7273c Apollon Oikonomopoulos
    """Query the list of block devices
466 2be7273c Apollon Oikonomopoulos

467 2be7273c Apollon Oikonomopoulos
    """
468 2be7273c Apollon Oikonomopoulos
    devices = params[0]
469 2be7273c Apollon Oikonomopoulos
    return backend.GetBlockDevSizes(devices)
470 2be7273c Apollon Oikonomopoulos
471 a8083063 Iustin Pop
  # volume  --------------------------
472 a8083063 Iustin Pop
473 3ecf6786 Iustin Pop
  @staticmethod
474 b2a6ccd4 Iustin Pop
  def perspective_lv_list(params):
475 3ecf6786 Iustin Pop
    """Query the list of logical volumes in a given volume group.
476 3ecf6786 Iustin Pop

477 3ecf6786 Iustin Pop
    """
478 a8083063 Iustin Pop
    vgname = params[0]
479 c26a6bd2 Iustin Pop
    return backend.GetVolumeList(vgname)
480 a8083063 Iustin Pop
481 3ecf6786 Iustin Pop
  @staticmethod
482 3ecf6786 Iustin Pop
  def perspective_vg_list(params):
483 3ecf6786 Iustin Pop
    """Query the list of volume groups.
484 3ecf6786 Iustin Pop

485 3ecf6786 Iustin Pop
    """
486 a8083063 Iustin Pop
    return backend.ListVolumeGroups()
487 a8083063 Iustin Pop
488 e337de97 Michael Hanselmann
  # Storage --------------------------
489 e337de97 Michael Hanselmann
490 e337de97 Michael Hanselmann
  @staticmethod
491 e337de97 Michael Hanselmann
  def perspective_storage_list(params):
492 e337de97 Michael Hanselmann
    """Get list of storage units.
493 e337de97 Michael Hanselmann

494 e337de97 Michael Hanselmann
    """
495 e337de97 Michael Hanselmann
    (su_name, su_args, name, fields) = params
496 e337de97 Michael Hanselmann
    return storage.GetStorage(su_name, *su_args).List(name, fields)
497 e337de97 Michael Hanselmann
498 8979196a Michael Hanselmann
  @staticmethod
499 8979196a Michael Hanselmann
  def perspective_storage_modify(params):
500 8979196a Michael Hanselmann
    """Modify a storage unit.
501 8979196a Michael Hanselmann

502 8979196a Michael Hanselmann
    """
503 8979196a Michael Hanselmann
    (su_name, su_args, name, changes) = params
504 8979196a Michael Hanselmann
    return storage.GetStorage(su_name, *su_args).Modify(name, changes)
505 8979196a Michael Hanselmann
506 637b8d7e Michael Hanselmann
  @staticmethod
507 637b8d7e Michael Hanselmann
  def perspective_storage_execute(params):
508 637b8d7e Michael Hanselmann
    """Execute an operation on a storage unit.
509 637b8d7e Michael Hanselmann

510 637b8d7e Michael Hanselmann
    """
511 637b8d7e Michael Hanselmann
    (su_name, su_args, name, op) = params
512 637b8d7e Michael Hanselmann
    return storage.GetStorage(su_name, *su_args).Execute(name, op)
513 637b8d7e Michael Hanselmann
514 a8083063 Iustin Pop
  # bridge  --------------------------
515 a8083063 Iustin Pop
516 3ecf6786 Iustin Pop
  @staticmethod
517 3ecf6786 Iustin Pop
  def perspective_bridges_exist(params):
518 3ecf6786 Iustin Pop
    """Check if all bridges given exist on this node.
519 3ecf6786 Iustin Pop

520 3ecf6786 Iustin Pop
    """
521 a8083063 Iustin Pop
    bridges_list = params[0]
522 a8083063 Iustin Pop
    return backend.BridgesExist(bridges_list)
523 a8083063 Iustin Pop
524 a8083063 Iustin Pop
  # instance  --------------------------
525 a8083063 Iustin Pop
526 3ecf6786 Iustin Pop
  @staticmethod
527 3ecf6786 Iustin Pop
  def perspective_instance_os_add(params):
528 3ecf6786 Iustin Pop
    """Install an OS on a given instance.
529 3ecf6786 Iustin Pop

530 3ecf6786 Iustin Pop
    """
531 d15a9ad3 Guido Trotter
    inst_s = params[0]
532 319856a9 Michael Hanselmann
    inst = objects.Instance.FromDict(inst_s)
533 e557bae9 Guido Trotter
    reinstall = params[1]
534 4a0e011f Iustin Pop
    debug = params[2]
535 4a0e011f Iustin Pop
    return backend.InstanceOsAdd(inst, reinstall, debug)
536 a8083063 Iustin Pop
537 3ecf6786 Iustin Pop
  @staticmethod
538 decd5f45 Iustin Pop
  def perspective_instance_run_rename(params):
539 decd5f45 Iustin Pop
    """Runs the OS rename script for an instance.
540 decd5f45 Iustin Pop

541 decd5f45 Iustin Pop
    """
542 4a0e011f Iustin Pop
    inst_s, old_name, debug = params
543 319856a9 Michael Hanselmann
    inst = objects.Instance.FromDict(inst_s)
544 4a0e011f Iustin Pop
    return backend.RunRenameInstance(inst, old_name, debug)
545 decd5f45 Iustin Pop
546 decd5f45 Iustin Pop
  @staticmethod
547 3ecf6786 Iustin Pop
  def perspective_instance_shutdown(params):
548 3ecf6786 Iustin Pop
    """Shutdown an instance.
549 3ecf6786 Iustin Pop

550 3ecf6786 Iustin Pop
    """
551 319856a9 Michael Hanselmann
    instance = objects.Instance.FromDict(params[0])
552 6263189c Guido Trotter
    timeout = params[1]
553 6263189c Guido Trotter
    return backend.InstanceShutdown(instance, timeout)
554 a8083063 Iustin Pop
555 3ecf6786 Iustin Pop
  @staticmethod
556 3ecf6786 Iustin Pop
  def perspective_instance_start(params):
557 3ecf6786 Iustin Pop
    """Start an instance.
558 3ecf6786 Iustin Pop

559 3ecf6786 Iustin Pop
    """
560 323f9095 Stephen Shirley
    (instance_name, startup_paused) = params
561 323f9095 Stephen Shirley
    instance = objects.Instance.FromDict(instance_name)
562 323f9095 Stephen Shirley
    return backend.StartInstance(instance, startup_paused)
563 a8083063 Iustin Pop
564 3ecf6786 Iustin Pop
  @staticmethod
565 6906a9d8 Guido Trotter
  def perspective_migration_info(params):
566 6906a9d8 Guido Trotter
    """Gather information about an instance to be migrated.
567 6906a9d8 Guido Trotter

568 6906a9d8 Guido Trotter
    """
569 6906a9d8 Guido Trotter
    instance = objects.Instance.FromDict(params[0])
570 6906a9d8 Guido Trotter
    return backend.MigrationInfo(instance)
571 6906a9d8 Guido Trotter
572 6906a9d8 Guido Trotter
  @staticmethod
573 6906a9d8 Guido Trotter
  def perspective_accept_instance(params):
574 6906a9d8 Guido Trotter
    """Prepare the node to accept an instance.
575 6906a9d8 Guido Trotter

576 6906a9d8 Guido Trotter
    """
577 6906a9d8 Guido Trotter
    instance, info, target = params
578 6906a9d8 Guido Trotter
    instance = objects.Instance.FromDict(instance)
579 6906a9d8 Guido Trotter
    return backend.AcceptInstance(instance, info, target)
580 6906a9d8 Guido Trotter
581 6906a9d8 Guido Trotter
  @staticmethod
582 6a1434d7 Andrea Spadaccini
  def perspective_instance_finalize_migration_dst(params):
583 6a1434d7 Andrea Spadaccini
    """Finalize the instance migration on the destination node.
584 6906a9d8 Guido Trotter

585 6906a9d8 Guido Trotter
    """
586 6906a9d8 Guido Trotter
    instance, info, success = params
587 6906a9d8 Guido Trotter
    instance = objects.Instance.FromDict(instance)
588 6a1434d7 Andrea Spadaccini
    return backend.FinalizeMigrationDst(instance, info, success)
589 6906a9d8 Guido Trotter
590 6906a9d8 Guido Trotter
  @staticmethod
591 2a10865c Iustin Pop
  def perspective_instance_migrate(params):
592 2a10865c Iustin Pop
    """Migrates an instance.
593 2a10865c Iustin Pop

594 2a10865c Iustin Pop
    """
595 2a10865c Iustin Pop
    instance, target, live = params
596 9f0e6b37 Iustin Pop
    instance = objects.Instance.FromDict(instance)
597 2a10865c Iustin Pop
    return backend.MigrateInstance(instance, target, live)
598 2a10865c Iustin Pop
599 2a10865c Iustin Pop
  @staticmethod
600 6a1434d7 Andrea Spadaccini
  def perspective_instance_finalize_migration_src(params):
601 6a1434d7 Andrea Spadaccini
    """Finalize the instance migration on the source node.
602 6a1434d7 Andrea Spadaccini

603 6a1434d7 Andrea Spadaccini
    """
604 6a1434d7 Andrea Spadaccini
    instance, success, live = params
605 6a1434d7 Andrea Spadaccini
    instance = objects.Instance.FromDict(instance)
606 6a1434d7 Andrea Spadaccini
    return backend.FinalizeMigrationSource(instance, success, live)
607 6a1434d7 Andrea Spadaccini
608 6a1434d7 Andrea Spadaccini
  @staticmethod
609 6a1434d7 Andrea Spadaccini
  def perspective_instance_get_migration_status(params):
610 6a1434d7 Andrea Spadaccini
    """Reports migration status.
611 6a1434d7 Andrea Spadaccini

612 6a1434d7 Andrea Spadaccini
    """
613 6a1434d7 Andrea Spadaccini
    instance = objects.Instance.FromDict(params[0])
614 6a1434d7 Andrea Spadaccini
    return backend.GetMigrationStatus(instance).ToDict()
615 6a1434d7 Andrea Spadaccini
616 6a1434d7 Andrea Spadaccini
  @staticmethod
617 007a2f3e Alexander Schreiber
  def perspective_instance_reboot(params):
618 007a2f3e Alexander Schreiber
    """Reboot an instance.
619 007a2f3e Alexander Schreiber

620 007a2f3e Alexander Schreiber
    """
621 007a2f3e Alexander Schreiber
    instance = objects.Instance.FromDict(params[0])
622 007a2f3e Alexander Schreiber
    reboot_type = params[1]
623 17c3f802 Guido Trotter
    shutdown_timeout = params[2]
624 17c3f802 Guido Trotter
    return backend.InstanceReboot(instance, reboot_type, shutdown_timeout)
625 007a2f3e Alexander Schreiber
626 007a2f3e Alexander Schreiber
  @staticmethod
627 3ecf6786 Iustin Pop
  def perspective_instance_info(params):
628 3ecf6786 Iustin Pop
    """Query instance information.
629 3ecf6786 Iustin Pop

630 3ecf6786 Iustin Pop
    """
631 16ad1a83 Iustin Pop
    return backend.GetInstanceInfo(params[0], params[1])
632 a8083063 Iustin Pop
633 3ecf6786 Iustin Pop
  @staticmethod
634 56e7640c Iustin Pop
  def perspective_instance_migratable(params):
635 56e7640c Iustin Pop
    """Query whether the specified instance can be migrated.
636 56e7640c Iustin Pop

637 56e7640c Iustin Pop
    """
638 56e7640c Iustin Pop
    instance = objects.Instance.FromDict(params[0])
639 56e7640c Iustin Pop
    return backend.GetInstanceMigratable(instance)
640 56e7640c Iustin Pop
641 56e7640c Iustin Pop
  @staticmethod
642 3ecf6786 Iustin Pop
  def perspective_all_instances_info(params):
643 3ecf6786 Iustin Pop
    """Query information about all instances.
644 3ecf6786 Iustin Pop

645 3ecf6786 Iustin Pop
    """
646 e69d05fd Iustin Pop
    return backend.GetAllInstancesInfo(params[0])
647 a8083063 Iustin Pop
648 3ecf6786 Iustin Pop
  @staticmethod
649 3ecf6786 Iustin Pop
  def perspective_instance_list(params):
650 3ecf6786 Iustin Pop
    """Query the list of running instances.
651 3ecf6786 Iustin Pop

652 3ecf6786 Iustin Pop
    """
653 c26a6bd2 Iustin Pop
    return backend.GetInstanceList(params[0])
654 a8083063 Iustin Pop
655 a8083063 Iustin Pop
  # node --------------------------
656 a8083063 Iustin Pop
657 3ecf6786 Iustin Pop
  @staticmethod
658 caad16e2 Iustin Pop
  def perspective_node_has_ip_address(params):
659 caad16e2 Iustin Pop
    """Checks if a node has the given ip address.
660 caad16e2 Iustin Pop

661 caad16e2 Iustin Pop
    """
662 8b312c1d Manuel Franceschini
    return netutils.IPAddress.Own(params[0])
663 caad16e2 Iustin Pop
664 caad16e2 Iustin Pop
  @staticmethod
665 3ecf6786 Iustin Pop
  def perspective_node_info(params):
666 3ecf6786 Iustin Pop
    """Query node information.
667 3ecf6786 Iustin Pop

668 3ecf6786 Iustin Pop
    """
669 e69d05fd Iustin Pop
    vgname, hypervisor_type = params
670 e69d05fd Iustin Pop
    return backend.GetNodeInfo(vgname, hypervisor_type)
671 a8083063 Iustin Pop
672 3ecf6786 Iustin Pop
  @staticmethod
673 19ddc57a Renรฉ Nussbaumer
  def perspective_etc_hosts_modify(params):
674 19ddc57a Renรฉ Nussbaumer
    """Modify a node entry in /etc/hosts.
675 19ddc57a Renรฉ Nussbaumer

676 19ddc57a Renรฉ Nussbaumer
    """
677 19ddc57a Renรฉ Nussbaumer
    backend.EtcHostsModify(params[0], params[1], params[2])
678 19ddc57a Renรฉ Nussbaumer
679 19ddc57a Renรฉ Nussbaumer
    return True
680 19ddc57a Renรฉ Nussbaumer
681 19ddc57a Renรฉ Nussbaumer
  @staticmethod
682 3ecf6786 Iustin Pop
  def perspective_node_verify(params):
683 3ecf6786 Iustin Pop
    """Run a verify sequence on this node.
684 3ecf6786 Iustin Pop

685 3ecf6786 Iustin Pop
    """
686 62c9ec92 Iustin Pop
    return backend.VerifyNode(params[0], params[1])
687 a8083063 Iustin Pop
688 3ecf6786 Iustin Pop
  @staticmethod
689 fb460cf7 Andrea Spadaccini
  def perspective_node_start_master_daemons(params):
690 fb460cf7 Andrea Spadaccini
    """Start the master daemons on this node.
691 3ecf6786 Iustin Pop

692 3ecf6786 Iustin Pop
    """
693 fb460cf7 Andrea Spadaccini
    return backend.StartMasterDaemons(params[0])
694 fb460cf7 Andrea Spadaccini
695 fb460cf7 Andrea Spadaccini
  @staticmethod
696 fb460cf7 Andrea Spadaccini
  def perspective_node_activate_master_ip(params):
697 fb460cf7 Andrea Spadaccini
    """Activate the master IP on this node.
698 fb460cf7 Andrea Spadaccini

699 fb460cf7 Andrea Spadaccini
    """
700 c79198a0 Andrea Spadaccini
    master_params = objects.MasterNetworkParameters.FromDict(params[0])
701 57c7bc57 Andrea Spadaccini
    return backend.ActivateMasterIp(master_params, params[1])
702 fb460cf7 Andrea Spadaccini
703 fb460cf7 Andrea Spadaccini
  @staticmethod
704 fb460cf7 Andrea Spadaccini
  def perspective_node_deactivate_master_ip(params):
705 fb460cf7 Andrea Spadaccini
    """Deactivate the master IP on this node.
706 fb460cf7 Andrea Spadaccini

707 fb460cf7 Andrea Spadaccini
    """
708 c79198a0 Andrea Spadaccini
    master_params = objects.MasterNetworkParameters.FromDict(params[0])
709 57c7bc57 Andrea Spadaccini
    return backend.DeactivateMasterIp(master_params, params[1])
710 a8083063 Iustin Pop
711 3ecf6786 Iustin Pop
  @staticmethod
712 3ecf6786 Iustin Pop
  def perspective_node_stop_master(params):
713 7c74bbe0 Andrea Spadaccini
    """Stops master daemons on this node.
714 3ecf6786 Iustin Pop

715 3ecf6786 Iustin Pop
    """
716 fb460cf7 Andrea Spadaccini
    return backend.StopMasterDaemons()
717 a8083063 Iustin Pop
718 3ecf6786 Iustin Pop
  @staticmethod
719 5a8648eb Andrea Spadaccini
  def perspective_node_change_master_netmask(params):
720 5a8648eb Andrea Spadaccini
    """Change the master IP netmask.
721 5a8648eb Andrea Spadaccini

722 5a8648eb Andrea Spadaccini
    """
723 41e079ce Andrea Spadaccini
    return backend.ChangeMasterNetmask(params[0], params[1], params[2],
724 41e079ce Andrea Spadaccini
                                       params[3])
725 5a8648eb Andrea Spadaccini
726 5a8648eb Andrea Spadaccini
  @staticmethod
727 3ecf6786 Iustin Pop
  def perspective_node_leave_cluster(params):
728 3ecf6786 Iustin Pop
    """Cleanup after leaving a cluster.
729 3ecf6786 Iustin Pop

730 3ecf6786 Iustin Pop
    """
731 b989b9d9 Ken Wehr
    return backend.LeaveCluster(params[0])
732 a8083063 Iustin Pop
733 3ecf6786 Iustin Pop
  @staticmethod
734 3ecf6786 Iustin Pop
  def perspective_node_volumes(params):
735 3ecf6786 Iustin Pop
    """Query the list of all logical volume groups.
736 3ecf6786 Iustin Pop

737 3ecf6786 Iustin Pop
    """
738 dcb93971 Michael Hanselmann
    return backend.NodeVolumes()
739 dcb93971 Michael Hanselmann
740 56aa9fd5 Iustin Pop
  @staticmethod
741 56aa9fd5 Iustin Pop
  def perspective_node_demote_from_mc(params):
742 56aa9fd5 Iustin Pop
    """Demote a node from the master candidate role.
743 56aa9fd5 Iustin Pop

744 56aa9fd5 Iustin Pop
    """
745 56aa9fd5 Iustin Pop
    return backend.DemoteFromMC()
746 56aa9fd5 Iustin Pop
747 f5118ade Iustin Pop
  @staticmethod
748 f5118ade Iustin Pop
  def perspective_node_powercycle(params):
749 f5118ade Iustin Pop
    """Tries to powercycle the nod.
750 f5118ade Iustin Pop

751 f5118ade Iustin Pop
    """
752 f5118ade Iustin Pop
    hypervisor_type = params[0]
753 f5118ade Iustin Pop
    return backend.PowercycleNode(hypervisor_type)
754 f5118ade Iustin Pop
755 a8083063 Iustin Pop
  # cluster --------------------------
756 a8083063 Iustin Pop
757 3ecf6786 Iustin Pop
  @staticmethod
758 3ecf6786 Iustin Pop
  def perspective_version(params):
759 3ecf6786 Iustin Pop
    """Query version information.
760 3ecf6786 Iustin Pop

761 3ecf6786 Iustin Pop
    """
762 c26a6bd2 Iustin Pop
    return constants.PROTOCOL_VERSION
763 a8083063 Iustin Pop
764 3ecf6786 Iustin Pop
  @staticmethod
765 3ecf6786 Iustin Pop
  def perspective_upload_file(params):
766 3ecf6786 Iustin Pop
    """Upload a file.
767 3ecf6786 Iustin Pop

768 3ecf6786 Iustin Pop
    Note that the backend implementation imposes strict rules on which
769 3ecf6786 Iustin Pop
    files are accepted.
770 3ecf6786 Iustin Pop

771 3ecf6786 Iustin Pop
    """
772 415a7304 Michael Hanselmann
    return backend.UploadFile(*(params[0]))
773 a8083063 Iustin Pop
774 4e071d3b Iustin Pop
  @staticmethod
775 4e071d3b Iustin Pop
  def perspective_master_info(params):
776 4e071d3b Iustin Pop
    """Query master information.
777 4e071d3b Iustin Pop

778 4e071d3b Iustin Pop
    """
779 4e071d3b Iustin Pop
    return backend.GetMasterInfo()
780 a8083063 Iustin Pop
781 6ddc95ec Michael Hanselmann
  @staticmethod
782 4f6014d4 Renรฉ Nussbaumer
  def perspective_run_oob(params):
783 4f6014d4 Renรฉ Nussbaumer
    """Runs oob on node.
784 4f6014d4 Renรฉ Nussbaumer

785 4f6014d4 Renรฉ Nussbaumer
    """
786 1aa88d95 Renรฉ Nussbaumer
    output = backend.RunOob(params[0], params[1], params[2], params[3])
787 1aa88d95 Renรฉ Nussbaumer
    if output:
788 1aa88d95 Renรฉ Nussbaumer
      result = serializer.LoadJson(output)
789 1aa88d95 Renรฉ Nussbaumer
    else:
790 1aa88d95 Renรฉ Nussbaumer
      result = None
791 1aa88d95 Renรฉ Nussbaumer
    return result
792 4f6014d4 Renรฉ Nussbaumer
793 4f6014d4 Renรฉ Nussbaumer
  @staticmethod
794 6ddc95ec Michael Hanselmann
  def perspective_write_ssconf_files(params):
795 6ddc95ec Michael Hanselmann
    """Write ssconf files.
796 6ddc95ec Michael Hanselmann

797 6ddc95ec Michael Hanselmann
    """
798 03d1dba2 Michael Hanselmann
    (values,) = params
799 03d1dba2 Michael Hanselmann
    return backend.WriteSsconfFiles(values)
800 6ddc95ec Michael Hanselmann
801 a8083063 Iustin Pop
  # os -----------------------
802 a8083063 Iustin Pop
803 3ecf6786 Iustin Pop
  @staticmethod
804 3ecf6786 Iustin Pop
  def perspective_os_diagnose(params):
805 3ecf6786 Iustin Pop
    """Query detailed information about existing OSes.
806 3ecf6786 Iustin Pop

807 3ecf6786 Iustin Pop
    """
808 255dcebd Iustin Pop
    return backend.DiagnoseOS()
809 a8083063 Iustin Pop
810 3ecf6786 Iustin Pop
  @staticmethod
811 3ecf6786 Iustin Pop
  def perspective_os_get(params):
812 3ecf6786 Iustin Pop
    """Query information about a given OS.
813 3ecf6786 Iustin Pop

814 3ecf6786 Iustin Pop
    """
815 a8083063 Iustin Pop
    name = params[0]
816 255dcebd Iustin Pop
    os_obj = backend.OSFromDisk(name)
817 c26a6bd2 Iustin Pop
    return os_obj.ToDict()
818 a8083063 Iustin Pop
819 acd9ff9e Iustin Pop
  @staticmethod
820 acd9ff9e Iustin Pop
  def perspective_os_validate(params):
821 acd9ff9e Iustin Pop
    """Run a given OS' validation routine.
822 acd9ff9e Iustin Pop

823 acd9ff9e Iustin Pop
    """
824 acd9ff9e Iustin Pop
    required, name, checks, params = params
825 acd9ff9e Iustin Pop
    return backend.ValidateOS(required, name, checks, params)
826 acd9ff9e Iustin Pop
827 a8083063 Iustin Pop
  # hooks -----------------------
828 a8083063 Iustin Pop
829 3ecf6786 Iustin Pop
  @staticmethod
830 3ecf6786 Iustin Pop
  def perspective_hooks_runner(params):
831 3ecf6786 Iustin Pop
    """Run hook scripts.
832 3ecf6786 Iustin Pop

833 3ecf6786 Iustin Pop
    """
834 a8083063 Iustin Pop
    hpath, phase, env = params
835 a8083063 Iustin Pop
    hr = backend.HooksRunner()
836 a8083063 Iustin Pop
    return hr.RunHooks(hpath, phase, env)
837 a8083063 Iustin Pop
838 8d528b7c Iustin Pop
  # iallocator -----------------
839 8d528b7c Iustin Pop
840 8d528b7c Iustin Pop
  @staticmethod
841 8d528b7c Iustin Pop
  def perspective_iallocator_runner(params):
842 8d528b7c Iustin Pop
    """Run an iallocator script.
843 8d528b7c Iustin Pop

844 8d528b7c Iustin Pop
    """
845 8d528b7c Iustin Pop
    name, idata = params
846 8d528b7c Iustin Pop
    iar = backend.IAllocatorRunner()
847 8d528b7c Iustin Pop
    return iar.Run(name, idata)
848 8d528b7c Iustin Pop
849 06009e27 Iustin Pop
  # test -----------------------
850 06009e27 Iustin Pop
851 06009e27 Iustin Pop
  @staticmethod
852 06009e27 Iustin Pop
  def perspective_test_delay(params):
853 06009e27 Iustin Pop
    """Run test delay.
854 06009e27 Iustin Pop

855 06009e27 Iustin Pop
    """
856 06009e27 Iustin Pop
    duration = params[0]
857 c26a6bd2 Iustin Pop
    status, rval = utils.TestDelay(duration)
858 c26a6bd2 Iustin Pop
    if not status:
859 c26a6bd2 Iustin Pop
      raise backend.RPCFail(rval)
860 c26a6bd2 Iustin Pop
    return rval
861 06009e27 Iustin Pop
862 4e071d3b Iustin Pop
  # file storage ---------------
863 4e071d3b Iustin Pop
864 a5d7fb43 Manuel Franceschini
  @staticmethod
865 a5d7fb43 Manuel Franceschini
  def perspective_file_storage_dir_create(params):
866 a5d7fb43 Manuel Franceschini
    """Create the file storage directory.
867 a5d7fb43 Manuel Franceschini

868 a5d7fb43 Manuel Franceschini
    """
869 a5d7fb43 Manuel Franceschini
    file_storage_dir = params[0]
870 a5d7fb43 Manuel Franceschini
    return backend.CreateFileStorageDir(file_storage_dir)
871 a5d7fb43 Manuel Franceschini
872 a5d7fb43 Manuel Franceschini
  @staticmethod
873 a5d7fb43 Manuel Franceschini
  def perspective_file_storage_dir_remove(params):
874 a5d7fb43 Manuel Franceschini
    """Remove the file storage directory.
875 a5d7fb43 Manuel Franceschini

876 a5d7fb43 Manuel Franceschini
    """
877 a5d7fb43 Manuel Franceschini
    file_storage_dir = params[0]
878 a5d7fb43 Manuel Franceschini
    return backend.RemoveFileStorageDir(file_storage_dir)
879 a5d7fb43 Manuel Franceschini
880 a5d7fb43 Manuel Franceschini
  @staticmethod
881 a5d7fb43 Manuel Franceschini
  def perspective_file_storage_dir_rename(params):
882 a5d7fb43 Manuel Franceschini
    """Rename the file storage directory.
883 a5d7fb43 Manuel Franceschini

884 a5d7fb43 Manuel Franceschini
    """
885 a5d7fb43 Manuel Franceschini
    old_file_storage_dir = params[0]
886 a5d7fb43 Manuel Franceschini
    new_file_storage_dir = params[1]
887 a5d7fb43 Manuel Franceschini
    return backend.RenameFileStorageDir(old_file_storage_dir,
888 a5d7fb43 Manuel Franceschini
                                        new_file_storage_dir)
889 a5d7fb43 Manuel Franceschini
890 4e071d3b Iustin Pop
  # jobs ------------------------
891 4e071d3b Iustin Pop
892 ca52cdeb Michael Hanselmann
  @staticmethod
893 7f30777b Michael Hanselmann
  @_RequireJobQueueLock
894 ca52cdeb Michael Hanselmann
  def perspective_jobqueue_update(params):
895 ca52cdeb Michael Hanselmann
    """Update job queue.
896 ca52cdeb Michael Hanselmann

897 ca52cdeb Michael Hanselmann
    """
898 ca52cdeb Michael Hanselmann
    (file_name, content) = params
899 7f30777b Michael Hanselmann
    return backend.JobQueueUpdate(file_name, content)
900 ca52cdeb Michael Hanselmann
901 ca52cdeb Michael Hanselmann
  @staticmethod
902 f1f3f45c Michael Hanselmann
  @_RequireJobQueueLock
903 ca52cdeb Michael Hanselmann
  def perspective_jobqueue_purge(params):
904 ca52cdeb Michael Hanselmann
    """Purge job queue.
905 ca52cdeb Michael Hanselmann

906 ca52cdeb Michael Hanselmann
    """
907 ca52cdeb Michael Hanselmann
    return backend.JobQueuePurge()
908 ca52cdeb Michael Hanselmann
909 af5ebcb1 Michael Hanselmann
  @staticmethod
910 af5ebcb1 Michael Hanselmann
  @_RequireJobQueueLock
911 af5ebcb1 Michael Hanselmann
  def perspective_jobqueue_rename(params):
912 af5ebcb1 Michael Hanselmann
    """Rename a job queue file.
913 af5ebcb1 Michael Hanselmann

914 af5ebcb1 Michael Hanselmann
    """
915 dd875d32 Michael Hanselmann
    # TODO: What if a file fails to rename?
916 fb1ffbca Michael Hanselmann
    return [backend.JobQueueRename(old, new) for old, new in params[0]]
917 af5ebcb1 Michael Hanselmann
918 6217e295 Iustin Pop
  # hypervisor ---------------
919 6217e295 Iustin Pop
920 6217e295 Iustin Pop
  @staticmethod
921 6217e295 Iustin Pop
  def perspective_hypervisor_validate_params(params):
922 6217e295 Iustin Pop
    """Validate the hypervisor parameters.
923 6217e295 Iustin Pop

924 6217e295 Iustin Pop
    """
925 6217e295 Iustin Pop
    (hvname, hvparams) = params
926 6217e295 Iustin Pop
    return backend.ValidateHVParams(hvname, hvparams)
927 6217e295 Iustin Pop
928 f942a838 Michael Hanselmann
  # Crypto
929 f942a838 Michael Hanselmann
930 f942a838 Michael Hanselmann
  @staticmethod
931 ef40fbfb Michael Hanselmann
  def perspective_x509_cert_create(params):
932 f942a838 Michael Hanselmann
    """Creates a new X509 certificate for SSL/TLS.
933 f942a838 Michael Hanselmann

934 f942a838 Michael Hanselmann
    """
935 f942a838 Michael Hanselmann
    (validity, ) = params
936 f942a838 Michael Hanselmann
    return backend.CreateX509Certificate(validity)
937 f942a838 Michael Hanselmann
938 f942a838 Michael Hanselmann
  @staticmethod
939 ef40fbfb Michael Hanselmann
  def perspective_x509_cert_remove(params):
940 f942a838 Michael Hanselmann
    """Removes a X509 certificate.
941 f942a838 Michael Hanselmann

942 f942a838 Michael Hanselmann
    """
943 f942a838 Michael Hanselmann
    (name, ) = params
944 f942a838 Michael Hanselmann
    return backend.RemoveX509Certificate(name)
945 f942a838 Michael Hanselmann
946 1651d116 Michael Hanselmann
  # Import and export
947 1651d116 Michael Hanselmann
948 1651d116 Michael Hanselmann
  @staticmethod
949 ef40fbfb Michael Hanselmann
  def perspective_import_start(params):
950 1651d116 Michael Hanselmann
    """Starts an import daemon.
951 1651d116 Michael Hanselmann

952 1651d116 Michael Hanselmann
    """
953 b8c160c1 Michael Hanselmann
    (opts_s, instance, component, (dest, dest_args)) = params
954 eb630f50 Michael Hanselmann
955 eb630f50 Michael Hanselmann
    opts = objects.ImportExportOptions.FromDict(opts_s)
956 eb630f50 Michael Hanselmann
957 eb630f50 Michael Hanselmann
    return backend.StartImportExportDaemon(constants.IEM_IMPORT, opts,
958 1651d116 Michael Hanselmann
                                           None, None,
959 1651d116 Michael Hanselmann
                                           objects.Instance.FromDict(instance),
960 6613661a Iustin Pop
                                           component, dest,
961 1651d116 Michael Hanselmann
                                           _DecodeImportExportIO(dest,
962 1651d116 Michael Hanselmann
                                                                 dest_args))
963 eb630f50 Michael Hanselmann
964 1651d116 Michael Hanselmann
  @staticmethod
965 ef40fbfb Michael Hanselmann
  def perspective_export_start(params):
966 1651d116 Michael Hanselmann
    """Starts an export daemon.
967 1651d116 Michael Hanselmann

968 1651d116 Michael Hanselmann
    """
969 b8c160c1 Michael Hanselmann
    (opts_s, host, port, instance, component, (source, source_args)) = params
970 eb630f50 Michael Hanselmann
971 eb630f50 Michael Hanselmann
    opts = objects.ImportExportOptions.FromDict(opts_s)
972 eb630f50 Michael Hanselmann
973 eb630f50 Michael Hanselmann
    return backend.StartImportExportDaemon(constants.IEM_EXPORT, opts,
974 1651d116 Michael Hanselmann
                                           host, port,
975 1651d116 Michael Hanselmann
                                           objects.Instance.FromDict(instance),
976 6613661a Iustin Pop
                                           component, source,
977 1651d116 Michael Hanselmann
                                           _DecodeImportExportIO(source,
978 1651d116 Michael Hanselmann
                                                                 source_args))
979 1651d116 Michael Hanselmann
980 1651d116 Michael Hanselmann
  @staticmethod
981 ef40fbfb Michael Hanselmann
  def perspective_impexp_status(params):
982 1651d116 Michael Hanselmann
    """Retrieves the status of an import or export daemon.
983 1651d116 Michael Hanselmann

984 1651d116 Michael Hanselmann
    """
985 1651d116 Michael Hanselmann
    return backend.GetImportExportStatus(params[0])
986 1651d116 Michael Hanselmann
987 1651d116 Michael Hanselmann
  @staticmethod
988 f81c4737 Michael Hanselmann
  def perspective_impexp_abort(params):
989 f81c4737 Michael Hanselmann
    """Aborts an import or export.
990 f81c4737 Michael Hanselmann

991 f81c4737 Michael Hanselmann
    """
992 f81c4737 Michael Hanselmann
    return backend.AbortImportExport(params[0])
993 f81c4737 Michael Hanselmann
994 f81c4737 Michael Hanselmann
  @staticmethod
995 ef40fbfb Michael Hanselmann
  def perspective_impexp_cleanup(params):
996 1651d116 Michael Hanselmann
    """Cleans up after an import or export.
997 1651d116 Michael Hanselmann

998 1651d116 Michael Hanselmann
    """
999 1651d116 Michael Hanselmann
    return backend.CleanupImportExport(params[0])
1000 1651d116 Michael Hanselmann
1001 a8083063 Iustin Pop
1002 f93427cd Iustin Pop
def CheckNoded(_, args):
1003 f93427cd Iustin Pop
  """Initial checks whether to run or exit with a failure.
1004 f93427cd Iustin Pop

1005 f93427cd Iustin Pop
  """
1006 f93427cd Iustin Pop
  if args: # noded doesn't take any arguments
1007 f93427cd Iustin Pop
    print >> sys.stderr, ("Usage: %s [-f] [-d] [-p port] [-b ADDRESS]" %
1008 f93427cd Iustin Pop
                          sys.argv[0])
1009 f93427cd Iustin Pop
    sys.exit(constants.EXIT_FAILURE)
1010 f01738fc Iustin Pop
  try:
1011 f01738fc Iustin Pop
    codecs.lookup("string-escape")
1012 f01738fc Iustin Pop
  except LookupError:
1013 f01738fc Iustin Pop
    print >> sys.stderr, ("Can't load the string-escape code which is part"
1014 f01738fc Iustin Pop
                          " of the Python installation. Is your installation"
1015 f01738fc Iustin Pop
                          " complete/correct? Aborting.")
1016 f01738fc Iustin Pop
    sys.exit(constants.EXIT_FAILURE)
1017 f93427cd Iustin Pop
1018 f93427cd Iustin Pop
1019 3ee53f1f Iustin Pop
def PrepNoded(options, _):
1020 3ee53f1f Iustin Pop
  """Preparation node daemon function, executed with the PID file held.
1021 3ecf6786 Iustin Pop

1022 3ecf6786 Iustin Pop
  """
1023 bebf68d3 Guido Trotter
  if options.mlock:
1024 bebf68d3 Guido Trotter
    request_executor_class = MlockallRequestExecutor
1025 4c32a8bd Luca Bigliardi
    try:
1026 4c32a8bd Luca Bigliardi
      utils.Mlockall()
1027 4c32a8bd Luca Bigliardi
    except errors.NoCtypesError:
1028 4c32a8bd Luca Bigliardi
      logging.warning("Cannot set memory lock, ctypes module not found")
1029 4c32a8bd Luca Bigliardi
      request_executor_class = http.server.HttpServerRequestExecutor
1030 bebf68d3 Guido Trotter
  else:
1031 bebf68d3 Guido Trotter
    request_executor_class = http.server.HttpServerRequestExecutor
1032 02bea2fc Luca Bigliardi
1033 04ccf5e9 Guido Trotter
  # Read SSL certificate
1034 3b1b0cb6 Guido Trotter
  if options.ssl:
1035 3b1b0cb6 Guido Trotter
    ssl_params = http.HttpSslParams(ssl_key_path=options.ssl_key,
1036 3b1b0cb6 Guido Trotter
                                    ssl_cert_path=options.ssl_cert)
1037 3b1b0cb6 Guido Trotter
  else:
1038 3b1b0cb6 Guido Trotter
    ssl_params = None
1039 7d88772a Iustin Pop
1040 81198f6e Iustin Pop
  err = _PrepareQueueLock()
1041 81198f6e Iustin Pop
  if err is not None:
1042 81198f6e Iustin Pop
    # this might be some kind of file-system/permission error; while
1043 81198f6e Iustin Pop
    # this breaks the job queue functionality, we shouldn't prevent
1044 81198f6e Iustin Pop
    # startup of the whole node daemon because of this
1045 81198f6e Iustin Pop
    logging.critical("Can't init/verify the queue, proceeding anyway: %s", err)
1046 7d88772a Iustin Pop
1047 04ccf5e9 Guido Trotter
  mainloop = daemon.Mainloop()
1048 04ccf5e9 Guido Trotter
  server = NodeHttpServer(mainloop, options.bind_address, options.port,
1049 38b77287 Luca Bigliardi
                          ssl_params=ssl_params, ssl_verify_peer=True,
1050 bebf68d3 Guido Trotter
                          request_executor_class=request_executor_class)
1051 04ccf5e9 Guido Trotter
  server.Start()
1052 3ee53f1f Iustin Pop
  return (mainloop, server)
1053 3ee53f1f Iustin Pop
1054 5119f2ec Michael Hanselmann
1055 b459a848 Andrea Spadaccini
def ExecNoded(options, args, prep_data): # pylint: disable=W0613
1056 3ee53f1f Iustin Pop
  """Main node daemon function, executed with the PID file held.
1057 3ee53f1f Iustin Pop

1058 3ee53f1f Iustin Pop
  """
1059 3ee53f1f Iustin Pop
  (mainloop, server) = prep_data
1060 04ccf5e9 Guido Trotter
  try:
1061 04ccf5e9 Guido Trotter
    mainloop.Run()
1062 04ccf5e9 Guido Trotter
  finally:
1063 04ccf5e9 Guido Trotter
    server.Stop()
1064 a8083063 Iustin Pop
1065 a8083063 Iustin Pop
1066 5119f2ec Michael Hanselmann
def Main():
1067 04ccf5e9 Guido Trotter
  """Main function for the node daemon.
1068 04ccf5e9 Guido Trotter

1069 04ccf5e9 Guido Trotter
  """
1070 04ccf5e9 Guido Trotter
  parser = OptionParser(description="Ganeti node daemon",
1071 04ccf5e9 Guido Trotter
                        usage="%prog [-f] [-d] [-p port] [-b ADDRESS]",
1072 04ccf5e9 Guido Trotter
                        version="%%prog (ganeti) %s" %
1073 04ccf5e9 Guido Trotter
                        constants.RELEASE_VERSION)
1074 bebf68d3 Guido Trotter
  parser.add_option("--no-mlock", dest="mlock",
1075 bebf68d3 Guido Trotter
                    help="Do not mlock the node memory in ram",
1076 bebf68d3 Guido Trotter
                    default=True, action="store_false")
1077 bebf68d3 Guido Trotter
1078 3ee53f1f Iustin Pop
  daemon.GenericMain(constants.NODED, parser, CheckNoded, PrepNoded, ExecNoded,
1079 084aba47 Michael Hanselmann
                     default_ssl_cert=constants.NODED_CERT_FILE,
1080 1c54156d Luca Bigliardi
                     default_ssl_key=constants.NODED_CERT_FILE,
1081 565083ef Luca Bigliardi
                     console_logging=True)