Skip to content
Snippets Groups Projects
Commit 813bf49b authored by Philipp Stanner's avatar Philipp Stanner Committed by Danilo Krummrich
Browse files

rust: add basic abstractions for iomem operations


Access to the kernel's IO-functions (e.g., readb()) is needed by almost
all drivers. Currently, there are no abstractions for those functions.

Since iomem is so widely used, it's necessary to provide a generic
interface that all subsystems providing IO memory can use. The existing
C implementations of such subsystems typically provide their own
wrappers around functions like ioremap() which take care of respecting
resource boundaries etc. It is, therefore, desirable to use these
wrappers because using ioremap() and iounmap() directly would
effectively result in parts of those subsystems being reimplemented in
Rust.

As most if not all device drivers should be fully satisfied regarding
their iomem demands by the existing subsystem interfaces, Rust
abstractions as congruent as possible with the existing infrastructure
shall use the existing subsystem (e.g., PCI) interfaces for creating
IO mappings, while simultaneously wrapping those mappings in Rust
containers whose Drop() traits ensure that the resources are released
again.

The process for mapping iomem would consequently look as follows:

  1. The subsystem abstraction (e.g., PCI) requests and ioremaps the
     memory through the corresponding C functions.
  2. The subsystem uses resources obtained in step #1 to create a Rust
     IoMem data structure that implements the IO functionality such as
     readb() for the iomem.
  3. The subsystem code wrapps IoMem into additional containers that
     ensure, e.g., thread safety, prevent UAF etc. Additionally, the
     subsystem ensures that access to IoMem is revoked latest when the
     driver's remove() callback is invoked.

Hereby, the subsystem data structure obtains ownership over the iomem.
Release of the iomem and, possibly, other subsystem associated data is
then handled through the Drop() trait of the subsystem data structure.

IO memory can become invalid during runtime (for example because the
driver's remove() callback was invoked, revoking access to the driver's
resources). However, in parallel executing routines might still be
active. Consequently, the subsytem should also guard the iomem in some
way.

One way to do this is the Devres implementation, which provides a
container that is capable of revoking access to its payload when
the driver's remove() callback is invoked.

The figure illustrates what usage of IoMem through subsystems might look
like:
               Devres
  *------------------------------*
  |                              |
  |   subsystem data structure   |
  |   *----------------------*   |
  |   |        IoMem         |   |
  |   | *------------------* |   |
  |   | |  io_addr = 0x42, | |   |
  |   | |  io_len = 9001,  | |   |
  |   | |                  | |   |
  |   | |  readb(),        | |   |
  |   | |  writeb(),       | |   |
  |   | |  ...             | |   |
  |   | *------------------* |   |
  |   |   deref(),           |   |
  |   |   drop(),            |   |
  |   |   ...                |   |
  |   *----------------------*   |
  |    deref(),                  |
  |    drop(),                   |
  *------------------------------*

For additional convenience, subsystem abstractions can implement the
Deref() trait for their data structures so that access he iomem can be
fully transparent.

In summary, IoMem would just serve as a container providing the IO
functions, and the subsystem, which knows about the memory layout,
request mechanisms etc, shall create and guard IoMem and ensure that its
resources are released latest at remove() (through Devres) or earlier
through its Drop() implementation.

Add 'IoMem', a struct holding an IO-Pointer and a length parameter,
which both shall be initialized validly by the subsystem.

Add Rust abstractions for basic IO memory operations on IoMem.

Signed-off-by: default avatarPhilipp Stanner <pstanner@redhat.com>
Signed-off-by: default avatarDanilo Krummrich <dakr@redhat.com>
parent 4f19acb7
No related branches found
No related tags found
Loading
Loading
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment