Statistics
| Branch: | Tag: | Revision:

root / lib / server / noded.py @ 73cdf9a3

History | View | Annotate | Download (27.3 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 7260cfbe Iustin Pop
# pylint: disable-msg=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 a8083063 Iustin Pop
37 a8083063 Iustin Pop
from optparse import OptionParser
38 a8083063 Iustin Pop
39 a8083063 Iustin Pop
from ganeti import backend
40 a8083063 Iustin Pop
from ganeti import constants
41 a8083063 Iustin Pop
from ganeti import objects
42 a8083063 Iustin Pop
from ganeti import errors
43 25d6d12a Michael Hanselmann
from ganeti import jstore
44 cc28af80 Michael Hanselmann
from ganeti import daemon
45 1df6506c Michael Hanselmann
from ganeti import http
46 16abfbc2 Alexander Schreiber
from ganeti import utils
47 e337de97 Michael Hanselmann
from ganeti import storage
48 ab221ddf Michael Hanselmann
from ganeti import serializer
49 a744b676 Manuel Franceschini
from ganeti import netutils
50 a8083063 Iustin Pop
51 30e4e741 Iustin Pop
import ganeti.http.server # pylint: disable-msg=W0611
52 19205c39 Michael Hanselmann
53 a8083063 Iustin Pop
54 25d6d12a Michael Hanselmann
queue_lock = None
55 25d6d12a Michael Hanselmann
56 25d6d12a Michael Hanselmann
57 81198f6e Iustin Pop
def _PrepareQueueLock():
58 81198f6e Iustin Pop
  """Try to prepare the queue lock.
59 81198f6e Iustin Pop

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

558 3ecf6786 Iustin Pop
    """
559 319856a9 Michael Hanselmann
    instance = objects.Instance.FromDict(params[0])
560 07813a9e Iustin Pop
    return backend.StartInstance(instance)
561 a8083063 Iustin Pop
562 3ecf6786 Iustin Pop
  @staticmethod
563 6906a9d8 Guido Trotter
  def perspective_migration_info(params):
564 6906a9d8 Guido Trotter
    """Gather information about an instance to be migrated.
565 6906a9d8 Guido Trotter

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

574 6906a9d8 Guido Trotter
    """
575 6906a9d8 Guido Trotter
    instance, info, target = params
576 6906a9d8 Guido Trotter
    instance = objects.Instance.FromDict(instance)
577 6906a9d8 Guido Trotter
    return backend.AcceptInstance(instance, info, target)
578 6906a9d8 Guido Trotter
579 6906a9d8 Guido Trotter
  @staticmethod
580 6906a9d8 Guido Trotter
  def perspective_finalize_migration(params):
581 6906a9d8 Guido Trotter
    """Finalize the instance migration.
582 6906a9d8 Guido Trotter

583 6906a9d8 Guido Trotter
    """
584 6906a9d8 Guido Trotter
    instance, info, success = params
585 6906a9d8 Guido Trotter
    instance = objects.Instance.FromDict(instance)
586 6906a9d8 Guido Trotter
    return backend.FinalizeMigration(instance, info, success)
587 6906a9d8 Guido Trotter
588 6906a9d8 Guido Trotter
  @staticmethod
589 2a10865c Iustin Pop
  def perspective_instance_migrate(params):
590 2a10865c Iustin Pop
    """Migrates an instance.
591 2a10865c Iustin Pop

592 2a10865c Iustin Pop
    """
593 2a10865c Iustin Pop
    instance, target, live = params
594 9f0e6b37 Iustin Pop
    instance = objects.Instance.FromDict(instance)
595 2a10865c Iustin Pop
    return backend.MigrateInstance(instance, target, live)
596 2a10865c Iustin Pop
597 2a10865c Iustin Pop
  @staticmethod
598 007a2f3e Alexander Schreiber
  def perspective_instance_reboot(params):
599 007a2f3e Alexander Schreiber
    """Reboot an instance.
600 007a2f3e Alexander Schreiber

601 007a2f3e Alexander Schreiber
    """
602 007a2f3e Alexander Schreiber
    instance = objects.Instance.FromDict(params[0])
603 007a2f3e Alexander Schreiber
    reboot_type = params[1]
604 17c3f802 Guido Trotter
    shutdown_timeout = params[2]
605 17c3f802 Guido Trotter
    return backend.InstanceReboot(instance, reboot_type, shutdown_timeout)
606 007a2f3e Alexander Schreiber
607 007a2f3e Alexander Schreiber
  @staticmethod
608 3ecf6786 Iustin Pop
  def perspective_instance_info(params):
609 3ecf6786 Iustin Pop
    """Query instance information.
610 3ecf6786 Iustin Pop

611 3ecf6786 Iustin Pop
    """
612 16ad1a83 Iustin Pop
    return backend.GetInstanceInfo(params[0], params[1])
613 a8083063 Iustin Pop
614 3ecf6786 Iustin Pop
  @staticmethod
615 56e7640c Iustin Pop
  def perspective_instance_migratable(params):
616 56e7640c Iustin Pop
    """Query whether the specified instance can be migrated.
617 56e7640c Iustin Pop

618 56e7640c Iustin Pop
    """
619 56e7640c Iustin Pop
    instance = objects.Instance.FromDict(params[0])
620 56e7640c Iustin Pop
    return backend.GetInstanceMigratable(instance)
621 56e7640c Iustin Pop
622 56e7640c Iustin Pop
  @staticmethod
623 3ecf6786 Iustin Pop
  def perspective_all_instances_info(params):
624 3ecf6786 Iustin Pop
    """Query information about all instances.
625 3ecf6786 Iustin Pop

626 3ecf6786 Iustin Pop
    """
627 e69d05fd Iustin Pop
    return backend.GetAllInstancesInfo(params[0])
628 a8083063 Iustin Pop
629 3ecf6786 Iustin Pop
  @staticmethod
630 3ecf6786 Iustin Pop
  def perspective_instance_list(params):
631 3ecf6786 Iustin Pop
    """Query the list of running instances.
632 3ecf6786 Iustin Pop

633 3ecf6786 Iustin Pop
    """
634 c26a6bd2 Iustin Pop
    return backend.GetInstanceList(params[0])
635 a8083063 Iustin Pop
636 a8083063 Iustin Pop
  # node --------------------------
637 a8083063 Iustin Pop
638 3ecf6786 Iustin Pop
  @staticmethod
639 16abfbc2 Alexander Schreiber
  def perspective_node_tcp_ping(params):
640 16abfbc2 Alexander Schreiber
    """Do a TcpPing on the remote node.
641 16abfbc2 Alexander Schreiber

642 16abfbc2 Alexander Schreiber
    """
643 a744b676 Manuel Franceschini
    return netutils.TcpPing(params[1], params[2], timeout=params[3],
644 a744b676 Manuel Franceschini
                            live_port_needed=params[4], source=params[0])
645 16abfbc2 Alexander Schreiber
646 16abfbc2 Alexander Schreiber
  @staticmethod
647 caad16e2 Iustin Pop
  def perspective_node_has_ip_address(params):
648 caad16e2 Iustin Pop
    """Checks if a node has the given ip address.
649 caad16e2 Iustin Pop

650 caad16e2 Iustin Pop
    """
651 8b312c1d Manuel Franceschini
    return netutils.IPAddress.Own(params[0])
652 caad16e2 Iustin Pop
653 caad16e2 Iustin Pop
  @staticmethod
654 3ecf6786 Iustin Pop
  def perspective_node_info(params):
655 3ecf6786 Iustin Pop
    """Query node information.
656 3ecf6786 Iustin Pop

657 3ecf6786 Iustin Pop
    """
658 e69d05fd Iustin Pop
    vgname, hypervisor_type = params
659 e69d05fd Iustin Pop
    return backend.GetNodeInfo(vgname, hypervisor_type)
660 a8083063 Iustin Pop
661 3ecf6786 Iustin Pop
  @staticmethod
662 19ddc57a René Nussbaumer
  def perspective_etc_hosts_modify(params):
663 19ddc57a René Nussbaumer
    """Modify a node entry in /etc/hosts.
664 19ddc57a René Nussbaumer

665 19ddc57a René Nussbaumer
    """
666 19ddc57a René Nussbaumer
    backend.EtcHostsModify(params[0], params[1], params[2])
667 19ddc57a René Nussbaumer
668 19ddc57a René Nussbaumer
    return True
669 19ddc57a René Nussbaumer
670 19ddc57a René Nussbaumer
  @staticmethod
671 3ecf6786 Iustin Pop
  def perspective_node_verify(params):
672 3ecf6786 Iustin Pop
    """Run a verify sequence on this node.
673 3ecf6786 Iustin Pop

674 3ecf6786 Iustin Pop
    """
675 62c9ec92 Iustin Pop
    return backend.VerifyNode(params[0], params[1])
676 a8083063 Iustin Pop
677 3ecf6786 Iustin Pop
  @staticmethod
678 3ecf6786 Iustin Pop
  def perspective_node_start_master(params):
679 3ecf6786 Iustin Pop
    """Promote this node to master status.
680 3ecf6786 Iustin Pop

681 3ecf6786 Iustin Pop
    """
682 3583908a Guido Trotter
    return backend.StartMaster(params[0], params[1])
683 a8083063 Iustin Pop
684 3ecf6786 Iustin Pop
  @staticmethod
685 3ecf6786 Iustin Pop
  def perspective_node_stop_master(params):
686 3ecf6786 Iustin Pop
    """Demote this node from master status.
687 3ecf6786 Iustin Pop

688 3ecf6786 Iustin Pop
    """
689 1c65840b Iustin Pop
    return backend.StopMaster(params[0])
690 a8083063 Iustin Pop
691 3ecf6786 Iustin Pop
  @staticmethod
692 3ecf6786 Iustin Pop
  def perspective_node_leave_cluster(params):
693 3ecf6786 Iustin Pop
    """Cleanup after leaving a cluster.
694 3ecf6786 Iustin Pop

695 3ecf6786 Iustin Pop
    """
696 b989b9d9 Ken Wehr
    return backend.LeaveCluster(params[0])
697 a8083063 Iustin Pop
698 3ecf6786 Iustin Pop
  @staticmethod
699 3ecf6786 Iustin Pop
  def perspective_node_volumes(params):
700 3ecf6786 Iustin Pop
    """Query the list of all logical volume groups.
701 3ecf6786 Iustin Pop

702 3ecf6786 Iustin Pop
    """
703 dcb93971 Michael Hanselmann
    return backend.NodeVolumes()
704 dcb93971 Michael Hanselmann
705 56aa9fd5 Iustin Pop
  @staticmethod
706 56aa9fd5 Iustin Pop
  def perspective_node_demote_from_mc(params):
707 56aa9fd5 Iustin Pop
    """Demote a node from the master candidate role.
708 56aa9fd5 Iustin Pop

709 56aa9fd5 Iustin Pop
    """
710 56aa9fd5 Iustin Pop
    return backend.DemoteFromMC()
711 56aa9fd5 Iustin Pop
712 56aa9fd5 Iustin Pop
713 f5118ade Iustin Pop
  @staticmethod
714 f5118ade Iustin Pop
  def perspective_node_powercycle(params):
715 f5118ade Iustin Pop
    """Tries to powercycle the nod.
716 f5118ade Iustin Pop

717 f5118ade Iustin Pop
    """
718 f5118ade Iustin Pop
    hypervisor_type = params[0]
719 f5118ade Iustin Pop
    return backend.PowercycleNode(hypervisor_type)
720 f5118ade Iustin Pop
721 f5118ade Iustin Pop
722 a8083063 Iustin Pop
  # cluster --------------------------
723 a8083063 Iustin Pop
724 3ecf6786 Iustin Pop
  @staticmethod
725 3ecf6786 Iustin Pop
  def perspective_version(params):
726 3ecf6786 Iustin Pop
    """Query version information.
727 3ecf6786 Iustin Pop

728 3ecf6786 Iustin Pop
    """
729 c26a6bd2 Iustin Pop
    return constants.PROTOCOL_VERSION
730 a8083063 Iustin Pop
731 3ecf6786 Iustin Pop
  @staticmethod
732 3ecf6786 Iustin Pop
  def perspective_upload_file(params):
733 3ecf6786 Iustin Pop
    """Upload a file.
734 3ecf6786 Iustin Pop

735 3ecf6786 Iustin Pop
    Note that the backend implementation imposes strict rules on which
736 3ecf6786 Iustin Pop
    files are accepted.
737 3ecf6786 Iustin Pop

738 3ecf6786 Iustin Pop
    """
739 a8083063 Iustin Pop
    return backend.UploadFile(*params)
740 a8083063 Iustin Pop
741 4e071d3b Iustin Pop
  @staticmethod
742 4e071d3b Iustin Pop
  def perspective_master_info(params):
743 4e071d3b Iustin Pop
    """Query master information.
744 4e071d3b Iustin Pop

745 4e071d3b Iustin Pop
    """
746 4e071d3b Iustin Pop
    return backend.GetMasterInfo()
747 a8083063 Iustin Pop
748 6ddc95ec Michael Hanselmann
  @staticmethod
749 4f6014d4 René Nussbaumer
  def perspective_run_oob(params):
750 4f6014d4 René Nussbaumer
    """Runs oob on node.
751 4f6014d4 René Nussbaumer

752 4f6014d4 René Nussbaumer
    """
753 1aa88d95 René Nussbaumer
    output = backend.RunOob(params[0], params[1], params[2], params[3])
754 1aa88d95 René Nussbaumer
    if output:
755 1aa88d95 René Nussbaumer
      result = serializer.LoadJson(output)
756 1aa88d95 René Nussbaumer
    else:
757 1aa88d95 René Nussbaumer
      result = None
758 1aa88d95 René Nussbaumer
    return result
759 4f6014d4 René Nussbaumer
760 4f6014d4 René Nussbaumer
  @staticmethod
761 6ddc95ec Michael Hanselmann
  def perspective_write_ssconf_files(params):
762 6ddc95ec Michael Hanselmann
    """Write ssconf files.
763 6ddc95ec Michael Hanselmann

764 6ddc95ec Michael Hanselmann
    """
765 03d1dba2 Michael Hanselmann
    (values,) = params
766 03d1dba2 Michael Hanselmann
    return backend.WriteSsconfFiles(values)
767 6ddc95ec Michael Hanselmann
768 a8083063 Iustin Pop
  # os -----------------------
769 a8083063 Iustin Pop
770 3ecf6786 Iustin Pop
  @staticmethod
771 3ecf6786 Iustin Pop
  def perspective_os_diagnose(params):
772 3ecf6786 Iustin Pop
    """Query detailed information about existing OSes.
773 3ecf6786 Iustin Pop

774 3ecf6786 Iustin Pop
    """
775 255dcebd Iustin Pop
    return backend.DiagnoseOS()
776 a8083063 Iustin Pop
777 3ecf6786 Iustin Pop
  @staticmethod
778 3ecf6786 Iustin Pop
  def perspective_os_get(params):
779 3ecf6786 Iustin Pop
    """Query information about a given OS.
780 3ecf6786 Iustin Pop

781 3ecf6786 Iustin Pop
    """
782 a8083063 Iustin Pop
    name = params[0]
783 255dcebd Iustin Pop
    os_obj = backend.OSFromDisk(name)
784 c26a6bd2 Iustin Pop
    return os_obj.ToDict()
785 a8083063 Iustin Pop
786 acd9ff9e Iustin Pop
  @staticmethod
787 acd9ff9e Iustin Pop
  def perspective_os_validate(params):
788 acd9ff9e Iustin Pop
    """Run a given OS' validation routine.
789 acd9ff9e Iustin Pop

790 acd9ff9e Iustin Pop
    """
791 acd9ff9e Iustin Pop
    required, name, checks, params = params
792 acd9ff9e Iustin Pop
    return backend.ValidateOS(required, name, checks, params)
793 acd9ff9e Iustin Pop
794 a8083063 Iustin Pop
  # hooks -----------------------
795 a8083063 Iustin Pop
796 3ecf6786 Iustin Pop
  @staticmethod
797 3ecf6786 Iustin Pop
  def perspective_hooks_runner(params):
798 3ecf6786 Iustin Pop
    """Run hook scripts.
799 3ecf6786 Iustin Pop

800 3ecf6786 Iustin Pop
    """
801 a8083063 Iustin Pop
    hpath, phase, env = params
802 a8083063 Iustin Pop
    hr = backend.HooksRunner()
803 a8083063 Iustin Pop
    return hr.RunHooks(hpath, phase, env)
804 a8083063 Iustin Pop
805 8d528b7c Iustin Pop
  # iallocator -----------------
806 8d528b7c Iustin Pop
807 8d528b7c Iustin Pop
  @staticmethod
808 8d528b7c Iustin Pop
  def perspective_iallocator_runner(params):
809 8d528b7c Iustin Pop
    """Run an iallocator script.
810 8d528b7c Iustin Pop

811 8d528b7c Iustin Pop
    """
812 8d528b7c Iustin Pop
    name, idata = params
813 8d528b7c Iustin Pop
    iar = backend.IAllocatorRunner()
814 8d528b7c Iustin Pop
    return iar.Run(name, idata)
815 8d528b7c Iustin Pop
816 06009e27 Iustin Pop
  # test -----------------------
817 06009e27 Iustin Pop
818 06009e27 Iustin Pop
  @staticmethod
819 06009e27 Iustin Pop
  def perspective_test_delay(params):
820 06009e27 Iustin Pop
    """Run test delay.
821 06009e27 Iustin Pop

822 06009e27 Iustin Pop
    """
823 06009e27 Iustin Pop
    duration = params[0]
824 c26a6bd2 Iustin Pop
    status, rval = utils.TestDelay(duration)
825 c26a6bd2 Iustin Pop
    if not status:
826 c26a6bd2 Iustin Pop
      raise backend.RPCFail(rval)
827 c26a6bd2 Iustin Pop
    return rval
828 06009e27 Iustin Pop
829 4e071d3b Iustin Pop
  # file storage ---------------
830 4e071d3b Iustin Pop
831 a5d7fb43 Manuel Franceschini
  @staticmethod
832 a5d7fb43 Manuel Franceschini
  def perspective_file_storage_dir_create(params):
833 a5d7fb43 Manuel Franceschini
    """Create the file storage directory.
834 a5d7fb43 Manuel Franceschini

835 a5d7fb43 Manuel Franceschini
    """
836 a5d7fb43 Manuel Franceschini
    file_storage_dir = params[0]
837 a5d7fb43 Manuel Franceschini
    return backend.CreateFileStorageDir(file_storage_dir)
838 a5d7fb43 Manuel Franceschini
839 a5d7fb43 Manuel Franceschini
  @staticmethod
840 a5d7fb43 Manuel Franceschini
  def perspective_file_storage_dir_remove(params):
841 a5d7fb43 Manuel Franceschini
    """Remove the file storage directory.
842 a5d7fb43 Manuel Franceschini

843 a5d7fb43 Manuel Franceschini
    """
844 a5d7fb43 Manuel Franceschini
    file_storage_dir = params[0]
845 a5d7fb43 Manuel Franceschini
    return backend.RemoveFileStorageDir(file_storage_dir)
846 a5d7fb43 Manuel Franceschini
847 a5d7fb43 Manuel Franceschini
  @staticmethod
848 a5d7fb43 Manuel Franceschini
  def perspective_file_storage_dir_rename(params):
849 a5d7fb43 Manuel Franceschini
    """Rename the file storage directory.
850 a5d7fb43 Manuel Franceschini

851 a5d7fb43 Manuel Franceschini
    """
852 a5d7fb43 Manuel Franceschini
    old_file_storage_dir = params[0]
853 a5d7fb43 Manuel Franceschini
    new_file_storage_dir = params[1]
854 a5d7fb43 Manuel Franceschini
    return backend.RenameFileStorageDir(old_file_storage_dir,
855 a5d7fb43 Manuel Franceschini
                                        new_file_storage_dir)
856 a5d7fb43 Manuel Franceschini
857 4e071d3b Iustin Pop
  # jobs ------------------------
858 4e071d3b Iustin Pop
859 ca52cdeb Michael Hanselmann
  @staticmethod
860 7f30777b Michael Hanselmann
  @_RequireJobQueueLock
861 ca52cdeb Michael Hanselmann
  def perspective_jobqueue_update(params):
862 ca52cdeb Michael Hanselmann
    """Update job queue.
863 ca52cdeb Michael Hanselmann

864 ca52cdeb Michael Hanselmann
    """
865 ca52cdeb Michael Hanselmann
    (file_name, content) = params
866 7f30777b Michael Hanselmann
    return backend.JobQueueUpdate(file_name, content)
867 ca52cdeb Michael Hanselmann
868 ca52cdeb Michael Hanselmann
  @staticmethod
869 f1f3f45c Michael Hanselmann
  @_RequireJobQueueLock
870 ca52cdeb Michael Hanselmann
  def perspective_jobqueue_purge(params):
871 ca52cdeb Michael Hanselmann
    """Purge job queue.
872 ca52cdeb Michael Hanselmann

873 ca52cdeb Michael Hanselmann
    """
874 ca52cdeb Michael Hanselmann
    return backend.JobQueuePurge()
875 ca52cdeb Michael Hanselmann
876 af5ebcb1 Michael Hanselmann
  @staticmethod
877 af5ebcb1 Michael Hanselmann
  @_RequireJobQueueLock
878 af5ebcb1 Michael Hanselmann
  def perspective_jobqueue_rename(params):
879 af5ebcb1 Michael Hanselmann
    """Rename a job queue file.
880 af5ebcb1 Michael Hanselmann

881 af5ebcb1 Michael Hanselmann
    """
882 dd875d32 Michael Hanselmann
    # TODO: What if a file fails to rename?
883 c26a6bd2 Iustin Pop
    return [backend.JobQueueRename(old, new) for old, new in params]
884 af5ebcb1 Michael Hanselmann
885 6217e295 Iustin Pop
  # hypervisor ---------------
886 6217e295 Iustin Pop
887 6217e295 Iustin Pop
  @staticmethod
888 6217e295 Iustin Pop
  def perspective_hypervisor_validate_params(params):
889 6217e295 Iustin Pop
    """Validate the hypervisor parameters.
890 6217e295 Iustin Pop

891 6217e295 Iustin Pop
    """
892 6217e295 Iustin Pop
    (hvname, hvparams) = params
893 6217e295 Iustin Pop
    return backend.ValidateHVParams(hvname, hvparams)
894 6217e295 Iustin Pop
895 f942a838 Michael Hanselmann
  # Crypto
896 f942a838 Michael Hanselmann
897 f942a838 Michael Hanselmann
  @staticmethod
898 ef40fbfb Michael Hanselmann
  def perspective_x509_cert_create(params):
899 f942a838 Michael Hanselmann
    """Creates a new X509 certificate for SSL/TLS.
900 f942a838 Michael Hanselmann

901 f942a838 Michael Hanselmann
    """
902 f942a838 Michael Hanselmann
    (validity, ) = params
903 f942a838 Michael Hanselmann
    return backend.CreateX509Certificate(validity)
904 f942a838 Michael Hanselmann
905 f942a838 Michael Hanselmann
  @staticmethod
906 ef40fbfb Michael Hanselmann
  def perspective_x509_cert_remove(params):
907 f942a838 Michael Hanselmann
    """Removes a X509 certificate.
908 f942a838 Michael Hanselmann

909 f942a838 Michael Hanselmann
    """
910 f942a838 Michael Hanselmann
    (name, ) = params
911 f942a838 Michael Hanselmann
    return backend.RemoveX509Certificate(name)
912 f942a838 Michael Hanselmann
913 1651d116 Michael Hanselmann
  # Import and export
914 1651d116 Michael Hanselmann
915 1651d116 Michael Hanselmann
  @staticmethod
916 ef40fbfb Michael Hanselmann
  def perspective_import_start(params):
917 1651d116 Michael Hanselmann
    """Starts an import daemon.
918 1651d116 Michael Hanselmann

919 1651d116 Michael Hanselmann
    """
920 eb630f50 Michael Hanselmann
    (opts_s, instance, dest, dest_args) = params
921 eb630f50 Michael Hanselmann
922 eb630f50 Michael Hanselmann
    opts = objects.ImportExportOptions.FromDict(opts_s)
923 eb630f50 Michael Hanselmann
924 eb630f50 Michael Hanselmann
    return backend.StartImportExportDaemon(constants.IEM_IMPORT, opts,
925 1651d116 Michael Hanselmann
                                           None, None,
926 1651d116 Michael Hanselmann
                                           objects.Instance.FromDict(instance),
927 1651d116 Michael Hanselmann
                                           dest,
928 1651d116 Michael Hanselmann
                                           _DecodeImportExportIO(dest,
929 1651d116 Michael Hanselmann
                                                                 dest_args))
930 eb630f50 Michael Hanselmann
931 1651d116 Michael Hanselmann
  @staticmethod
932 ef40fbfb Michael Hanselmann
  def perspective_export_start(params):
933 1651d116 Michael Hanselmann
    """Starts an export daemon.
934 1651d116 Michael Hanselmann

935 1651d116 Michael Hanselmann
    """
936 eb630f50 Michael Hanselmann
    (opts_s, host, port, instance, source, source_args) = params
937 eb630f50 Michael Hanselmann
938 eb630f50 Michael Hanselmann
    opts = objects.ImportExportOptions.FromDict(opts_s)
939 eb630f50 Michael Hanselmann
940 eb630f50 Michael Hanselmann
    return backend.StartImportExportDaemon(constants.IEM_EXPORT, opts,
941 1651d116 Michael Hanselmann
                                           host, port,
942 1651d116 Michael Hanselmann
                                           objects.Instance.FromDict(instance),
943 1651d116 Michael Hanselmann
                                           source,
944 1651d116 Michael Hanselmann
                                           _DecodeImportExportIO(source,
945 1651d116 Michael Hanselmann
                                                                 source_args))
946 1651d116 Michael Hanselmann
947 1651d116 Michael Hanselmann
  @staticmethod
948 ef40fbfb Michael Hanselmann
  def perspective_impexp_status(params):
949 1651d116 Michael Hanselmann
    """Retrieves the status of an import or export daemon.
950 1651d116 Michael Hanselmann

951 1651d116 Michael Hanselmann
    """
952 1651d116 Michael Hanselmann
    return backend.GetImportExportStatus(params[0])
953 1651d116 Michael Hanselmann
954 1651d116 Michael Hanselmann
  @staticmethod
955 f81c4737 Michael Hanselmann
  def perspective_impexp_abort(params):
956 f81c4737 Michael Hanselmann
    """Aborts an import or export.
957 f81c4737 Michael Hanselmann

958 f81c4737 Michael Hanselmann
    """
959 f81c4737 Michael Hanselmann
    return backend.AbortImportExport(params[0])
960 f81c4737 Michael Hanselmann
961 f81c4737 Michael Hanselmann
  @staticmethod
962 ef40fbfb Michael Hanselmann
  def perspective_impexp_cleanup(params):
963 1651d116 Michael Hanselmann
    """Cleans up after an import or export.
964 1651d116 Michael Hanselmann

965 1651d116 Michael Hanselmann
    """
966 1651d116 Michael Hanselmann
    return backend.CleanupImportExport(params[0])
967 1651d116 Michael Hanselmann
968 a8083063 Iustin Pop
969 f93427cd Iustin Pop
def CheckNoded(_, args):
970 f93427cd Iustin Pop
  """Initial checks whether to run or exit with a failure.
971 f93427cd Iustin Pop

972 f93427cd Iustin Pop
  """
973 f93427cd Iustin Pop
  if args: # noded doesn't take any arguments
974 f93427cd Iustin Pop
    print >> sys.stderr, ("Usage: %s [-f] [-d] [-p port] [-b ADDRESS]" %
975 f93427cd Iustin Pop
                          sys.argv[0])
976 f93427cd Iustin Pop
    sys.exit(constants.EXIT_FAILURE)
977 f93427cd Iustin Pop
978 f93427cd Iustin Pop
979 3ee53f1f Iustin Pop
def PrepNoded(options, _):
980 3ee53f1f Iustin Pop
  """Preparation node daemon function, executed with the PID file held.
981 3ecf6786 Iustin Pop

982 3ecf6786 Iustin Pop
  """
983 bebf68d3 Guido Trotter
  if options.mlock:
984 bebf68d3 Guido Trotter
    request_executor_class = MlockallRequestExecutor
985 4c32a8bd Luca Bigliardi
    try:
986 4c32a8bd Luca Bigliardi
      utils.Mlockall()
987 4c32a8bd Luca Bigliardi
    except errors.NoCtypesError:
988 4c32a8bd Luca Bigliardi
      logging.warning("Cannot set memory lock, ctypes module not found")
989 4c32a8bd Luca Bigliardi
      request_executor_class = http.server.HttpServerRequestExecutor
990 bebf68d3 Guido Trotter
  else:
991 bebf68d3 Guido Trotter
    request_executor_class = http.server.HttpServerRequestExecutor
992 02bea2fc Luca Bigliardi
993 04ccf5e9 Guido Trotter
  # Read SSL certificate
994 3b1b0cb6 Guido Trotter
  if options.ssl:
995 3b1b0cb6 Guido Trotter
    ssl_params = http.HttpSslParams(ssl_key_path=options.ssl_key,
996 3b1b0cb6 Guido Trotter
                                    ssl_cert_path=options.ssl_cert)
997 3b1b0cb6 Guido Trotter
  else:
998 3b1b0cb6 Guido Trotter
    ssl_params = None
999 7d88772a Iustin Pop
1000 81198f6e Iustin Pop
  err = _PrepareQueueLock()
1001 81198f6e Iustin Pop
  if err is not None:
1002 81198f6e Iustin Pop
    # this might be some kind of file-system/permission error; while
1003 81198f6e Iustin Pop
    # this breaks the job queue functionality, we shouldn't prevent
1004 81198f6e Iustin Pop
    # startup of the whole node daemon because of this
1005 81198f6e Iustin Pop
    logging.critical("Can't init/verify the queue, proceeding anyway: %s", err)
1006 7d88772a Iustin Pop
1007 04ccf5e9 Guido Trotter
  mainloop = daemon.Mainloop()
1008 04ccf5e9 Guido Trotter
  server = NodeHttpServer(mainloop, options.bind_address, options.port,
1009 38b77287 Luca Bigliardi
                          ssl_params=ssl_params, ssl_verify_peer=True,
1010 bebf68d3 Guido Trotter
                          request_executor_class=request_executor_class)
1011 04ccf5e9 Guido Trotter
  server.Start()
1012 3ee53f1f Iustin Pop
  return (mainloop, server)
1013 3ee53f1f Iustin Pop
1014 5119f2ec Michael Hanselmann
1015 3ee53f1f Iustin Pop
def ExecNoded(options, args, prep_data): # pylint: disable-msg=W0613
1016 3ee53f1f Iustin Pop
  """Main node daemon function, executed with the PID file held.
1017 3ee53f1f Iustin Pop

1018 3ee53f1f Iustin Pop
  """
1019 3ee53f1f Iustin Pop
  (mainloop, server) = prep_data
1020 04ccf5e9 Guido Trotter
  try:
1021 04ccf5e9 Guido Trotter
    mainloop.Run()
1022 04ccf5e9 Guido Trotter
  finally:
1023 04ccf5e9 Guido Trotter
    server.Stop()
1024 a8083063 Iustin Pop
1025 a8083063 Iustin Pop
1026 5119f2ec Michael Hanselmann
def Main():
1027 04ccf5e9 Guido Trotter
  """Main function for the node daemon.
1028 04ccf5e9 Guido Trotter

1029 04ccf5e9 Guido Trotter
  """
1030 04ccf5e9 Guido Trotter
  parser = OptionParser(description="Ganeti node daemon",
1031 04ccf5e9 Guido Trotter
                        usage="%prog [-f] [-d] [-p port] [-b ADDRESS]",
1032 04ccf5e9 Guido Trotter
                        version="%%prog (ganeti) %s" %
1033 04ccf5e9 Guido Trotter
                        constants.RELEASE_VERSION)
1034 bebf68d3 Guido Trotter
  parser.add_option("--no-mlock", dest="mlock",
1035 bebf68d3 Guido Trotter
                    help="Do not mlock the node memory in ram",
1036 bebf68d3 Guido Trotter
                    default=True, action="store_false")
1037 bebf68d3 Guido Trotter
1038 3ee53f1f Iustin Pop
  daemon.GenericMain(constants.NODED, parser, CheckNoded, PrepNoded, ExecNoded,
1039 084aba47 Michael Hanselmann
                     default_ssl_cert=constants.NODED_CERT_FILE,
1040 1c54156d Luca Bigliardi
                     default_ssl_key=constants.NODED_CERT_FILE,
1041 565083ef Luca Bigliardi
                     console_logging=True)