Skip to content

Commit

Permalink
Introduce LocalVM to extract BaseVM being smaller class
Browse files Browse the repository at this point in the history
It prepares the work for RemoteVM.
  • Loading branch information
fepitre committed Nov 23, 2024
1 parent 039b7d3 commit 0e2e8d9
Show file tree
Hide file tree
Showing 15 changed files with 151 additions and 111 deletions.
2 changes: 1 addition & 1 deletion doc/qubes-features.rst
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,7 @@ request in ``features-request`` event handler. If no extension handles given
feature request, it will be ignored. The extension should carefuly validate
requested features (ignoring those not recognized - may be for another
extension) and only then set appropriate value on VM object
(:py:attr:`qubes.vm.BaseVM.features`). It is recommended to make the
(:py:attr:`qubes.vm.LocalVM.features`). It is recommended to make the
verification code as bulletproof as possible (for example allow only specific
simple values, instead of complex structures), because feature requests come
from untrusted sources. The features actually set on the VM in some cases may
Expand Down
6 changes: 3 additions & 3 deletions doc/qubes-vm/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -19,13 +19,13 @@ two, the :py:class:`qubes.vm.qubesvm.QubesVM` cares about Qubes-specific
actions, that are more or less directly related to security model. It is
intended to be easily auditable by non-expert programmers (ie. we don't use
Python's magic there). The second class is its parent,
:py:class:`qubes.vm.BaseVM`, which is concerned about technicalities like XML
:py:class:`qubes.vm.LocalVM`, which is concerned about technicalities like XML
serialising/deserialising. It is of less concern to threat model auditors, but
still relevant to overall security of the Qubes OS. It is written for
programmers by programmers.

The second object is the XML node that refers to the domain. It can be accessed
as :py:attr:`Qubes.vm.BaseVM.xml` attribute of the domain object. The third one
as :py:attr:`Qubes.vm.LocalVM.xml` attribute of the domain object. The third one
is :py:attr:`Qubes.vm.qubesvm.QubesVM.libvirt_domain` object for directly
interacting with libvirt. Those objects are intended to be used from core and/or
plugins, but not directly by user or from qvm-tools. They are however public, so
Expand All @@ -48,7 +48,7 @@ Package contents
Main public classes
^^^^^^^^^^^^^^^^^^^

.. autoclass:: qubes.vm.BaseVM
.. autoclass:: qubes.vm.LocalVM
:members:
:show-inheritance:

Expand Down
10 changes: 6 additions & 4 deletions qubes/app.py
Original file line number Diff line number Diff line change
Expand Up @@ -503,17 +503,19 @@ def vms(self):
def add(self, value, _enable_events=True):
"""Add VM to collection
:param qubes.vm.BaseVM value: VM to add
:param qubes.vm.LocalVM value: VM to add
:param _enable_events:
:raises TypeError: when value is of wrong type
:raises ValueError: when there is already VM which has equal ``qid``
"""

# this violates duck typing, but is needed
# for VMProperty to function correctly
if not isinstance(value, qubes.vm.BaseVM):
if not isinstance(value, qubes.vm.LocalVM):
raise TypeError(
"{} holds only BaseVM instances".format(self.__class__.__name__)
"{} holds only LocalVM instances".format(
self.__class__.__name__
)
)

if value.qid in self:
Expand Down Expand Up @@ -543,7 +545,7 @@ def __getitem__(self, key):
return vm
raise KeyError(key)

if isinstance(key, qubes.vm.BaseVM):
if isinstance(key, qubes.vm.LocalVM):
key = key.uuid

if isinstance(key, uuid.UUID):
Expand Down
2 changes: 1 addition & 1 deletion qubes/ext/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,7 @@ def decorator(func):
elif "vm" in kwargs:
func.ha_vm = kwargs["vm"]
else:
func.ha_vm = qubes.vm.BaseVM
func.ha_vm = qubes.vm.LocalVM

return func

Expand Down
2 changes: 1 addition & 1 deletion qubes/features.py
Original file line number Diff line number Diff line change
Expand Up @@ -161,7 +161,7 @@ def _recursive_check(
raise NotImplementedError("app does not have features yet")

assert isinstance(
self.subject, _vm.BaseVM
self.subject, _vm.LocalVM
), "recursive checks do not work for {}".format(
type(self.subject).__name__
)
Expand Down
2 changes: 1 addition & 1 deletion qubes/tests/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -507,7 +507,7 @@ def cleanup_gc(self):
obj,
(
qubes.Qubes,
qubes.vm.BaseVM,
qubes.vm.LocalVM,
libvirt.virConnect,
libvirt.virDomain,
),
Expand Down
2 changes: 1 addition & 1 deletion qubes/tests/init.py
Original file line number Diff line number Diff line change
Expand Up @@ -402,7 +402,7 @@ def test_010_property_require(self):
pass


class TestVM(qubes.vm.BaseVM):
class TestVM(qubes.vm.LocalVM):
qid = qubes.property("qid", type=int)
name = qubes.property("name")
uuid = uuid.uuid5(uuid.NAMESPACE_DNS, "testvm")
Expand Down
2 changes: 1 addition & 1 deletion qubes/tests/integ/backupcompatibility.py
Original file line number Diff line number Diff line change
Expand Up @@ -494,7 +494,7 @@ def assertRestored(self, name, **kwargs):
)
else:
actual_value = getattr(vm, prop)
if isinstance(actual_value, qubes.vm.BaseVM):
if isinstance(actual_value, qubes.vm.LocalVM):
self.assertEqual(
value,
actual_value.name,
Expand Down
2 changes: 1 addition & 1 deletion qubes/tests/storage_callback.py
Original file line number Diff line number Diff line change
Expand Up @@ -240,7 +240,7 @@ def tearDown(self):
self.app.close()
del self.app
for attr in dir(self):
if isinstance(getattr(self, attr), qubes.vm.BaseVM):
if isinstance(getattr(self, attr), qubes.vm.LocalVM):
delattr(self, attr)

if os.path.exists(self.test_log):
Expand Down
4 changes: 2 additions & 2 deletions qubes/tests/storage_lvm.py
Original file line number Diff line number Diff line change
Expand Up @@ -176,7 +176,7 @@ def tearDown(self):
self.app.close()
del self.app
for attr in dir(self):
if isinstance(getattr(self, attr), qubes.vm.BaseVM):
if isinstance(getattr(self, attr), qubes.vm.LocalVM):
delattr(self, attr)

def test_000_default_thin_pool(self):
Expand Down Expand Up @@ -1488,7 +1488,7 @@ def tearDown(self):
self.app.close()
del self.app
for attr in dir(self):
if isinstance(getattr(self, attr), qubes.vm.BaseVM):
if isinstance(getattr(self, attr), qubes.vm.LocalVM):
delattr(self, attr)

def test_000_search_thin_pool(self):
Expand Down
4 changes: 2 additions & 2 deletions qubes/tests/vm/init.py
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ def __init__(self):
self.vmm = TestVMM()


class TestVM(qubes.vm.BaseVM):
class TestVM(qubes.vm.LocalVM):
qid = qubes.property("qid", type=int)
name = qubes.property("name")
testprop = qubes.property("testprop")
Expand All @@ -55,7 +55,7 @@ def is_running(self):
return False


class TC_10_BaseVM(qubes.tests.QubesTestCase):
class TC_10_LocalVM(qubes.tests.QubesTestCase):
def setUp(self):
super().setUp()
self.xml = lxml.etree.XML(
Expand Down
Loading

0 comments on commit 0e2e8d9

Please sign in to comment.