I’m working on a project using the i.MX8QM MEK board, where I’m responsible for implementing Interrupt Translation Services (ITS) and Locality-specific Peripheral Interrupt (LPI) support within a hypervisor environment for PCIe devices.
Thus, to test my implementation I'm using your board since it provides a PCIe Controller in RC mode and a GIC-500 with support for LPI and ITS.
When I use the MSI controller embedded in the PCIe controller, the PCIe device works fine. However, if I specify that I want to use ITS as my MSI Controller, the device doesn't work.
Next is my device tree:
gic:interrupt-controller@51a00000 {
compatible = "arm,gic-v3";
reg = <0x00 0x51a00000 0x00 0x10000 0x00 0x51b00000 0x00 0xc0000 0x00 0x52000000 0x00 0x2000 0x00 0x52010000 0x00 0x1000 0x00 0x52020000 0x00 0x20000>;
#interrupt-cells = <0x03>;
interrupt-controller;
interrupts = <0x01 0x09 0x04>;
interrupt-parent = <&gic>;
#address-cells = <0x02>;
#size-cells = <0x02>;
ranges;
phandle = <0x01>;
its@51a20000 {
reg = <0x00 0x51a20000 0x00 0x20000>;
phandle = <0x8004>;
compatible = "arm,gic-v3-its";
#msi-cells = <1>;
msi-controller;
};
};
pcie@5f000000 {
compatible = "fsl,imx8qm-pcie\0snps,dw-pcie";
reg = <0x5f000000 0x00 0x10000 0x6ff00000 0x00 0x80000>;
reg-names = "dbi", "config";
#address-cells = <0x03>;
#size-cells = <0x02>;
device_type = "pci";
bus-range = <0x00 0xff>;
ranges = <0x81000000 0x00 0x00 0x6ff80000 0x00 0x10000 0x82000000 0x00 0x60000000 0x60000000 0x00 0xff00000>;
num-lanes = <0x01>;
num-viewport = <0x04>;
interrupts = <0x00 0x46 0x04 0x00 0x48 0x04>;
interrupt-names = "msi\0dma";
#interrupt-cells = <0x01>;
interrupt-map-mask = <0x00 0x00 0x00 0x07>;
interrupt-map = <0x00 0x00 0x00 0x01 0x01 0x00 0x00 0x00 0x49 0x04 0x00 0x00 0x00 0x02 0x01 0x00 0x00 0x00 0x4a 0x04 0x00 0x00 0x00 0x03 0x01 0x00 0x00 0x00 0x4b 0x04 0x00 0x00 0x00 0x04 0x01 0x00 0x00 0x00 0x4c 0x04>;
clocks = <0xde 0x00 0xde 0x01 0xde 0x02>;
clock-names = "pcie\0pcie_bus\0pcie_inbound_axi";
power-domains = <0x18 0x98>;
fsl,max-link-speed = <0x03>;
hsio-cfg = <0x02>;
local-addr = <0x40000000>;
ctrl-csr = <0xd8>;
phys = <0xdf>;
phy-names = "pcie-phy";
status = "okay";
pinctrl-names = "default";
pinctrl-0 = <0xe0>;
reset-gpio = <0x7b 0x1d 0x01>;
host-wake-gpio = <0x7b 0x1c 0x01>;
vpcie-supply = <0xe1>;
interrupt-parent = <&gic>;
phandle = <0x229>;
msi-map-mask = <0xffff>;
msi-map = <0x00 0x8004 0x00 0x4>,
<0x100 0x8004 0x100 0x4>;
msi-parent= <0x8004>;
Is there any configuration that I missing? There are no dts in Linux repository regarding this board.
Is it even possible to use LPI as the MSI interrupts for PCIe devices with imx boards?
Thank you!
Hello,
Are you working on latest BSP? since all the configuration looks ok,
You can check this by running the command lspci -vv
and looking for the "Capabilities" section for your device. If you see "MSI" or "MSI-X" listed there
Enable MSI interrupts: To enable MSI interrupts for a particular device, you need to write to its configuration space. Use the setpci
command to do this. For example, to enable MSI interrupts on device 02:00.0, you can use the following command:
sudo setpci -s 02:00.0 COMMAND=0510
The 0510
value sets the "Command" register to enable MSI interrupts.
Check if MSI interrupts are enabled: After enabling MSI interrupts, you can verify if they are working properly by checking the kernel log. Use the dmesg
command and look for messages related to the device you enabled MSI for. If everything went smoothly, you should see something like "msi: Enable device interrupts succeeded" in the log.
Handle MSI interrupts in your code: Now that MSI interrupts are enabled, you need to handle them in your code. This involves registering an interrupt handler that will be called whenever the device sends an interrupt. The exact process for this depends on your programming language and framework, so you'll need to consult the documentation for your specific setup.
Regards