Date: Thu, 28 Mar 2024 10:20:20 +0000 (UTC) Message-ID: <878866072.115.1711621220873@653043b1c6c6> Subject: Exported From Confluence MIME-Version: 1.0 Content-Type: multipart/related; boundary="----=_Part_114_382517430.1711621220873" ------=_Part_114_382517430.1711621220873 Content-Type: text/html; charset=UTF-8 Content-Transfer-Encoding: quoted-printable Content-Location: file:///C:/exported.html
iomem is a xl config file option that can be used = to map memory into a domU. Typically, it is used to map device memory into = a domU as part of device assignment. However it can also be used to setup a= cacheable shared memory region between dom0 and a domU. This section expla= ins how to do that.
First, we have to add a reserved-memory node to the host device tree to = advertise the special memory region to dom0, so that it won't use it to all= ocate memory as any other pages. For that, we can make use of the newly int= roduced "xen,shared-memory-v1" compatible string. For example:
&= nbsp; reserved-memory { #address-cells =3D <0x2>; #size-cells =3D <0x2>; ranges; xen-shmem@70000000 { compatible =3D "xen,shared-memory= -v1"; reg =3D <0x0 0x70000000 0x0 0x= 1000>; }; };
This node tells dom0 that one page at 0x70000000 is to be use as reserve= d memory. Then, we need to do the same for DomU. We can do that by adding a= device tree fragment to the DomU VM config file. The device tree fragment = could be for example:
/dts-v1/= ; / { /* #*cells are here to keep DTC happy */ #address-cells =3D <2>; #size-cells =3D <2>; passthrough { #address-cells =3D <2>; #size-cells =3D <2>; ranges; reserved-memory { #address-cells =3D <2>; #size-cells =3D <2>; ranges; xen-shmem@70000000 { compatible =3D "xen= ,shared-memory-v1"; reg =3D <0x0 0x7= 0000000 0x0 0x1000>; }; }; memory { &nb= sp;=20 device_type =3D "memory"; reg =3D <0x0 0x70000000 0x0 0x= 1000>; }; }; };
Similarly to the dom0 example, it tells the domU kernel that the page at= 0x70000000 is to be used as reserved memory. Note that we also added the r= ange to a regular memory node, because it is required by device tree that a= ll reserved-memory ranges are also covered by the regular memory node= s. We add the device tree fragment to the DomU device tree using the = device_tree option in the VM config file, the same way we use it for device= assignment:
device_t= ree =3D "/root/snippet.dtb"
Finally, we only need to map the page into the DomU address space at the= right address, which in this example is 0x70000000. We can do that with th= e iomem VM config option. It is possible to specify the cacheability of the= mapping, "memory" means normal cacheable memory:
iomem = =3D ["0x70000,1@0x70000,memory"]
In this example, we are asking to map one page at physical address 0x700= 00000 into the guest pseudo-physical address space at 0x70000000. We are al= so asking to make the mapping a normal cacheable memory mapping.
Please refer to the following docs in the Xen tree:
This feature allows sharing one or more pages in memory across VMs, simp= ly by adding one config option to the VM config file. Memory can be shared = as cacheable memory. Here is an example:
# Add fo= llowing to the config file of VM1:=20 static_shm =3D ["id=3DID1, begin=3D0x40000000, size=3D0x1000, role=3Downer"= ] # Add following to the config file of VM2:=20 static_shm =3D ["id=3DID1, begin=3D0x48000000, size=3D0x1000, role=3Dborrow= er"]
In this example we are sharing one page owned by VM1 with VM2. The owner= of the page is the "owner" VM (VM1), while the other VM is called "borrowe= r" (VM2). The memory of Xen VMs always starts at 0x40000000 (guest phy= sical address), so in this example we are sharing the first page of VM1 wit= h VM2. Make sure to choose a valid allocated address of the owner VM.<= /p>
0x48000000 is the address where the page will appear in VM2. Make sure t= o choose an free address in VM2. In this example, if we assigned 128M of RA= M to VM2, then the shared page will be mapped right at the end of memory.= p>
The shared page is advertised as "reserved-memory" in the guest device t= ree. This is a sample device tree node of a guest with a static_shm configu= ration:
reserved= -memory { #address-cells =3D = <0x2>; #size-cells =3D <= ;0x2>; ranges; xen-shmem@40000000 = {  = ; compatible =3D "xen,shared-memory-v1";  = ; id =3D "ID1";  = ; reg =3D <0x0 0x40000000 0x0 0x1000>; };
The guest is free to use the reserved-memory region as it wishes. For in= stance, in the case of the Linux kernel, it is possible to export the memor= y as cacheable memory to userspace with a dmabuf driver. See this proof of = concept of Linux driver and user-space program:
xen-dmabuf user space = program
Carve out a range of memory to be used for sharing
You can do that by editing the host device tree, reducing the amount of RAM=
in the memory node, and adding a separate new "mmio-sram" node as follows:=
--- mpso= c.dts.1 2019-10-31 16:00:35.574817353 -0700 +++ mpsoc.dts.2 2019-10-31 16:00:24.850379706 -0700 @@ -1738,6 +1738,11 @@ =20 memory { device_type =3D "memory"; - reg =3D <0x0 0x0 0x0 0x80000000 0x8 0x0 0x0 0x80000000>; + reg =3D <0x0 0x0 0x0 0x7f000000 0x8 0x0 0x0 0x80000000>; + }; + + sram@7f000000 { + compatible =3D "mmio-sram"; + reg =3D <0x0 0x7f000000 0x0 0x1000000>; }; };
In this example the range 0x7f000000 - 0x80000000 was removed from the memo=
ry node and exposed as a special mmio-sram region to be assigned.
If you don=E2=80=99t want dom0 to get access automatically to the range, ad=
d xen,passthrough; under the sram@7f000000 node.
Share the sram region with dom0-less domUs
Dom0 will get access to the sram region automatically (unless xen,passthrou=
gh; was specified). You can map the region to one or more dom0-less domUs b=
y adding an sram node to the dom0-less DomU partial device tree. For instan=
ce:
/dts-v1/= ; =20 / { #address-cells =3D <0x2>; #size-cells =3D <0x1>; =20 gic: gic { #interrupt-cells =3D <0x3>; interrupt-controller; }; =20 passthrough { compatible =3D "simple-bus"; ranges; #address-cells =3D <0x2>; #size-cells =3D <0x1>; =20 sram@7f000000 { compatible =3D "mmio-sram"; reg =3D <0x0 0x7f000000 0x0 0x1000000>; xen,reg =3D <0x0 0x7f000000 0x1000000 0x0 0x7f000000>; xen,force-assign-without-iommu =3D <0x1>; }; }; };
Note that the xen,reg property is key because it triggers the remapping of =
the memory range at the same location into the DomU. If you want to map the=
memory as cacheable is possible to use xen,reg-cacheable instead of xen,re=
g.
Use the sram region
When you boot the system, Dom0 and the DomUs will get a mapping of the sram=
region (0x7f000000 - 0x80000000) automatically. You can use the shared mem=
ory by calling `ioremap' in your kernel.