#!/usr/bin/env python import sys sys.path.append('/usr/lib/python') import os, struct from time import strftime from xen.xend import sxp SIGNATURE = "LinuxGuestRecord" LENLEN = struct.calcsize('i') class VMImageException(Exception): pass class VMImage: def __init__(self, path, cfg=None): self._path = path if cfg: self._cfg = cfg else: self.parse() def parse(self): fd = file(self._path) sig = fd.read(len(SIGNATURE)) if sig != SIGNATURE: raise VMImageException('Signature not found in VM image %s' % self._path) sz = struct.unpack("!i", fd.read(LENLEN))[0] cfg = fd.read(sz) p = sxp.Parser() p.input(cfg) self._cfg = p.get_val() self._vmoff = sz + len(SIGNATURE) self._fd = fd def writehdr(self): cfgstr = sxp.to_string(self._cfg) fd = file(self._path, 'wb') fd.write(SIGNATURE) fd.write(struct.pack("!i", len(cfgstr))) fd.write(cfgstr) self._fd = fd def getvbd(self): vbd = None for child in sxp.children(self._cfg, 'device'): for child in sxp.children(child, 'vbd'): vbd = sxp.child(child, 'uname') return vbd def run(cmd): print cmd fd = os.popen(cmd) for line in fd: print line.rstrip() return not fd.close() dom = sys.argv[1] date = strftime('%m%d%H%M%S') checkpoint = '%s-%s' % (dom, date) #checkpoint = dom rc = run('sudo xm save -c %s %s' % (dom, checkpoint)) if not rc: sys.exit(1) img = VMImage(checkpoint) vbd = img.getvbd() nvbd = os.path.join(os.path.dirname(vbd[1]), checkpoint) vbd[1] = nvbd tgt = checkpoint + '.new' nimg = VMImage(tgt, img._cfg) nimg.writehdr() data = img._fd.read(65536) while data: nimg._fd.write(data) data = img._fd.read(65536) os.rename(tgt, checkpoint)