mirror of
https://github.com/QubesOS/qubes-doc.git
synced 2025-07-30 10:09:23 -04:00
Convert to RST
This is done using tools at https://github.com/maiska/qubes-translation-utilz, commit 4c8e2a7f559fd37e29b51769ed1ab1c6cf92e00d.
This commit is contained in:
parent
e3db139fe3
commit
7e464d0f40
428 changed files with 32833 additions and 29703 deletions
926
developer/services/admin-api.rst
Normal file
926
developer/services/admin-api.rst
Normal file
|
@ -0,0 +1,926 @@
|
|||
=========
|
||||
Admin API
|
||||
=========
|
||||
|
||||
*You may also be interested in the article* \ `Introducing the Qubes Admin API <https://www.qubes-os.org/news/2017/06/27/qubes-admin-api/>`__\ *.*
|
||||
|
||||
Goals
|
||||
=====
|
||||
|
||||
The goals of the Admin API system is to provide a way for the user to
|
||||
manage the domains without direct access to dom0.
|
||||
|
||||
Foreseen benefits include:
|
||||
|
||||
- Ability to remotely manage the Qubes OS.
|
||||
- Possibility to create multi-user system, where different users are
|
||||
able to use different sets of domains, possibly overlapping. This
|
||||
would also require to have separate GUI domain.
|
||||
|
||||
The API would be used by:
|
||||
|
||||
- Qubes OS Manager (or any tools that would replace it)
|
||||
- CLI tools, when run from another VM (and possibly also from dom0)
|
||||
- remote management tools
|
||||
- any custom tools
|
||||
|
||||
Threat model
|
||||
============
|
||||
|
||||
TBD
|
||||
|
||||
Components
|
||||
==========
|
||||
|
||||
.. figure:: /attachment/doc/admin-api-architecture.png
|
||||
:alt: Admin API Architecture
|
||||
|
||||
|
||||
|
||||
A central entity in the Qubes Admin API system is a ``qubesd`` daemon,
|
||||
which holds information about all domains in the system and mediates all
|
||||
actions (like starting and stopping a qube) with ``libvirtd``. The
|
||||
``qubesd`` daemon also manages the ``qubes.xml`` file, which stores all
|
||||
persistent state information and dispatches events to extensions. Last
|
||||
but not least, ``qubesd`` is responsible for querying the RPC policy for
|
||||
qrexec daemon.
|
||||
|
||||
The ``qubesd`` daemon may be accessed from other domains through a set
|
||||
of qrexec API calls called the “Admin API”. This API is the intended
|
||||
management interface supported by the Qubes OS. The API is stable. When
|
||||
called, the RPC handler performs basic validation and forwards the
|
||||
request to the ``qubesd`` via UNIX domain socket. The socket API is
|
||||
private, unstable, and not yet documented.
|
||||
|
||||
The calls
|
||||
=========
|
||||
|
||||
The API should be implemented as a set of qrexec calls. This is to make
|
||||
it easy to set the policy using current mechanism.
|
||||
|
||||
|
||||
.. list-table::
|
||||
:widths: 15 8 8 10 20 30
|
||||
:align: left
|
||||
:header-rows: 1
|
||||
|
||||
* - call
|
||||
- dest
|
||||
- argument
|
||||
- inside
|
||||
- return
|
||||
- note
|
||||
* - ``admin.vmclass.List``
|
||||
- ``dom0``
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<class>\n``
|
||||
-
|
||||
* - ``admin.vm.List``
|
||||
- ``dom0|<vm>``
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<name> class=<class> state=<state>\n``
|
||||
-
|
||||
* - ``admin.vm.Create.<class>``
|
||||
- ``dom0``
|
||||
- template
|
||||
- ``name=<name> label=<label>``
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.CreateInPool.<class>``
|
||||
- ``dom0``
|
||||
- template
|
||||
- ``name=<name> label=<label>``, ``pool=<pool> pool:<volume>=<pool>``
|
||||
- `-`
|
||||
- either use ``pool=`` to put all volumes there, or ``pool:<volume>=`` for individual volumes - both forms are not allowed at the same time
|
||||
* - ``admin.vm.CreateDisposable``
|
||||
- template
|
||||
- `-`
|
||||
- `-`
|
||||
- name
|
||||
- Create new DisposableVM, ``template`` is any AppVM with ``dispvm_allowed`` set to True, or ``dom0`` to use default defined in ``default_dispvm`` property of calling VM; VM created with this call will be automatically removed after its shutdown; the main difference from ``admin.vm.Create.DispVM`` is automatic (random) name generation.
|
||||
* - ``admin.vm.Remove``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.label.List``
|
||||
- ``dom0``
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<property>\n``
|
||||
-
|
||||
* - ``admin.label.Create``
|
||||
- ``dom0``
|
||||
- label
|
||||
- ``0xRRGGBB``
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.label.Get``
|
||||
- ``dom0``
|
||||
- label
|
||||
- `-`
|
||||
- ``0xRRGGBB``
|
||||
-
|
||||
* - ``admin.label.Index``
|
||||
- ``dom0``
|
||||
- label
|
||||
- `-`
|
||||
- ``<label-index>``
|
||||
-
|
||||
* - ``admin.label.Remove``
|
||||
- ``dom0``
|
||||
- label
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.property.List``
|
||||
- ``dom0``
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<property>\n``
|
||||
-
|
||||
* - ``admin.property.Get``
|
||||
- ``dom0``
|
||||
- property
|
||||
- `-`
|
||||
- ``default={True|False}`` ``type={str|int|bool|vm|label|list} <value>``
|
||||
- Type ``list`` is added in R4.1. Values are of type ``str`` and each entry is suffixed with newline character.
|
||||
* - ``admin.property.GetAll``
|
||||
- ``dom0``
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<property-name> <full-value-as-in-property.Get>``
|
||||
- Get all the properties in one call. Each property is returned on a separate line and use the same value encoding as property.Get method, with an exception that newlines are encoded as literal ``\n`` and literal ``\`` are encoded as ``\\``.
|
||||
* - ``admin.property.GetDefault``
|
||||
- ``dom0``
|
||||
- propety
|
||||
- `-`
|
||||
- ``type={str|int|bool|vm|label|list} <value>``
|
||||
- Type ``list`` is added in R4.1. Values are of type ``str`` and each entry is suffixed with newline character.
|
||||
* - ``admin.property.Help``
|
||||
- ``dom0``
|
||||
- property
|
||||
- `-`
|
||||
- ``help``
|
||||
-
|
||||
* - ``admin.property.HelpRst``
|
||||
- ``dom0``
|
||||
- property
|
||||
- `-`
|
||||
- ``help.rst``
|
||||
-
|
||||
* - ``admin.property.Reset``
|
||||
- ``dom0``
|
||||
- property
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.property.Set``
|
||||
- ``dom0``
|
||||
- property
|
||||
- value
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.property.List``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<property>\n``
|
||||
-
|
||||
* - ``admin.vm.property.Get``
|
||||
- vm
|
||||
- property
|
||||
- `-`
|
||||
- ``default={True|False}`` ``type={str|int|bool|vm|label|list} <value>``
|
||||
- Type ``list`` is added in R4.1. Each list entry is suffixed with a newline character.
|
||||
* - ``admin.vm.property.GetAll``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<property-name> <full-value-as-in-property.Get>\n``
|
||||
- Get all the properties in one call. Each property is returned on a separate line and use the same value encoding as property.Get method, with an exception that newlines are encoded as literal ``\n`` and literal ``\`` are encoded as ``\\``.
|
||||
* - ``admin.vm.property.GetDefault``
|
||||
- vm
|
||||
- property
|
||||
- `-`
|
||||
- ``type={str|int|bool|vm|label|type} <value>``
|
||||
- Type ``list`` is added in R4.1. Each list entry is suffixed with a newline character
|
||||
* - ``admin.vm.property.Help``
|
||||
- vm
|
||||
- property
|
||||
- `-`
|
||||
- ``help``
|
||||
-
|
||||
* - ``admin.vm.property.HelpRst``
|
||||
- vm
|
||||
- property
|
||||
- `-`
|
||||
- ``help.rst``
|
||||
-
|
||||
* - ``admin.vm.property.Reset``
|
||||
- vm
|
||||
- property
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.property.Set``
|
||||
- vm
|
||||
- property
|
||||
- value
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.feature.List``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<feature>\n``
|
||||
-
|
||||
* - ``admin.vm.feature.Get``
|
||||
- vm
|
||||
- feature
|
||||
- `-`
|
||||
- value
|
||||
-
|
||||
* - ``admin.vm.feature.CheckWithTemplate``
|
||||
- vm
|
||||
- feature
|
||||
- `-`
|
||||
- value
|
||||
-
|
||||
* - ``admin.vm.feature.CheckWithNetvm``
|
||||
- vm
|
||||
- feature
|
||||
- `-`
|
||||
- value
|
||||
-
|
||||
* - ``admin.vm.feature.CheckWithAdminVM``
|
||||
- vm
|
||||
- feature
|
||||
- `-`
|
||||
- value
|
||||
-
|
||||
* - ``admin.vm.feature.CheckWithTemplateAndAdminVM``
|
||||
- vm
|
||||
- feature
|
||||
- `-`
|
||||
- value
|
||||
-
|
||||
* - ``admin.vm.feature.Remove``
|
||||
- vm
|
||||
- feature
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.feature.Set``
|
||||
- vm
|
||||
- feature
|
||||
- value
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.notes.Get``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- notes
|
||||
-
|
||||
* - ``admin.vm.notes.Set``
|
||||
- vm
|
||||
- `-`
|
||||
- notes
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.tag.List``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<tag>\n``
|
||||
-
|
||||
* - ``admin.vm.tag.Get``
|
||||
- vm
|
||||
- tag
|
||||
- `-`
|
||||
- ``0`` or ``1``
|
||||
- retcode?
|
||||
* - ``admin.vm.tag.Remove``
|
||||
- vm
|
||||
- tag
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.tag.Set``
|
||||
- vm
|
||||
- tag
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.firewall.Get``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<rule>\n``
|
||||
- rules syntax as in :doc:`firewall interface </developer/debugging/vm-interface>` (Firewall Rules in 4x) with addition of ``expire=`` and ``comment=`` options; ``comment=`` (if present) must be the last option
|
||||
* - ``admin.vm.firewall.Set``
|
||||
- vm
|
||||
- `-`
|
||||
- ``<rule>\n``
|
||||
- `-`
|
||||
- set firewall rules, see ``admin.vm.firewall.Get`` for syntax
|
||||
* - ``admin.vm.firewall.Reload``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- `-`
|
||||
- force reload firewall without changing any rule
|
||||
* - ``admin.vm.device.<class>.Attach``
|
||||
- vm
|
||||
- device
|
||||
- assignment-serialization
|
||||
- `-`
|
||||
- ``device`` is in form ``<backend-name>+<device-ident>`` optional options given in ``key=value`` format, separated with spaces; options can include ``persistent=True`` to "persistently" attach the device (default is temporary)
|
||||
* - ``admin.vm.device.<class>.Detach``
|
||||
- vm
|
||||
- device
|
||||
- `-`
|
||||
- `-`
|
||||
- ``device`` is in form ``<backend-name>+<device-ident>``
|
||||
* - ``admin.vm.device.<class>.Detach``
|
||||
- vm
|
||||
- device
|
||||
- `-`
|
||||
- `-`
|
||||
- ``device`` is in form ``<backend-name>+<device-ident>``
|
||||
* - ``admin.vm.device.<class>.Assign``
|
||||
- vm
|
||||
- device
|
||||
- assignement-serialization
|
||||
- `-`
|
||||
- ``device`` is in form ``<backend-name>+<device-ident>`` ``assignment-serialization`` is specified in the section Device Serialization.
|
||||
* - ``admin.vm.device.<class>.Unassign``
|
||||
- vm
|
||||
- device
|
||||
- `-`
|
||||
- `-`
|
||||
- ``device`` is in form ``<backend-name>+<device-ident>``
|
||||
* - ``admin.vm.device.<class>.Set.required``
|
||||
- vm
|
||||
- device
|
||||
- ``True|False``
|
||||
- `-`
|
||||
- ``device`` is in form ``<backend-name>+<device-ident>``
|
||||
* - ``admin.vm.deviceclass.List``
|
||||
- `dom0`
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<deviceclass>\n``
|
||||
-
|
||||
* - ``admin.vm.device.<class>.Available``
|
||||
- vm
|
||||
- device-ident
|
||||
- `-`
|
||||
- ``<device-ident> <device-serialization>\n``
|
||||
- optional service argument may be used to get info about a single device, ``device-serialization`` is specified in the section Device Serialization.
|
||||
* - ``admin.vm.device.<class>.Assigned``
|
||||
- vm
|
||||
- device-ident
|
||||
- `-`
|
||||
- ``<device-ident> <assignment-serialization>\n``
|
||||
- optional service argument may be used to get info about a single device, ``assignement-serialization`` is specified in the section Device Serialization.
|
||||
* - ``admin.vm.device.<class>.Attached``
|
||||
- vm
|
||||
- device-ident
|
||||
- `-`
|
||||
- ``<device-ident> <assignment-serialization>\n``
|
||||
- optional service argument may be used to get info about a single device, ``assignment-serialization`` is specified in the section Device Serialization.
|
||||
* - ``admin.pool.List``
|
||||
- ``dom0``
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<pool>\n``
|
||||
-
|
||||
* - ``admin.pool.ListDrivers``
|
||||
- ``dom0``
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<pool-driver> <property> ...\n``
|
||||
- Properties allowed in ``admin.pool.Add``
|
||||
* - ``admin.pool.Info``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- `-`
|
||||
- ``<property>=<value>``
|
||||
-
|
||||
* - ``admin.pool.Add``
|
||||
- ``dom0``
|
||||
- driver
|
||||
- ``<property>=<value>\n``
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.pool.Set.revisions_to_keep``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- ``<value>``
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.pool.Remove``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.pool.volume.List``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- `-`
|
||||
- volume id
|
||||
-
|
||||
* - ``admin.pool.volume.Info``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- vid
|
||||
- ``<property>=<value>\n``
|
||||
-
|
||||
* - ``admin.pool.volume.Set.revisions_to_keep``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- ``<vid> <value>``
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.pool.volume.ListSnapshots``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- vid
|
||||
- ``<snapshot>\n``
|
||||
-
|
||||
* - ``admin.pool.volume.Snapshot``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- vid
|
||||
- snapshot
|
||||
-
|
||||
* - ``admin.pool.volume.Revert``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- ``<vid> <snapshot>``
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.pool.volume.Resize``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- ``<vid> <size_in_bytes>``
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.pool.volume.Import``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- ``<vid>\n<raw volume data>``
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.pool.volume.CloneFrom``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- vid
|
||||
- token, to be used in ``admin.pool.volume.CloneTo``
|
||||
- obtain a token to copy volume ``vid`` in ``pool``; the token is one time use only, it's invalidated by ``admin.pool.volume.CloneTo``, even if the operation fails
|
||||
* - ``admin.pool.volume.CloneTo``
|
||||
- ``dom0``
|
||||
- pool
|
||||
- ``<vid> <token>``
|
||||
- `-`
|
||||
- copy volume pointed by a token to volume ``vid`` in ``pool``
|
||||
* - ``admin.vm.volume.List``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<volume>\n``
|
||||
- ``<volume>`` is per-VM volume name (``root``, ``private``, etc), ``<vid>`` is pool-unique volume id
|
||||
* - ``admin.vm.volume.Info``
|
||||
- vm
|
||||
- volume
|
||||
- `-`
|
||||
- ``<property>=<value>\n``
|
||||
-
|
||||
* - ``admin.vm.volume.Set.revisions_to_keep``
|
||||
- vm
|
||||
- volume
|
||||
- value
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.volume.ListSnapshots``
|
||||
- vm
|
||||
- volume
|
||||
- `-`
|
||||
- snapshot
|
||||
- duplicate of ``admin.pool.volume.``, but with other call params
|
||||
* - ``admin.vm.volume.Snapshot``
|
||||
- vm
|
||||
- volume
|
||||
- `-`
|
||||
- snapshot
|
||||
- id.
|
||||
* - ``admin.vm.volume.Revert``
|
||||
- vm
|
||||
- volume
|
||||
- snapshot
|
||||
- `-`
|
||||
- id.
|
||||
* - ``admin.vm.volume.Resize``
|
||||
- vm
|
||||
- volume
|
||||
- size_in_bytes
|
||||
- `-`
|
||||
- id.
|
||||
* - ``admin.vm.volume.Import``
|
||||
- vm
|
||||
- volume
|
||||
- raw volume data
|
||||
- `-`
|
||||
- id.
|
||||
* - ``admin.vm.volume.ImportWithSize``
|
||||
- vm
|
||||
- volume
|
||||
- ``<size_in_bytes>\n<raw volume data>``
|
||||
- `-`
|
||||
- new version of ``admin.vm.volume.Import``, allows new volume to be different size
|
||||
* - ``admin.vm.volume.Clear``
|
||||
- vm
|
||||
- volume
|
||||
- `-`
|
||||
- `-`
|
||||
- clear contents of volume
|
||||
* - ``admin.vm.volume.CloneFrom``
|
||||
- vm
|
||||
- volume
|
||||
- `-`
|
||||
- token, to be used in ``admin.vm.volume.CloneTo``
|
||||
- obtain a token to copy ``volume`` of ``vm``; the token is one time use only, it's invalidated by ``admin.vm.volume.CloneTo``, even if the operation fails
|
||||
* - ``admin.vm.volume.CloneTo``
|
||||
- vm
|
||||
- volume
|
||||
- token, obtained with ``admin.vm.volume.CloneFrom``
|
||||
- `-`
|
||||
- copy volume pointed by a token to ``volume`` of ``vm``
|
||||
* - ``admin.vm.CurrentState``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- ``<state-property>=<value>``
|
||||
- state properties: ``power_state``, ``mem``, ``mem_static_max``, ``cputime``
|
||||
* - ``admin.vm.Start``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.Shutdown``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.Pause``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.Unpause``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.vm.Kill``
|
||||
- vm
|
||||
- `-`
|
||||
- `-`
|
||||
- `-`
|
||||
-
|
||||
* - ``admin.backup.Execute``
|
||||
- ``dom0``
|
||||
- config id
|
||||
- `-`
|
||||
- `-`
|
||||
- config in ``/etc/qubes/backup/<id>.conf``, only one backup operation of given ``config id`` can be running at once
|
||||
* - ``admin.backup.Info``
|
||||
- ``dom0``
|
||||
- config id
|
||||
- `-`
|
||||
- backup info
|
||||
- info what would be included in the backup
|
||||
* - ``admin.backup.Cancel``
|
||||
- ``dom0``
|
||||
- config id
|
||||
- `-`
|
||||
- `-`
|
||||
- cancel running backup operation
|
||||
* - ``admin.Events``
|
||||
- ``dom0|vm``
|
||||
- `-`
|
||||
- `-`
|
||||
- events
|
||||
-
|
||||
* - ``admin.vm.Stats``
|
||||
- ``dom0|vm``
|
||||
- `-`
|
||||
- `-`
|
||||
- ``vm-stats`` events, see below
|
||||
- emit VM statistics (CPU, memory usage) in form of events
|
||||
|
||||
|
||||
Volume properties:
|
||||
|
||||
- ``pool``
|
||||
- ``vid``
|
||||
- ``size``
|
||||
- ``usage``
|
||||
- ``rw``
|
||||
- ``source``
|
||||
- ``save_on_stop``
|
||||
- ``snap_on_start``
|
||||
- ``revisions_to_keep``
|
||||
- ``is_outdated``
|
||||
|
||||
Method ``admin.vm.Stats`` returns ``vm-stats`` events every
|
||||
``stats_interval`` seconds, for every running VM. Parameters of
|
||||
``vm-stats`` events:
|
||||
|
||||
- ``memory_kb`` - memory usage in kB
|
||||
- ``cpu_time`` - absolute CPU time (in milliseconds) spent by the VM
|
||||
since its startup, normalized for one CPU
|
||||
- ``cpu_usage`` - CPU usage in percents
|
||||
|
||||
Returned messages
|
||||
=================
|
||||
|
||||
First byte of a message is a message type. This is 8 bit non-zero
|
||||
integer. Values start at 0x30 (48, ``'0'``, zero digit in ASCII) for
|
||||
readability in hexdump. Next byte must be 0x00 (a separator).
|
||||
|
||||
This alternatively can be thought of as zero-terminated string
|
||||
containing single ASCII digit.
|
||||
|
||||
OK (0)
|
||||
------
|
||||
|
||||
::
|
||||
|
||||
30 00 <content>
|
||||
|
||||
Server will close the connection after delivering single message.
|
||||
|
||||
EVENT (1)
|
||||
---------
|
||||
|
||||
::
|
||||
|
||||
31 00 <subject> 00 <event> 00 ( <key> 00 <value> 00 )* 00
|
||||
|
||||
Events are returned as stream of messages in selected API calls.
|
||||
Normally server will not close the connection.
|
||||
|
||||
A method yielding events will not ever return a ``OK`` or ``EXCEPTION``
|
||||
message.
|
||||
|
||||
When calling such method, it will produce an artificial event
|
||||
``connection-established`` just after connection, to help avoiding race
|
||||
conditions during event handler registration.
|
||||
|
||||
EXCEPTION (2)
|
||||
-------------
|
||||
|
||||
::
|
||||
|
||||
32 00 <type> 00 ( <traceback> )? 00 <format string> 00 ( <field> 00 )*
|
||||
|
||||
Server will close the connection.
|
||||
|
||||
Traceback may be empty, can be enabled server-side as part of debug
|
||||
mode. Delimiting zero-byte is always present.
|
||||
|
||||
Fields should be formatted to ``%``-style format string, possibly
|
||||
after client-side translation, to form final message to be displayed
|
||||
to the user. Server does not by itself support translation.
|
||||
|
||||
Tags
|
||||
====
|
||||
|
||||
The tags provided can be used to write custom policies. They are not
|
||||
used in a default Qubes OS installation. However, they are created
|
||||
anyway.
|
||||
|
||||
- ``created-by-<vm>`` — Created in an extension to `qubesd` at the moment
|
||||
of creation of the VM. Cannot be changed via API, which is also
|
||||
enforced by this extension.
|
||||
- ``managed-by-<vm>`` — Can be used for the same purpose, but it is not
|
||||
created automatically, nor is it forbidden to set or reset this tag.
|
||||
|
||||
Backup profile
|
||||
==============
|
||||
|
||||
Backup-related calls do not allow (yet) to specify what should be
|
||||
included in the backup. This needs to be configured separately in dom0,
|
||||
with a backup profile, stored in ``/etc/qubes/backup/<profile>.conf``.
|
||||
The file use yaml syntax and have following settings:
|
||||
|
||||
- ``include`` - list of VMs to include, can also contains tags using
|
||||
``$tag:some-tag`` syntax or all VMs of given type using
|
||||
``$type:AppVM``, known from qrexec policy
|
||||
- ``exclude`` - list of VMs to exclude, after evaluating ``include``
|
||||
setting
|
||||
- ``destination_vm`` - VM to which the backup should be send
|
||||
- ``destination_path`` - path to which backup should be written in
|
||||
``destination_vm``. This setting is given to ``qubes.Backup`` service
|
||||
and technically it’s up to it how to interpret it. In current
|
||||
implementation it is interpreted as a directory where a new file
|
||||
should be written (with a name based on the current timestamp), or a
|
||||
command where the backup should be piped to
|
||||
- ``compression`` - should the backup be compressed (default: True)?
|
||||
The value can be either ``False`` or ``True`` for default
|
||||
compression, or a compression command (needs to accept ``-d``
|
||||
argument for decompression)
|
||||
- ``passphrase_text`` - passphrase used to encrypt and integrity
|
||||
protect the backup
|
||||
- ``passphrase_vm`` - VM which should be asked what backup passphrase
|
||||
should be used. The asking is performed using
|
||||
``qubes.BackupPassphrase+profile_name`` service, which is expected to
|
||||
output chosen passphrase to its stdout. Empty output cancel the
|
||||
backup operation. This service can be used either to ask the user
|
||||
interactively, or to have some automated passphrase handling (for
|
||||
example: generate randomly, then encrypt with a public key and send
|
||||
somewhere)
|
||||
|
||||
Not all settings needs to be set.
|
||||
|
||||
Example backup profile:
|
||||
|
||||
.. code:: yaml
|
||||
|
||||
# Backup only selected VMs
|
||||
include:
|
||||
- work
|
||||
- personal
|
||||
- ``vault``
|
||||
- banking
|
||||
|
||||
# Store the backup on external disk
|
||||
destination_vm: sys-usb
|
||||
destination_path: /media/my-backup-disk
|
||||
|
||||
# Use static passphrase
|
||||
passphrase_text: "My$Very!@Strong23Passphrase"
|
||||
|
||||
And slightly more advanced one:
|
||||
|
||||
.. code:: yaml
|
||||
|
||||
# Include all VMs with a few exceptions
|
||||
include:
|
||||
- $type:AppVM
|
||||
- $type:TemplateVM
|
||||
- $type:StandaloneVM
|
||||
exclude:
|
||||
- untrusted
|
||||
- $tag:do-not-backup
|
||||
|
||||
# parallel gzip for faster backup
|
||||
compression: pigz
|
||||
|
||||
# ask 'vault' VM for the backup passphrase
|
||||
passphrase_vm: vault
|
||||
|
||||
# send the (encrypted) backup directly to remote server
|
||||
destination_vm: sys-net
|
||||
destination_path: ncftpput -u my-ftp-username -p my-ftp-pass -c my-ftp-server /directory/for/backups
|
||||
|
||||
Device Serialization
|
||||
--------------------
|
||||
|
||||
Both device and assignment serialization is ASCII-encoded and contains space-separated key-value pairs. The format includes an ``=`` between the key and value, and the value is always enclosed in single quotes (``'``). Values may contain spaces or even single quotes, which are escaped with a backslash. If a value is not set (``None``), it is represented as ``'unknown'``. For boolean values, ``True`` is represented as ``'yes'``, and ``False`` as ``'no'``. The order of key-value pairs is irrelevant. Keys starting with ``_`` are considered extra properties and are saved in ``data`` or ``options`` for device or assignment respectively.
|
||||
|
||||
Information about the serialization format of specific properties can be found below.
|
||||
|
||||
Format:
|
||||
|
||||
::
|
||||
|
||||
<ident> <property_1>='<value_1>' <property_2>='<value_2>' <property_3>='<value_3>'...
|
||||
|
||||
Detailed serialization format for a device:
|
||||
|
||||
- ``ident='<ident>'``
|
||||
- ``backend_domain='<backend_domain.name>'``
|
||||
- ``devclass='<devclass>'``
|
||||
- ``vendor='<vendor>'``
|
||||
- ``product='<product>'``
|
||||
- ``manufacturer='<manufacturer>'``
|
||||
- ``name='<name>'``
|
||||
- ``serial='<serial>'``
|
||||
- ``self_identity='<self_identity>'``
|
||||
- ``interfaces='<interface1><interface2>...'`` Each device interface is represented with a 7-character length. Each device has at least one interface. Since the length of the interface representation is known, they are serialized as a single string with each interface representation concatenated one after another. The order is irrelevant.
|
||||
- ``parent_ident='<parent.ident>' parent_devclass='<parent.devclass>'``
|
||||
- ``attachment='<attachment.name>'``
|
||||
- ``_<key1>='<value1>' _<key2>='<value2>' ...`` (extra parameters)
|
||||
|
||||
Detailed serialization format for an assignment:
|
||||
|
||||
- ``ident='<ident>'``
|
||||
- ``backend_domain='<backend_domain.name>'``
|
||||
- ``devclass='<devclass>'``
|
||||
- ``frontend_domain='<frontend_domain.name>'``
|
||||
- ``required='<yes/no>'`` (default ‘no’)
|
||||
- ``attach_automatically='<yes/no>'`` (default ‘no’)
|
||||
- ``_<key1>='<str(value1)>' _<key2>='<str(value2)>' ...`` (options)
|
||||
|
||||
Example device serialization:
|
||||
|
||||
::
|
||||
|
||||
1-1.1.1 manufacturer='unknown' self_identity='0000:0000::?******' serial='unknown' ident='1-1.1.1' product='Qubes' vendor='ITL' name='Some untrusted garbage' devclass='bus' backend_domain='vm' interfaces=' ******u03**01' _additional_info='' _date='06.12.23' parent_ident='1-1.1' parent_devclass='None'
|
||||
|
||||
General notes
|
||||
=============
|
||||
|
||||
- there is no provision for ``qvm-run``, but there already exists
|
||||
``qubes.VMShell`` call
|
||||
- generally actions ``*.List`` return a list of objects and have
|
||||
“object identifier” as first word in a row. Such action can be also
|
||||
called with “object identifier” in argument to get only a single
|
||||
entry (in the same format).
|
||||
- closing qrexec connection normally does *not* interrupt running
|
||||
operation; this is important to avoid leaving the system in
|
||||
inconsistent state
|
||||
- actual operation starts only after caller send all the parameters
|
||||
(including a payload), signaled by sending EOF mark; there is no
|
||||
support for interactive protocols, to keep the protocol reasonable
|
||||
simple
|
||||
|
||||
Policy admin API
|
||||
================
|
||||
|
||||
There is also an API to view and update :doc:`Qubes RPC policy files </developer/services/qrexec>` in dom0. All of the following calls have dom0 as
|
||||
destination:
|
||||
|
||||
+----------------------------+----------+------------------------+------------------+
|
||||
| call | argument | inside | return |
|
||||
+============================+==========+========================+==================+
|
||||
| ``policy.List`` | `-` | `-` | ``<name1> |
|
||||
| ``policy.include.List`` | | | \n<name2>\n...`` |
|
||||
+----------------------------+----------+------------------------+------------------+
|
||||
| ``policy.Get`` | name | `-` | ``<token> |
|
||||
| ``policy.include.Get`` | | | \n<content>`` |
|
||||
+----------------------------+----------+------------------------+------------------+
|
||||
| ``policy.Replace`` | name | ``<token>\n<content>`` | `-` |
|
||||
| ``policy.include.Replace`` | | | |
|
||||
+----------------------------+----------+------------------------+------------------+
|
||||
| ``policy.Remove`` | name | ``<token>`` | `-` |
|
||||
| ``policy.include.Remove`` | | | |
|
||||
+----------------------------+----------+------------------------+------------------+
|
||||
|
||||
The ``policy.*`` calls refer to main policy files
|
||||
(``/etc/qubes/policy.d/``), and the ``policy.include.*`` calls refer to
|
||||
the include directory (``/etc/qubes/policy.d/include/``). The
|
||||
``.policy`` extension for files in the main directory is always omitted.
|
||||
|
||||
The responses do not follow admin API protocol, but signal error using
|
||||
an exit code and a message on stdout.
|
||||
|
||||
The changes are validated before saving, so that the policy cannot end
|
||||
up in an invalid state (e.g. syntax error, missing include file).
|
||||
|
||||
In addition, there is a mechanism to prevent concurrent modifications of
|
||||
the policy files:
|
||||
|
||||
- A ``*.Get`` call returns a file along with a *token* (currently
|
||||
implemented as a hash of the file).
|
||||
- When calling ``Replace`` or ``Remove``, you need to include the
|
||||
current token as first line. If the token does not match, the
|
||||
modification will fail.
|
||||
- When adding a new file using ``Replace``, pass ``new`` as token. This
|
||||
will ensure that the file does not exist before adding.
|
||||
- To skip the check, pass ``any`` as token.
|
||||
|
||||
TODO
|
||||
====
|
||||
|
||||
- notifications
|
||||
|
||||
- how to constrain the events?
|
||||
- how to pass the parameters? maybe XML, since this is trusted
|
||||
anyway and parser may be complicated
|
||||
|
||||
- how to constrain the possible values for ``admin.vm.property.Set``
|
||||
etc, like “you can change ``netvm``, but you have to pick from this
|
||||
set”; this currently can be done by writing an extension
|
||||
- a call for executing ``*.desktop`` file from
|
||||
``/usr/share/applications``, for use with appmenus without giving
|
||||
access to ``qubes.VMShell``; currently this can be done by writing
|
||||
custom qrexec calls
|
||||
- maybe some generator for ``.desktop`` for appmenus, which would wrap
|
||||
calls in ``qrexec-client-vm``
|
||||
|
||||
.. raw:: html
|
||||
|
||||
<!-- vim: set ts=4 sts=4 sw=4 et : -->
|
Loading…
Add table
Add a link
Reference in a new issue