diff --git a/dom0/qvm-core/qubes.py b/dom0/qvm-core/qubes.py index 62670ef6..136db706 100755 --- a/dom0/qvm-core/qubes.py +++ b/dom0/qvm-core/qubes.py @@ -228,7 +228,6 @@ class QubesVm(object): "volatile_img": { "eval": 'self.absolute_path(value, default_volatile_img)', 'order': 10 }, "firewall_conf": { "eval": 'self.absolute_path(value, default_firewall_conf_file)', 'order': 10 }, "installed_by_rpm": { "default": False, 'order': 10 }, - "updateable": { "default": False, 'order': 10 }, "template": { "default": None, 'order': 10 }, # order >= 20: have template set "uses_default_netvm": { "default": True, 'order': 20 }, @@ -266,7 +265,7 @@ class QubesVm(object): # Simple string attrs for prop in ['qid', 'name', 'dir_path', 'memory', 'maxmem', 'pcidevs', 'vcpus', 'internal',\ 'uses_default_kernel', 'kernel', 'uses_default_kernelopts',\ - 'kernelopts', 'services', 'updateable', 'installed_by_rpm',\ + 'kernelopts', 'services', 'installed_by_rpm',\ 'uses_default_netvm', 'include_in_backups' ]: attrs[prop]['save'] = 'str(self.%s)' % prop # Simple paths @@ -279,7 +278,7 @@ class QubesVm(object): attrs['netvm']['save'] = 'str(self.netvm.qid) if self.netvm is not None else "none"' attrs['netvm']['save_attr'] = "netvm_qid" - attrs['template']['save'] = 'str(self.template.qid) if self.template and not self.is_updateable() else "none"' + attrs['template']['save'] = 'str(self.template.qid) if self.template else "none"' attrs['template']['save_attr'] = "template_qid" attrs['label']['save'] = 'self.label.name' @@ -327,9 +326,6 @@ class QubesVm(object): # Some additional checks for template based VM if self.template is not None: - if self.updateable: - print >> sys.stderr, "ERROR: Template based VM cannot be updateable!" - return False if not self.template.is_template(): print >> sys.stderr, "ERROR: template_qid={0} doesn't point to a valid TemplateVM".\ format(self.template.qid) @@ -457,6 +453,11 @@ class QubesVm(object): def mac(self, new_mac): self._mac = new_mac + @property + def updateable(self): + return self.template is None + + # Leaved for compatibility def is_updateable(self): return self.updateable @@ -469,19 +470,6 @@ class QubesVm(object): else: return False - def set_updateable(self): - if self.is_updateable(): - return - - raise QubesException ("Change 'updateable' flag is not supported. Please use qvm-create.") - - def set_nonupdateable(self): - if not self.is_updateable(): - return - - raise QubesException ("Change 'updateable' flag is not supported. Please use qvm-create.") - - def pre_rename(self, new_name): pass @@ -875,7 +863,7 @@ class QubesVm(object): args['privatedev'] = "'script:file:{dir}/private.img,xvdb,w',".format(dir=self.dir_path) args['volatiledev'] = "'script:file:{dir}/volatile.img,xvdc,w',".format(dir=self.dir_path) modulesmode='r' - if self.is_updateable() and self.kernel is None: + if self.updateable and self.kernel is None: modulesmode='w' args['otherdevs'] = "'script:file:{dir}/modules.img,xvdd,{mode}',".format(dir=self.kernels_dir, mode=modulesmode) args['kernelopts'] = self.kernelopts @@ -937,7 +925,7 @@ class QubesVm(object): shutil.copy(source_template.dir_path + '/vm-' + qubes_whitelisted_appmenus, self.dir_path + '/' + qubes_whitelisted_appmenus) - if self.is_updateable(): + if self.updateable: template_root = source_template.root_img if verbose: print >> sys.stderr, "--> Copying the template's root image: {0}".\ @@ -1067,7 +1055,7 @@ class QubesVm(object): "VM directory doesn't exist: {0}".\ format(self.dir_path)) - if self.is_updateable() and not os.path.exists (self.root_img): + if self.updateable and not os.path.exists (self.root_img): raise QubesException ( "VM root image file doesn't exist: {0}".\ format(self.root_img)) @@ -1483,7 +1471,6 @@ class QubesTemplateVm(QubesVm): def _get_attrs_config(self): attrs_config = super(QubesTemplateVm, self)._get_attrs_config() attrs_config['dir_path']['eval'] = 'value if value is not None else qubes_templates_dir + "/" + self.name' - attrs_config['updateable']['default'] = True attrs_config['label']['default'] = default_template_label # New attributes @@ -1506,18 +1493,9 @@ class QubesTemplateVm(QubesVm): def type(self): return "TemplateVM" - def set_updateable(self): - if self.is_updateable(): - return - - assert not self.is_running() - # Make sure that all the AppVMs are non-updateable... - for appvm in self.appvms.values(): - if appvm.is_updateable(): - raise QubesException("One of the AppVMs ('{0}')is also 'updateable'\ - -- cannot make the TemplateVM {'{1}'} 'nonupdatable'".\ - format (appvm.name, self.name)) - self.updateable = True + @property + def updateable(self): + return True def get_rootdev(self, source_template=None): return "'script:origin:{dir}/root.img:{dir}/root-cow.img,xvda,w',".format(dir=self.dir_path) @@ -1633,7 +1611,7 @@ class QubesTemplateVm(QubesVm): self.reset_volatile_storage(verbose=verbose) - if not self.is_updateable(): + if not self.updateable: raise QubesException ("Cannot start Template VM that is marked \"nonupdatable\"") # TODO?: check if none of running appvms are outdated @@ -2104,7 +2082,7 @@ class QubesAppVm(QubesVm): super(QubesAppVm, self).create_on_disk(verbose, source_template=source_template) - if self.is_updateable(): + if self.updateable: if verbose: print >> sys.stderr, "--> Copying the template's appmenus templates dir:\n{0} ==>\n{1}".\ format(source_template.appmenus_templates_dir, self.appmenus_templates_dir) @@ -2170,7 +2148,6 @@ class QubesVmCollection(dict): def add_new_appvm(self, name, template, dir_path = None, conf_file = None, private_img = None, - updateable = False, label = None): qid = self.get_new_unused_qid() @@ -2180,7 +2157,6 @@ class QubesVmCollection(dict): netvm = self.get_default_netvm(), kernel = self.get_default_kernel(), uses_default_kernel = True, - updateable=updateable, label=label) if not self.verify_new_vm (vm): @@ -2236,14 +2212,13 @@ class QubesVmCollection(dict): def add_new_netvm(self, name, template, dir_path = None, conf_file = None, private_img = None, installed_by_rpm = False, - label = None, updateable = False): + label = None): qid = self.get_new_unused_qid() netid = self.get_new_unused_netid() vm = QubesNetVm (qid=qid, name=name, template=template, netid=netid, label=label, private_img=private_img, installed_by_rpm=installed_by_rpm, - updateable=updateable, kernel = self.get_default_kernel(), uses_default_kernel = True, dir_path=dir_path, conf_file=conf_file) @@ -2264,7 +2239,7 @@ class QubesVmCollection(dict): def add_new_proxyvm(self, name, template, dir_path = None, conf_file = None, private_img = None, installed_by_rpm = False, - label = None, updateable = False): + label = None): qid = self.get_new_unused_qid() netid = self.get_new_unused_netid() @@ -2272,7 +2247,6 @@ class QubesVmCollection(dict): netid=netid, label=label, private_img=private_img, installed_by_rpm=installed_by_rpm, dir_path=dir_path, conf_file=conf_file, - updateable=updateable, kernel = self.get_default_kernel(), uses_default_kernel = True, netvm = self.get_default_fw_netvm()) @@ -2482,7 +2456,7 @@ class QubesVmCollection(dict): kwargs = {} common_attr_list = ("qid", "name", "dir_path", "conf_file", "private_img", "root_img", "template_qid", - "installed_by_rpm", "updateable", "internal", + "installed_by_rpm", "internal", "uses_default_netvm", "label", "memory", "vcpus", "pcidevs", "maxmem", "kernel", "uses_default_kernel", "kernelopts", "uses_default_kernelopts", "mac", "services", "include_in_backups" ) @@ -2493,8 +2467,6 @@ class QubesVmCollection(dict): kwargs.pop(attribute) kwargs["qid"] = int(kwargs["qid"]) - if "updateable" in kwargs: - kwargs["updateable"] = True if kwargs["updateable"] == "True" else False if "include_in_backups" in kwargs: kwargs["include_in_backups"] = True if kwargs["include_in_backups"] == "True" else False diff --git a/dom0/qvm-core/qubesutils.py b/dom0/qvm-core/qubesutils.py index 5b21cccc..454603c0 100644 --- a/dom0/qvm-core/qubesutils.py +++ b/dom0/qvm-core/qubesutils.py @@ -390,7 +390,7 @@ def backup_prepare(base_backup_dir, vms_list = None, exclude_list = [], print_ca if vm.is_appvm(): files_to_backup += file_to_backup(vm.icon_path) - if vm.is_updateable(): + if vm.updateable: if os.path.exists(vm.dir_path + "/apps.templates"): # template files_to_backup += file_to_backup(vm.dir_path + "/apps.templates") @@ -405,7 +405,7 @@ def backup_prepare(base_backup_dir, vms_list = None, exclude_list = [], print_ca if os.path.exists(vm.dir_path + '/whitelisted-appmenus.list'): files_to_backup += file_to_backup(vm.dir_path + '/whitelisted-appmenus.list') - if vm.is_updateable(): + if vm.updateable: sz = vm.get_disk_usage(vm.root_img) files_to_backup += file_to_backup(vm.root_img, sz) vm_sz += sz @@ -419,9 +419,9 @@ def backup_prepare(base_backup_dir, vms_list = None, exclude_list = [], print_ca fmt="{{0:>{0}}} |".format(fields_to_display[1]["width"] + 1) if vm.is_netvm(): - s += fmt.format("NetVM" + (" + Sys" if vm.is_updateable() else "")) + s += fmt.format("NetVM" + (" + Sys" if vm.updateable else "")) else: - s += fmt.format("AppVM" + (" + Sys" if vm.is_updateable() else "")) + s += fmt.format("AppVM" + (" + Sys" if vm.updateable else "")) fmt="{{0:>{0}}} |".format(fields_to_display[2]["width"] + 1) s += fmt.format(size_to_human(vm_sz)) @@ -702,7 +702,7 @@ def backup_restore_print_summary(restore_info, print_callback = print_stdout): ('Proxy' if vm.is_proxyvm() else \ (' Net' if vm.is_netvm() else 'App'))"}, - "updbl" : {"func": "'Yes' if vm.is_updateable() else ''"}, + "updbl" : {"func": "'Yes' if vm.updateable else ''"}, "template": {"func": "'n/a' if vm.is_template() or vm.template is None else\ vm_info['template']"}, @@ -834,8 +834,6 @@ def backup_restore_do(backup_dir, restore_info, host_collection = None, print_ca error_callback("Skiping...") continue - updateable = vm.updateable - new_vm = None try: @@ -845,7 +843,6 @@ def backup_restore_do(backup_dir, restore_info, host_collection = None, print_ca dir_path=vm.dir_path, installed_by_rpm=False) - new_vm.updateable = updateable new_vm.verify_files() except Exception as err: error_callback("ERROR: {0}".format(err)) @@ -888,8 +885,6 @@ def backup_restore_do(backup_dir, restore_info, host_collection = None, print_ca else: uses_default_netvm = True - updateable = vm.updateable - new_vm = None try: restore_vm_dir (backup_dir, vm.dir_path, qubes_servicevms_dir); @@ -898,13 +893,11 @@ def backup_restore_do(backup_dir, restore_info, host_collection = None, print_ca new_vm = host_collection.add_new_netvm(vm.name, template, conf_file=vm.conf_file, dir_path=vm.dir_path, - updateable=updateable, label=vm.label) elif vm.type == "ProxyVM": new_vm = host_collection.add_new_proxyvm(vm.name, template, conf_file=vm.conf_file, dir_path=vm.dir_path, - updateable=updateable, label=vm.label) except Exception as err: error_callback("ERROR: {0}".format(err)) @@ -953,15 +946,12 @@ def backup_restore_do(backup_dir, restore_info, host_collection = None, print_ca else: uses_default_netvm = True - updateable = vm.updateable - new_vm = None try: restore_vm_dir (backup_dir, vm.dir_path, qubes_appvms_dir); new_vm = host_collection.add_new_appvm(vm.name, template, conf_file=vm.conf_file, dir_path=vm.dir_path, - updateable=updateable, label=vm.label) except Exception as err: error_callback("ERROR: {0}".format(err)) diff --git a/dom0/qvm-tools/qvm-clone b/dom0/qvm-tools/qvm-clone index b5d0b01d..ecdfc66c 100755 --- a/dom0/qvm-tools/qvm-clone +++ b/dom0/qvm-tools/qvm-clone @@ -60,7 +60,7 @@ def main(): dir_path=options.dir_path, installed_by_rpm=False) elif isinstance(src_vm, QubesAppVm): dst_vm = qvm_collection.add_new_appvm(name=dstname, template=src_vm.template, - updateable=src_vm.updateable, label=src_vm.label, + label=src_vm.label, dir_path=options.dir_path) else: print >> sys.stderr, "ERROR: Clone not supported for this type of VM" diff --git a/dom0/qvm-tools/qvm-create b/dom0/qvm-tools/qvm-create index 0b8457ad..595442fd 100755 --- a/dom0/qvm-tools/qvm-create +++ b/dom0/qvm-tools/qvm-create @@ -117,11 +117,11 @@ def main(): vm = None if options.netvm: - vm = qvm_collection.add_new_netvm(vmname, new_vm_template, label = label, updateable = options.standalone) + vm = qvm_collection.add_new_netvm(vmname, new_vm_template, label = label) elif options.proxyvm: - vm = qvm_collection.add_new_proxyvm(vmname, new_vm_template, label = label, updateable = options.standalone) + vm = qvm_collection.add_new_proxyvm(vmname, new_vm_template, label = label) else: - vm = qvm_collection.add_new_appvm(vmname, new_vm_template, label = label, updateable = options.standalone) + vm = qvm_collection.add_new_appvm(vmname, new_vm_template, label = label) if options.internal: vm.internal = True diff --git a/dom0/qvm-tools/qvm-ls b/dom0/qvm-tools/qvm-ls index 5757b485..3927ccfc 100755 --- a/dom0/qvm-tools/qvm-ls +++ b/dom0/qvm-tools/qvm-ls @@ -44,7 +44,7 @@ fields = { ('Proxy' if vm.is_proxyvm() else \ (' Net' if vm.is_netvm() else ''))"}, - "updbl" : {"func": "'Yes' if vm.is_updateable() else ''"}, + "updbl" : {"func": "'Yes' if vm.updateable else ''"}, "template": {"func": "'n/a' if vm.is_template() else\ ('None' if vm.template is None else\ diff --git a/dom0/qvm-tools/qvm-prefs b/dom0/qvm-tools/qvm-prefs index 237ea1ee..a77bf78d 100755 --- a/dom0/qvm-tools/qvm-prefs +++ b/dom0/qvm-tools/qvm-prefs @@ -41,7 +41,7 @@ def do_list(vm): print fmt.format ("template", vm.template.name) if vm.netvm is not None: print fmt.format ("netvm", vm.netvm.name) - print fmt.format ("updateable?", vm.is_updateable()) + print fmt.format ("updateable?", vm.updateable) print fmt.format ("installed by RPM?", vm.installed_by_rpm) print fmt.format ("include in backups", vm.include_in_backups) print fmt.format ("dir", vm.dir_path) @@ -152,59 +152,6 @@ def set_netvm(vms, vm, args): vm.netvm = netvm -def set_updateable(vms, vm, args): - if vm.is_updateable(): - print >> sys.stderr, "VM '{0}' is already set 'updateable', no action required.".format(vm.name) - return True - - if vm.is_running(): - print >> sys.stderr, "Cannot change 'updateable' attribute of a running VM. Shut it down first." - return False - - if vm.is_appvm(): - # Check if the Template is *non* updateable... - if not vm.template.is_updateable(): - print >> sys.stderr, "VM '{0}': Setting 'updateable' attribute to True.".format(vm.name) - vm.set_updateable() - else: - print >> sys.stderr, "The Template VM ('{0}') is marked as 'updateable' itself!".format(vm.template.name) - print >> sys.stderr, "Cannot make the AppVM updateable too, as this might cause COW-backed storage incoherency." - print >> sys.stderr, "If you want to make this AppVM updateable, you must first make the Template VM nonupdateable." - return False - - if vm.is_template(): - # Make sure that all the AppVMs are non-updateable... - for appvm in vm.appvms.values(): - if appvm.is_updateable(): - print >> sys.stderr, "At least one of the AppVMs ('{0}') of this Template VM is also marked 'updateable'.".format(appvm.name) - print >> sys.stderr, "Cannot make the Template VM updateable too, as this might cause COW-backed storage incoherency." - print >> sys.stderr, "If you want to make this Template VM updateable, you must first make all its decedent AppVMs nonupdateable." - return False - - - print >> sys.stderr, "VM '{0}': Setting 'updateable' attribute to True.".format(vm.name) - vm.set_updateable() - - return True - -def set_nonupdateable(vms, vm, args): - if not vm.is_updateable(): - print >> sys.stderr, "VM '{0}' is already set 'nonupdateable', no action required.".format(vm.name) - return True - - if vm.is_running(): - print >> sys.stderr, "Cannot change 'updateable' attribute of a running VM. Shut it down first." - return False - - if vm.is_netvm(): - print >> sys.stderr, "Why, on earth, would you want to make a NetVM 'nonupdateable'?" - return False - - - print >> sys.stderr, "VM '{0}': Setting 'updateable' attribute to False.".format(vm.name) - vm.set_nonupdateable() - return True - def set_kernel(vms, vm, args): if vm.template is not None: print >> sys.stderr, "Cannot set kernel for template-based VM. Set it for template instead." @@ -310,8 +257,6 @@ def set_include_in_backups(vms, vm, args): properties = { "include_in_backups": set_include_in_backups, - "updateable": set_updateable, - "nonupdateable": set_nonupdateable, "pcidevs": set_pcidevs, "label" : set_label, "netvm" : set_netvm, diff --git a/dom0/qvm-tools/qvm-sync-appmenus b/dom0/qvm-tools/qvm-sync-appmenus index 6b81c2cf..612c3370 100755 --- a/dom0/qvm-tools/qvm-sync-appmenus +++ b/dom0/qvm-tools/qvm-sync-appmenus @@ -164,8 +164,8 @@ def main(): print >>sys.stderr, "ERROR: A VM with the name '{0}' does not exist in the system.".format(vmname) exit(1) - if not vm.is_updateable(): - print >>sys.stderr, "ERROR: To sync appmenus for non-updateable VM, do it on template instead" + if vm.template is not None: + print >>sys.stderr, "ERROR: To sync appmenus for template based VM, do it on template instead" exit(1) if not vm.is_running():